satnaing / astro-paper

A minimal, accessible and SEO-friendly Astro blog theme
https://astro-paper.pages.dev/
MIT License
2.43k stars 510 forks source link

Failed to download dynamic font. Status: 400 #349

Closed JasonGrass closed 1 month ago

JasonGrass commented 2 months ago

When running the "astro build" command, I encounter the error: Failed to download dynamic font. Status: 400.

The specific location is in the loadGoogleFont function, const res = await fetch(resource[1]);

e.g. resource:

[
  "src: url(https://fonts.gstatic.com/l/font?kit=-F63fjptAgt5VM-kVkqdyU8n5igg0F9ltfHxrHOEdSEXWy7aHGpyzxyA3DWqrPf3xuinZcg&skey=b40c83751ce1954d&v=v19) format('truetype')",
  'https://fonts.gstatic.com/l/font?kit=-F63fjptAgt5VM-kVkqdyU8n5igg0F9ltfHxrHOEdSEXWy7aHGpyzxyA3DWqrPf3xuinZcg&skey=b40c83751ce1954d&v=v19',
  'truetype',
  index: 89,
  input: '@font-face {\n' +
    "  font-family: 'IBM Plex Mono';\n" +
    '  font-style: normal;\n' +
    '  font-weight: 400;\n' +
    "  src: url(https://fonts.gstatic.com/l/font?kit=-F63fjptAgt5VM-kVkqdyU8n5igg0F9ltfHxrHOEdSEXWy7aHGpyzxyA3DWqrPf3xuinZcg&skey=b40c83751ce1954d&v=v19) format('truetype');\n" +
    '}\n',
  groups: undefined
]

resource[1]:

https://fonts.gstatic.com/l/font?kit=-F63fjptAgt5VM-kVkqdyU8n5igg0F9ltfHxrHOEdSEXWy7aHGpyzxyA3DWqrPf3xuinZcg&skey=b40c83751ce1954d&v=v19

When I request this URL directly in the browser, the same error occurs:

image

This error also happens when building with vercel .

Any help would be greatly appreciated.

JasonGrass commented 2 months ago

I temporarily circumvented this issue by using local font files.

loadGoogleFont.ts

import type { FontStyle, FontWeight } from "satori";
import * as fs from "fs";
import * as path from "path";
import { fileURLToPath, pathToFileURL } from "url";

export type FontOptions = {
  name: string;
  data: ArrayBuffer;
  weight: FontWeight | undefined;
  style: FontStyle | undefined;
};

// read font ArrayBuffer
function readFileAsArrayBuffer(filePath: string): Promise<ArrayBuffer> {
  return new Promise((resolve, reject) => {
    fs.readFile(filePath, (err, data) => {
      if (err) {
        reject(err);
      } else {
        resolve(
          data.buffer.slice(data.byteOffset, data.byteOffset + data.byteLength)
        );
      }
    });
  });
}

async function createFontOptionsByLocal(): Promise<
  Array<{ name: string; data: ArrayBuffer; weight: number; style: string }>
> {
  const __filename = fileURLToPath(import.meta.url);
  const __dirname = path.dirname(__filename);

  const fontPath1 = path.join(
    __dirname,
    "../../resources/",
    "ibm-plex-mono-v19-latin-regular.ttf"
  );
  const fontPath2 = path.join(
    __dirname,
    "../../resources/",
    "ibm-plex-mono-v19-latin-700.ttf"
  );
  const fontData1 = await readFileAsArrayBuffer(fontPath1);
  const fontData2 = await readFileAsArrayBuffer(fontPath2);

  return [
    { name: "IBM Plex Mono", weight: 400, style: "normal", data: fontData1 },
    { name: "IBM Plex Mono", weight: 700, style: "bold", data: fontData2 },
  ];
}

// export default loadGoogleFonts;
export default createFontOptionsByLocal;

generate font file by https://gwfh.mranftl.com/fonts

ibm-plex-mono-v19-latin-700.zip ibm-plex-mono-v19-latin-regular.zip

satnaing commented 2 months ago

Hello! Is it still happening? When I test, it works fine. How can I reproduce?

JasonGrass commented 2 months ago

I found where the problem lies. The text parameter of loadGoogleFont cannot contain non-English characters.

async function loadGoogleFont(
  font: string,
  text: string
)
yclgkd commented 1 month ago

I found where the problem lies. The text parameter of loadGoogleFont cannot contain non-English characters.

async function loadGoogleFont(
  font: string,
  text: string
)

The same problem, finally I chose a font that supports non-English characters, the problem is solved.

const fontsConfig = [
    {
      name: "Noto Sans SC",
      font: "Noto+Sans+SC",
      weight: 400 as FontWeight,
      style: "normal" as FontStyle,
    },
    {
      name: "Noto Sans SC",
      font: "Noto+Sans+SC:wght@700",
      weight: 700 as FontWeight,
      style: "normal" as FontStyle,
    },
  ];