tl;博士
Next.js 13 的
/app
路由器的 layout
和 page
路由改变了我们向 <head>
添加内容的方式。如何向每个页面添加架构脚本? Next.js 会自动将放置在任何 <head>
或 layout
中的 page
标签编译为单个 <head>
。
就像在任何具有出色 SEO 的网站一样,我想在每个页面的头部包含一个架构脚本。
通常,这就像在
<head>
中编写一样简单,如下所示:
<!-- index.html -->
<head>
<script type="application/ld+json">
{
"@context": "https://schema.org",
// ... the rest
}
</script>
</head>
然后,对于 Next.js
/pages
目录,情况有点不同。我总是觉得必须使用 dangerouslySetInnerHTML
属性很奇怪,但至少它有效。
// index.tsx
import Head from 'next/head'
export default function Page() {
return (
<Head>
<script id="schema" type="application/ld+json" dangerouslySetInnerHTML={{__html: `
{
"@context": "https://schema.org",
// ... the rest
}
`}} />
</Head>
)
}
现在,随着
/app
路由器的推出,我们有了很棒的、新的、简化的方法来设置元数据,而无需通过 <head>
直接导入 next/head
。事实上,next/head
组件不应该在/app
路由器中使用。
所以问题就变成了……
<head>
?我希望 Next.js 团队已经考虑到了这一点,并将模式添加到新的
metadata
变量中,甚至是它自己的变量中,但他们似乎没有尽我所能做到这一点的计划告诉。
我尝试将
<head>
添加到 page
中,不幸的是,它没有正确合并到 <head>
中。到目前为止,我唯一能做的就是将架构添加到每个layout
,但是为每个页面都有单独的布局将是多么麻烦。
欢迎任何想法。
您可能已经有了答案,但对于我们所有人来说,可能正在寻找同一问题的解决方案:
import Head from 'next/head';
function ProductPage() {
function addProductJsonLd() {
return {
__html: `{
"@context": "https://schema.org/",
"@type": "Product",
"name": "Executive Anvil",
"image": [
"https://example.com/photos/1x1/photo.jpg",
"https://example.com/photos/4x3/photo.jpg",
"https://example.com/photos/16x9/photo.jpg"
],
"description": "Sleeker than ACME's Classic Anvil, the Executive Anvil is perfect for the business traveler looking for something to drop from a height.",
"sku": "0446310786",
"mpn": "925872",
"brand": {
"@type": "Brand",
"name": "ACME"
},
"review": {
"@type": "Review",
"reviewRating": {
"@type": "Rating",
"ratingValue": "4",
"bestRating": "5"
},
"author": {
"@type": "Person",
"name": "Fred Benson"
}
},
"aggregateRating": {
"@type": "AggregateRating",
"ratingValue": "4.4",
"reviewCount": "89"
},
"offers": {
"@type": "Offer",
"url": "https://example.com/anvil",
"priceCurrency": "USD",
"price": "119.99",
"priceValidUntil": "2020-11-20",
"itemCondition": "https://schema.org/UsedCondition",
"availability": "https://schema.org/InStock"
}
}
`,
};
}
return (
<div>
<Head>
<title>My Product</title>
<meta
name="description"
content="Super product with free shipping."
key="desc"
/>
<script
type="application/ld+json"
dangerouslySetInnerHTML={addProductJsonLd()}
key="product-jsonld"
/>
</Head>
<h1>My Product</h1>
<p>Super product for sale.</p>
</div>
);
}
export default ProductPage;
这里是 next.js 文档中包含更多信息的链接! https://nextjs.org/learn/seo/rendering-and-ranking/metadata
这里是如何在 NextJS App Router 中使用 JSON-LD 的示例 https://nextjs.org/docs/app/building-your-application/optimizing/metadata#json-ld