Free tools / OG image generator

OG image generator

A 1200 × 630 card, rendered on the fast path, as a PNG you can point og:image at.

This one does not use a browser. The og-card template runs on Satori, which turns a flexbox subset of HTML straight into SVG and then into a PNG — no Chromium, no page load, and a fraction of the cost. It is the right engine for cards, badges and any layout that is boxes and text.

Every OG image on galleyrender.com is made this way, from this template, at build time. If you want the same thing in your own build, the render is one HTTP call and the cache means a rebuild that changes nothing costs nothing.

Small spaced line above the headline. Up to 60 characters.

Up to 120 characters. Required.

Up to 200 characters.

50 of 50 trial renders left on this device

No key needed. Your browser calls the production service directly.

An example 1200 by 630 social card rendered by Galley.
Example output. Fill the form in and press render card.

Response, verbatim
Press render card to see the real response.

Wiring it into a build

Render once per page at build time, upload the bytes wherever your assets live, and point the meta tag at them. Identical input returns the stored object, so rebuilding a site whose copy has not changed does not re-render anything.

A build stepjavascript
// Node 22+. One card per page, at build time.
async function ogCard(page) {
  const res = await fetch("https://api.galleyrender.com/v1/render", {
    method: "POST",
    headers: {
      authorization: `Bearer ${process.env.GALLEY_API_KEY}`,
      "content-type": "application/json",
    },
    body: JSON.stringify({
      template: "og-card@1",
      format: "png",
      data: {
        eyebrow: page.section,
        title: page.title,
        subtitle: page.description,
        accent: "#2dd4bf",
        background: "#0b0f14",
      },
    }),
  });

  const render = await res.json();
  if (!res.ok) throw new Error(render.error.message);

  // render.cached is true on every build after the copy stops changing.
  const bytes = await fetch(render.url).then((r) => r.arrayBuffer());
  return Buffer.from(bytes);
}

The og-card template and its schema · Chromium and Satori · Why the second build is free