Blog heroes
Hero images for article pages. Wider than OG — ideal for above-the-fold banners on long-form posts.
Unlike OG images, hero images aren’t consumed by social crawlers, so there’s no public GET endpoint. Generate them server-side with an API key and embed the returned CDN URL directly in your HTML.
Generate
POST /api/images/generate
Authorization: Bearer ogsk_live_...
Content-Type: application/json
{
"projectId": "...",
"url": "https://example.com/blog/post-title",
"kind": "blog_hero",
"template": "panorama",
"style": { "aspectRatio": "16:9" }
}The response includes a cdnUrl — a permanent link to the rendered PNG on cdn.ogstack.dev. Store it alongside your post and serve it directly; no further API calls are needed to display the image.
Aspect ratios
aspectRatio | Dimensions |
|---|---|
16:9 | 1600 × 900 |
16:10 | 1920 × 1080 |
Default is 16:9. Pick 16:10 when your layout has a wider hero slot.
Next.js app router example
// app/blog/[slug]/page.tsx
import Image from "next/image";
import { getPost } from "@/lib/posts";
export default async function Post({ params }: { params: { slug: string } }) {
const post = await getPost(params.slug);
return (
<article>
<Image src={post.heroUrl} alt="" width={1600} height={900} priority />
<h1>{post.title}</h1>
</article>
);
}post.heroUrl is the cdnUrl returned at publish time and persisted with the post.
Build-time generation
If you pre-render posts at build time, call the API in your build script and cache the returned URL as a build artifact:
const res = await fetch("https://api.ogstack.dev/api/images/generate", {
method: "POST",
headers: {
"Content-Type": "application/json",
Authorization: `Bearer ${process.env.OGSTACK_API_KEY}`,
},
body: JSON.stringify({
projectId: process.env.OGSTACK_PROJECT_ID,
url: pageUrl,
kind: "blog_hero",
template: "panorama",
}),
});
const { cdnUrl } = await res.json();Cache cdnUrl so you only pay for generation once per post.