If you've ever shared a link to your site on Slack, LinkedIn, Facebook, or Twitter and seen the wrong title or description appear — you've hit a very common SPA problem.
Modern JavaScript apps (React, Vite, Next in SPA mode, no-code builders, etc.) often break link previews. Here's why — and how DataJelly fixes it.
The Core Problem
Social platforms do not execute JavaScript when generating link previews.
When someone shares your URL:
- Slack (or Facebook, LinkedIn, etc.) sends a single HTTP request.
- It reads the raw HTML response.
- It parses
<meta property="og:*">and Twitter Card tags from the<head>. - It builds the preview.
That's it. No JavaScript engine. No DOM rendering. No client-side hydration.
If your site relies on client-side rendering to inject metadata (via React Helmet or similar), the social bot never sees it.
Why This Breaks in SPAs
In most SPAs:
- The server returns a generic
index.htmlshell. - Open Graph tags are identical across all routes.
- React Helmet updates metadata in the live DOM — after JavaScript executes.
- Bots never execute that runtime code.
The result?
- Every shared link shows your homepage title.
/pricing,/blog/post,/docs/api— all preview the same.- You lose clarity, context, and engagement.
What DataJelly Does Differently
When Social Preview Stabilization is enabled for a domain, DataJelly fixes this at the edge.
Fully Rendered Snapshot
DataJelly captures a fully rendered HTML snapshot of each route — after JavaScript execution. That means:
- React Helmet metadata is present.
- Route-specific
<title>is correct. - Dynamic OG tags are applied.
- The DOM reflects what users actually see.
Intelligent Metadata Extraction
From that rendered snapshot, DataJelly extracts:
og:titleog:descriptionog:imageog:urlog:type- Twitter equivalents (
twitter:card,twitter:title, etc.)
If multiple versions of a tag exist (e.g., static shell + React Helmet), DataJelly:
- Prefers tags marked with
data-react-helmet="true" - Falls back to standard
og:*,twitter:*, or<meta name="description">if needed
This ensures the runtime metadata wins over the static shell.
Purpose-Built Social Preview HTML
Instead of returning your full app HTML, DataJelly generates a minimal document that contains only what social platforms need:
<title>og:*tags- Twitter Card tags
No scripts. No layout. No SPA shell.
Just clean metadata.
Edge-Level Bot Routing
At request time, DataJelly classifies the incoming user agent:
- Human
- Search engine bot
- AI bot
- Social preview bot
If the request is from facebookexternalhit, Slackbot, Twitterbot, LinkedInBot, etc. — and Social Preview Stabilization is enabled:
👉 DataJelly serves the minimal social preview HTML.
Everything else remains unchanged. Humans get your app. Search bots get rendered HTML. AI bots get Markdown.
Multi-Representation Architecture
With DataJelly enabled, each route can serve different representations depending on who is asking:
| Audience | Response Returned |
|---|---|
| 🧑 Human | Origin application |
| 🔍 Search engine | Pre-rendered SEO snapshot |
| 🤖 AI bot | Structured Markdown (optional) |
| 📱 Social bot | Minimal Social Preview HTML |
Each system gets exactly what it needs — nothing more, nothing less.
Why This Matters
Broken previews hurt:
- Click-through rates
- Trust
- Clarity
- Brand perception
And the worst part? Most developers don't realize it's happening — because everything looks fine in the browser.
Social Preview Stabilization fixes link previews without requiring frontend changes.
- No refactor.
- No SSR migration.
- No code rewrite.
Just flip a toggle per domain.
Manage & Monitor with DataJelly
DataJelly doesn't just fix social previews — it gives you full visibility and control over the Open Graph data being served for every page on your site.
Social Preview Audit
Most AI-built SPAs share a dirty secret: every page has identical OG data. Your homepage, pricing page, about page, and blog posts all show the same generic title and description when shared on social platforms.
DataJelly's Social Preview Audit automatically detects this. It groups pages with duplicate OG data, flags pages with missing metadata entirely, and highlights the pages that already have unique, correct previews.

Per-Page OG Management
DataJelly automatically extracts unique Open Graph data per page from your rendered snapshots. But for key pages — your homepage, pricing, about, etc. — you may want full manual control.
The Social Pages dashboard lets you see every route's OG title, description, and image at a glance. You can override any page's metadata directly, and those custom values persist across future crawls — they won't be overwritten.

Manual Override
Need your pricing page to say something specific when shared? Click edit on any page and set the exact OG title, description, image URL, and canonical URL. Your custom values are served to social bots going forward — no code changes needed.

The Result
Instead of this:
❌ Every shared link shows your homepage.
You get this:
✅ /pricing → Pricing preview
✅ /blog/how-we-built-this → Blog preview
✅ /docs/api → API docs preview
Correct. Route-specific. Deterministic.
Related Guides
Lovable SEO 101
Complete SEO guide for Lovable.dev sites.
SPA SEO Guide
Fix routing, metadata, and indexing in SPAs.
Bot Detection & Edge Routing
How DataJelly identifies bots at the edge.
Visibility Layer Guide
Fix AI and search visibility for JavaScript apps.
Fixing Broken Social Previews
The original announcement blog post.
