I'm using puppeteer-core with chrome-aws-lambda in a Firebase Cloud Function to scrape a webpage and apply a custom font. However, despite injecting the @font-face rule via page.addStyleTag, the font is not applied in the generated screenshot.
const scraper = async (url: string) => {
let browser;
try {
browser = await puppeteer.launch({
args: ["--no-sandbox", "--disable-web-security"],
executablePath: await chromium.executablePath,
headless: chromium.headless,
});
const page = await browser.newPage();
// Set user agent and viewport for mobile
await page.setUserAgent(
"Mozilla/5.0 (Linux; Android 11; Pixel 5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/119.0.0.0 Mobile Safari/537.36"
);
await page.setViewport({ width: 390, height: 844, deviceScaleFactor: 3 });
await page.goto(url, { waitUntil: "domcontentloaded" });
await page.waitForTimeout(5000); // Ensure the font has time to load
// Load custom font
const fontPath = path.join(__dirname, "..", "fonts", "Vazirmatn-Regular.ttf");
const fontBuffer = fs.readFileSync(fontPath);
const fontBase64 = fontBuffer.toString("base64");
const fontDataUrl = `data:font/ttf;base64,${fontBase64}`;
// Inject font into the page
await page.addStyleTag({
content: `
@font-face {
font-family: 'Vazirmatn';
src: url(${fontDataUrl}) format('truetype');
}
* {
font-family: 'Vazirmatn', sans-serif !important;
font-size: 24px;
}
`,
});
// Capture screenshot or evaluate page styles
await page.screenshot({ path: "output.png", fullPage: true });
} catch (error) {
console.error("Error scraping website:", error);
throw new Error("Failed to scrape website");
} finally {
if (browser) {
await browser.close();
}
}
};