diff --git a/src/Integrations/Divi/Design/FontInstaller.php b/src/Integrations/Divi/Design/FontInstaller.php index 8a99a45..da75ea5 100644 --- a/src/Integrations/Divi/Design/FontInstaller.php +++ b/src/Integrations/Divi/Design/FontInstaller.php @@ -81,7 +81,7 @@ class FontInstaller implements DiviAdapter * @param array $files Extension => temp file path (deleted or moved by WordPress). * @return list The extensions Divi stored – fewer than $files on a partial success. * @throws DiviLocked When font-upload is not released – before anything is written. - * @throws RuntimeException When Divi's font list is corrupt or Divi refuses a file or the whole font; nothing is stored then. + * @throws RuntimeException When Divi's font list is corrupt or Divi refuses a file or the font; nothing is stored. */ public function install(string $name, array $files, string $weights, string $family): array { diff --git a/src/Integrations/Media/RemoteFileFetcher.php b/src/Integrations/Media/RemoteFileFetcher.php index 3bb67b3..6a0f10b 100644 --- a/src/Integrations/Media/RemoteFileFetcher.php +++ b/src/Integrations/Media/RemoteFileFetcher.php @@ -42,8 +42,8 @@ class RemoteFileFetcher } /** - * Streams $url into $tmp; fetch() checks the URL itself (allows()), the caller checks the size of $tmp afterwards (a body above - * $maxBytes is cut off at $maxBytes + 1 bytes). + * Streams $url into $tmp; fetch() checks the URL itself (allows()), the caller checks the size of $tmp afterwards + * (a body above $maxBytes is cut off at $maxBytes + 1 bytes). * * @param string $context Names the download in the failure log, e.g. "media import". * @return array|null The response (headers, status), null when the download failed. diff --git a/tests/Integration/divi-theme-fonts-smoke.sh b/tests/Integration/divi-theme-fonts-smoke.sh index d313119..0724126 100755 --- a/tests/Integration/divi-theme-fonts-smoke.sh +++ b/tests/Integration/divi-theme-fonts-smoke.sh @@ -118,7 +118,9 @@ pass "theme_options snapshot restored (body_font_size, content_width, heading_fo UPLOAD=$(jq -cn --arg n "$FONT_NAME" --arg u "$FONT_URL" '{name: $n, files: {woff2: $u}, weights: "all"}') DRY=$(ability lit/divi-fonts-upload "$UPLOAD") [ "$(error_code "$DRY")" = "confirm_required" ] || fail "font dry run: $DRY" -echo "$DRY" | grep -q 'woff2' || fail "dry run does not name the format: $DRY" +echo "$DRY" | jq -e '.__error | fromjson | [.. | objects | select(has("sha256"))] + | length == 1 and (.[0].format == "woff2") and (.[0].sha256 | test("^[0-9a-f]{64}$")) and (.[0].bytes | type == "number" and . > 0)' >/dev/null \ + || fail "dry run does not report format, byte count and a 64-hex sha256: $DRY" LIT_FONT="$FONT_NAME" wp eval 'exit(isset(get_option("et_uploaded_fonts", [])[getenv("LIT_FONT")]) ? 1 : 0);' \ || fail "dry run installed the font" pass "font dry run installs nothing" @@ -128,13 +130,17 @@ DONE=$(ability lit/divi-fonts-upload "$(echo "$UPLOAD" | jq -c '. + {confirm: tr [ "$(echo "$DONE" | jq -r '.ok')" = "true" ] || fail "font upload: $DONE" LIT_FONT="$FONT_NAME" wp eval '$f = get_option("et_uploaded_fonts", [])[getenv("LIT_FONT")] ?? null; exit($f && isset($f["font_url"]["woff2"]) ? 0 : 1);' \ || fail "font not stored in et_uploaded_fonts" +# The stored file is on disk: font_file is the path (or, if Divi stores URLs only, the URL mapped into the uploads dir). +LIT_FONT="$FONT_NAME" wp eval '$f = get_option("et_uploaded_fonts", [])[getenv("LIT_FONT")]; $p = $f["font_file"]["woff2"] ?? ""; if ($p !== "" && !file_exists($p)) { $u = wp_get_upload_dir(); $p = str_replace($u["baseurl"], $u["basedir"], $f["font_url"]["woff2"] ?? $p); } exit($p !== "" && file_exists($p) && filesize($p) > 0 ? 0 : 1);' \ + || fail "stored font file does not exist" AGAIN=$(ability lit/divi-fonts-upload "$(echo "$UPLOAD" | jq -c '. + {confirm: true}')") -[ "$(error_code "$AGAIN")" != "" ] || fail "a second upload of the same name was accepted: $AGAIN" +[ "$(error_code "$AGAIN")" = "conflict" ] || fail "a second upload of the same name was accepted: $AGAIN" pass "font installed through Divi, same name refused" # 8. The uploaded font is a valid theme font now; Arial (web-safe) is refused as a new font name. DONE=$(confirm lit/divi-theme-options-update "$(jq -cn --arg n "$FONT_NAME" '{set: {body_font: $n}}')") [ "$(echo "$DONE" | jq -r '.ok')" = "true" ] || fail "uploaded font as body_font: $DONE" +[ "$(theme_option body_font)" = "'$FONT_NAME'" ] || fail "uploaded font not stored as body_font" # A taken name (web-safe, Google, uploaded) is a conflict, see DiviFontsUploadAbility. RESERVED=$(ability lit/divi-fonts-upload "$(jq -cn --arg u "$FONT_URL" '{name: "Arial", files: {woff2: $u}, weights: "all"}')") [ "$(error_code "$RESERVED")" = "conflict" ] || fail "web-safe name accepted: $RESERVED"