The problem
Every product page needs an og:image - the preview card that shows up when someone links it on social media. Hiring a designer per image does not scale. Cloud OG services charge monthly and require API keys.
So I ported the open-source ilabs OG generator into the shop's admin panel - as a single PHP page with zero build step.
How it works
The whole thing is a <canvas> element:
1. Pick a template (Image Right, Hero, Logo Wall...)
2. Edit the text, upload a logo
3. Tune the gradient, grid and noise
4. Hit Save Image
cv.toBlob(blob => {
const a = document.createElement('a');
a.href = URL.createObjectURL(blob);
a.download = 'og.png';
a.click();
}, 'image/png');
That is the entire export pipeline. The PNG lands in the Downloads folder.
Templates as data
Each template is a plain object - default text, colors, background and a draw function:
const TEMPLATES = {
'og:image-right': {
fields: ['tag', 'title', 'logo', 'image'],
defaults: { params: {...}, bg: {...} },
draw: drawImageRight
}
};
Adding a new layout means writing one draw function and one entry. No routing, no state management, no framework.
The lesson
A surprising number of "SaaS features" are 400 lines of canvas code. Before reaching for a service, ask: could this run in the browser? For image generation, the answer is almost always yes.