Express.js Open Graph Tags: Add OG Meta to Your Node App
Add og:title, og:image, og:description and Twitter card tags to any Express.js app using template engines or string interpolation — with live examples.
Express.js + EJS: the quickest setup
// views/partials/head.ejs
<head>
<title><%= ogTitle %></title>
<meta property="og:title" content="<%= ogTitle %>" />
<meta property="og:description" content="<%= ogDescription %>" />
<meta property="og:image" content="<%= ogImage %>" />
<meta property="og:url" content="<%= ogUrl %>" />
<meta property="og:type" content="website" />
<meta name="twitter:card" content="summary_large_image" />
<meta name="twitter:title" content="<%= ogTitle %>" />
<meta name="twitter:image" content="<%= ogImage %>" />
</head>
// router/posts.js
router.get('/:slug', async (req, res) => {
const post = await Post.findOne({ slug: req.params.slug });
res.render('post', {
ogTitle: post.title,
ogDescription: post.excerpt,
ogImage: `https://yourdomain.com/og/${post.slug}.png`,
ogUrl: `https://yourdomain.com/posts/${post.slug}`,
});
});Express + Handlebars (HBS)
{{! views/layouts/main.hbs }}
<head>
<title>{{ogTitle}}</title>
<meta property="og:title" content="{{ogTitle}}" />
<meta property="og:description" content="{{ogDescription}}" />
<meta property="og:image" content="{{ogImage}}" />
<meta property="og:url" content="{{ogUrl}}" />
<meta name="twitter:card" content="summary_large_image" />
</head>
// route
res.render('post', {
layout: 'main',
ogTitle: post.title,
ogDescription: post.excerpt,
ogImage: `https://yourdomain.com/og/${post.slug}.png`,
ogUrl: req.protocol + '://' + req.get('host') + req.path,
});Express middleware for default OG tags
Add a middleware that sets default OG locals so every route has a fallback:
// middleware/og-defaults.js
module.exports = (req, res, next) => {
res.locals.ogTitle = 'My App — Default Title';
res.locals.ogDescription = 'Default description for my app.';
res.locals.ogImage = 'https://yourdomain.com/og/default.png';
res.locals.ogUrl = req.protocol + '://' + req.get('host') + req.originalUrl;
next();
};
// app.js
app.use(require('./middleware/og-defaults'));
// Individual routes can override res.locals.ogTitle etc.Express API + SPA frontend
If Express is your API backend and a React/Vue SPA is your frontend, OG tags must be set server-side — either via SSR, prerendering, or a dedicated bot-detection middleware that returns full HTML for scrapers. SPAs don't work for OG tags because social scrapers don't execute JavaScript.
The easiest solution: use a prerendering service like Prerender.io or serve a special SSR response when User-Agent matches a known scraper bot.
Verify your Express OG tags
After deploying, paste your URL into OGFixer to preview how Twitter, Slack, Discord, and LinkedIn will render your links.