Use case
Use Sanity SEO fields in Next.js metadata
Query seoFields from Sanity, return buildSeoMeta() from generateMetadata(), render Schema.org JSON-LD components in Server Components, and keep frontend metadata tied to editor-owned content.
Benefits
Works with App Router
Return a Next.js Metadata-compatible object from generateMetadata() using buildSeoMeta().
Keeps editors in control
Sanity owns title, description, canonical URL, social cards, robots, and structured data fields.
Not locked to one frontend
Next.js uses the /next helper, while Astro, Nuxt, Vue, SvelteKit, Remix, and custom renderers can use /head.
How it works in Sanity
Query the document
Fetch slug, content, and the nested seo object with GROQ in your route.
Return metadata
Pass the seo object to buildSeoMeta() with baseUrl, path, defaults, and an image resolver.
Render JSON-LD
Use Schema.org components or builders alongside your page content when structured data is present.
Code examples
import type { Metadata } from 'next'
import { buildSeoMeta } from 'sanity-plugin-seofields/next'
export async function generateMetadata({
params,
}: {
params: Promise<{ slug: string }>
}): Promise<Metadata> {
const { slug } = await params
const post = await getPost(slug)
return buildSeoMeta({
seo: post?.seo,
baseUrl: 'https://example.com',
path: `/blog/${slug}`,
defaults: {
title: post?.title,
siteName: 'Example',
twitterSite: '@example',
},
imageUrlResolver: (image) => image.asset?.url,
})
}*[_type == "post" && slug.current == $slug][0]{
title,
"slug": slug.current,
seo {
title,
description,
canonicalUrl,
keywords,
robots { noIndex, noFollow },
openGraph { title, description, type, imageType, image { asset-> { url } }, imageUrl },
twitter { card, title, description, imageType, image { asset-> { url } }, imageUrl },
hreflangs[] { language, region, url }
},
schemaOrgArticle
}import { buildSeoHead } from 'sanity-plugin-seofields/head'
const head = buildSeoHead({
seo: page.seo,
baseUrl: 'https://example.com',
path: page.path,
})
// Use this shape in Astro, Nuxt, Vue, SvelteKit, Remix,
// or any renderer that wants serializable head data.Related docs
FAQ
Does buildSeoMeta work in Server Components?
Yes. The /next entry point is designed for Next.js App Router and can be used from generateMetadata() and Server Component code.
Can I still use the plugin outside Next.js?
Yes. Use sanity-plugin-seofields/head when you need plain head data for Astro, Nuxt, Vue, SvelteKit, Remix, or a custom renderer.
How do image URLs get resolved?
Pass an imageUrlResolver to buildSeoMeta() so Sanity image references can become absolute image URLs.
Can I render Schema.org JSON-LD in Next.js?
Yes. The /next export includes Schema.org React components and JSON-LD builder helpers for individual schema types.
Wire Sanity SEO into Next.js
Use the frontend integration docs for complete App Router, Pages Router, and framework-neutral examples.