schema-org Article and schema-org BlogPosting unlock Top Stories carousel eligibility on mobile Search and Google Discover — two high-traffic surfaces where content without Article markup cannot appear. Google's documentation states that datePublished, author, and image are required for rich result eligibility; a blog post missing these fields is indexed as a plain page, not an article, losing carousel placement to competitors whose posts carry complete markup. For any site relying on organic content discovery, this is a direct distribution gap: the same words, worse placement, because the schema signals are missing.
Info because most blog traffic still flows through standard search results even without Article schema, but the absence closes Top Stories and Discover carousels entirely — a meaningful lost channel for content-driven sites.
Add BlogPosting or Article schema to your blog post template. Generate it server-side from your post metadata so the values always match visible content (mismatches between schema and visible text can trigger a rich result penalty).
// app/blog/[slug]/page.tsx
export default async function BlogPost({ params }: { params: { slug: string } }) {
const post = await getPost(params.slug)
const schema = {
'@context': 'https://schema.org',
'@type': 'BlogPosting',
headline: post.title, // must match <h1>
datePublished: post.publishedAt,
dateModified: post.updatedAt ?? post.publishedAt,
author: { '@type': 'Person', name: post.authorName },
image: post.coverImageUrl, // required for Top Stories
description: post.excerpt,
}
return (
<>
<script
type="application/ld+json"
dangerouslySetInnerHTML={{ __html: JSON.stringify(schema) }}
/>
{/* article content */}
</>
)
}
See the markup-content-match check to verify that schema field values stay in sync with visible page content.
ID: marketing-advanced-seo.structured-data.article-schema
Severity: info
What to look for: Count all content/blog pages. Enumerate which have Article or BlogPosting schema with datePublished, author, and headline properties. Check pages that render blog posts, news articles, documentation pages, or similar long-form content. Look for @type of "Article", "BlogPosting", "NewsArticle", or "TechArticle" in JSON-LD blocks on these routes. Detect content pages by checking for app/blog/, app/posts/, app/articles/, pages/blog/, etc.
Pass criteria: Any detected blog/article/content route has JSON-LD with an Article-family type. At least 80% of content pages should have Article schema with at least 3 required properties.
Fail criteria: Blog or article routes exist but have no Article-family JSON-LD.
Skip (N/A) when: No blog, article, news, or long-form content routes detected in the project structure.
Cross-reference: For content depth on these pages, see content-depth.
Detail on fail: "Blog/article routes detected (e.g., app/blog/[slug]/page.tsx) but no Article or BlogPosting JSON-LD found on content pages."
Remediation: Article schema makes your content eligible for rich results in Google News, Top Stories carousels, and enhanced article display. Add it to your blog post template with the required fields: headline, author, datePublished, and image. These fields must match the visible page content — see the markup-content-match check for guidance on keeping schema and visible content in sync.
// app/blog/[slug]/page.tsx — BlogPosting schema
const articleSchema = { "@context": "https://schema.org", "@type": "BlogPosting", "headline": "...", "datePublished": "...", "author": { "@type": "Person", "name": "..." } }