Generating Open Graph preview images usually means running Playwright or Puppeteer on your own server — browser dependencies, a launch pool, queue management, and memory limits before you've written a single line of product logic.
One GET captures a screenshot of any public URL and returns it as base64 or raw binary:
curl --request GET \
--url 'https://api.sprytools.com/v1/screenshot/api/v1/screenshot?url=https://example.com&format=png&viewport=desktop&fullPage=false&blockAds=true' \
--header 'x-api-key: YOUR_API_KEY'
You get { success, format, width, height, fullPage, image, size } where image is a base64-encoded PNG you can drop straight into an <img> src or write to a file.
For OG images the standard canvas is 1200 × 630 — pass a custom viewport instead of the desktop preset:
const res = await fetch('https://api.sprytools.com/v1/screenshot/api/v1/screenshot', {
method: 'POST',
headers: {
'content-type': 'application/json',
'x-api-key': process.env.SPRYTOOLS_API_KEY,
},
body: JSON.stringify({
url: 'https://yourblog.com/posts/my-article',
viewport: { width: 1200, height: 630 },
format: 'png',
blockAds: true,
responseType: 'base64',
}),
});
const { image } = await res.json();
// image is ready to store in S3, Cloudflare R2, or serve from a Next.js route handler
Need to wait for a React or Vue page to finish hydrating before the screenshot fires? Add waitForSelector: '#hero-title' and the API holds until that element appears (up to the timeout you set, max 30 000 ms). format accepts png, jpeg, and webp; darkMode: true switches the OS colour scheme before capture.
Free key: 100 calls/day, no credit card — https://sprytools.com/apis/screenshot/
Do you generate OG images at build time or on-demand — and has one approach caused you more headaches than the other?
Top comments (0)