Skip to content

POST /render

Renders a single image from a structured JSON payload. Returns the binary image bytes directly — not a URL to an image.

POST https://og-engine.com/render

Authentication: Required (Authorization: Bearer oge_sk_...)

Field Type Required Default Constraints
format string Yes og, twitter, square, linkedin, story
template string No "default" default, social-card, blog-hero, email-banner, product-card, event, testimonial, github-repo, news-article, pricing, profile-card, announcement, or custom:<name> (Scale plan)
title string Yes Max 200 characters
description string No Max 500 characters
author string No Max 100 characters
tag string No Max 50 characters
variables object No {} Arbitrary key-value pairs (Record<string, string>) for template interpolation
images object No {} Named image URLs fetched server-side (Record<string, url>) for use in template image layers
style.accent string No "#38ef7d" Valid hex color (#rrggbb or #rgb)
style.font string No "Outfit" One of the 8 supported fonts
style.titleSize number No 48 28–72
style.descSize number No 22 14–32
style.layout string No "left" left, center, bottom
style.gradient string No "void" void, deep-sea, ember, forest, plum, slate
style.overlayOpacity number No 0.65 0.2–0.9 (used with background image)
style.autoFit boolean No false Auto-adjust font sizes to prevent overflow
output.format string No "png" png, webp (Starter+), pdf
output.quality number No 90 1–100 (WebP only)
Terminal window
curl -X POST https://og-engine.com/render \
-H "Authorization: Bearer oge_sk_YOUR_KEY" \
-H "Content-Type: application/json" \
-d '{
"format": "og",
"template": "default",
"title": "Server-Side Text Layout Without a Browser",
"description": "Pure JS text measurement replaces Puppeteer. ~22ms renders ([benchmarked](/benchmarks/)), zero browser dependencies.",
"author": "Pretext Engine",
"tag": "Open Source",
"style": {
"accent": "#38ef7d",
"font": "Outfit",
"titleSize": 48,
"descSize": 22,
"layout": "left",
"gradient": "void"
},
"output": {
"format": "png"
}
}' \
--output card.png

Use variables to pass arbitrary template interpolation data. Templates can reference these values to personalise content dynamically:

Terminal window
curl -X POST https://og-engine.com/render \
-H "Authorization: Bearer oge_sk_YOUR_KEY" \
-H "Content-Type: application/json" \
-d '{
"format": "og",
"template": "profile-card",
"title": "{{name}}",
"description": "{{bio}}",
"variables": {
"name": "Jane Smith",
"bio": "Staff Engineer at Acme Corp",
"handle": "@janesmith",
"followers": "4,200"
},
"output": { "format": "png" }
}' \
--output profile.png

Use images to pass server-fetched images by name. Custom templates can reference them via source on image layers:

Terminal window
curl -X POST https://og-engine.com/render \
-H "Authorization: Bearer oge_sk_YOUR_KEY" \
-H "Content-Type: application/json" \
-d '{
"format": "og",
"template": "custom:product-showcase",
"title": "Wireless Noise-Cancelling Headphones",
"description": "Premium sound. All day comfort.",
"images": {
"hero": "https://example.com/product-hero.jpg",
"logo": "https://example.com/brand-logo.png"
},
"output": { "format": "png" }
}' \
--output product.png

Named images are fetched server-side at render time. Each URL must be publicly accessible and return a valid JPEG, PNG, or WebP image under 5MB.

To supply a background image, use multipart/form-data. The JSON payload goes in a field named config, the image in image:

Terminal window
curl -X POST https://og-engine.com/render \
-H "Authorization: Bearer oge_sk_YOUR_KEY" \
-F 'config={
"format": "og",
"template": "blog-hero",
"title": "Building in the Open",
"style": { "overlayOpacity": 0.65 }
}' \
-F 'image=@cover.jpg' \
--output card.png

Accepted image formats: JPEG, PNG, WebP. Maximum size: 5MB.

On success, the response body is the raw binary image. The HTTP status is 200.

Header Example Description
Content-Type image/png MIME type (image/png, image/webp, or application/pdf)
X-Cache miss hit if served from image cache, miss otherwise
X-Render-Time-Ms 2.34 Server-side render time in milliseconds
X-Title-Lines 2 Number of lines the title was wrapped to
X-Desc-Lines 3 Number of lines the description was wrapped to
X-Layout-Overflow false true if any text was truncated with ellipsis
X-RateLimit-Limit 500 Monthly render quota
X-RateLimit-Remaining 483 Renders remaining this month
X-RateLimit-Reset 1735689600 Unix timestamp (seconds) of next quota reset

If your title or description is too long to fit within the max lines for the chosen format, OG Engine truncates the last visible line and appends . The response header X-Layout-Overflow: true signals this occurred.

To prevent truncation, use /validate before rendering to check fit, and adjust font size or shorten the text accordingly.

Status Code Cause
400 missing_field format or title not provided
400 invalid_format format is not one of the allowed values
400 invalid_font style.font is not a supported font
400 invalid_file Background image is too large or corrupt
401 unauthorized Missing or invalid API key
402 plan_required WebP output requested on Free plan
429 rate_limited Monthly quota exceeded
500 server_error Internal error
0.0ms|1300× vs Puppeteer
Accent
Font
Layout
Gradient
48
22