Metadata helps search engines understand what a page is about and index it accordingly. For optimal SEO performance and for web pages to be ranked and found on search engines, it is crucial that the pages have proper metadata.
Now, some metadata are global and need to be on every page, while some are local or specific to a page. Let's see how we add both in a Next.js app built with the Pages and the App Router.
Add metadata in the Pages Router
Global metadata
In the Pages Router, we add global metadata in a special file called _document.tsx
.
import { Html, Head, Main, NextScript } from 'next/document';
export default function Document() {
return (
<Html lang='en'>
<Head>
<meta charSet='UTF-8' />
<meta
name='robots'
content='index, follow, max-image-preview:large, max-snippet:-1, max-video-preview:-1'
/>
<meta property='og:locale' content='en_US' />
<meta name='author' content='Alamin Shaikh' />
<meta property='og:image:width' content='920' />
<meta property='og:image:height' content='470' />
<meta name='twitter:card' content='summary_large_image' />
<meta
property='og:site_name'
content='Developing Superior Software for Leading Businesses'
/>
<meta
name='keywords'
content='JavaScript developer, TypeScript developer, Web developer'
/>
</Head>
<body>
<Main />
<NextScript />
</body>
</Html>
);
}
Copy the meta
elements from the above Head
component and paste them within the Head
component in the _document.tsx
file of your project. Update the author
, og:site_name
, and keywords
to match your project's details.
Local metadata
In the Pages Router, we use a CustomHead
component to add local metadata specific to a page.
import Head from 'next/head';
type Props = {
title: string;
content: string;
pageSlug: string;
pageType?: string;
ogImage?: string;
};
export default function CustomHead({
title,
content,
pageSlug,
pageType = 'website',
ogImage = `${process.env.NEXT_PUBLIC_BASE_URL}/layout/og-image.png`,
}: Props) {
const ogTitle = title.replace(' - Alamin Shaikh', '');
const pageURL = `${process.env.NEXT_PUBLIC_BASE_URL}${pageSlug}`;
return (
<Head>
<title>{title}</title>
<meta name='description' content={content} />
<link rel='canonical' href={pageURL} />
<meta property='og:type' content={pageType} />
<meta property='og:title' content={ogTitle} />
<meta property='og:description' content={content} />
<meta property='og:url' content={pageURL} />
<meta property='og:image' content={ogImage} />
</Head>
);
}
As you can see, the above CustomHead
component receives five props. Three of the props: title
, content
, and pageSlug
are required and are unique to each page. The rest of the props: pageType
and ogImage
are optional.
Notice that we have default values for the pageType
and ogImage
props, so if they are not provided, the default ones will be used. Within the component, we create two variables: ogTitle
and pageURL
from the title
and pageSlug
props respectively.
From the component, we return the Head
component provided by Next.js with a title
, link
, and a few meta
elements. Following is a brief description of the elements:
title
: should be the page titledescription
: should be a description of the pagecanonical
: prioritizes the page to search engines over any duplicatesog:type
: should be the type of the web page e.g. website or articleog:title
: should be the title of the page without the brandingog:description
: should be the same as the general descriptionog:url
: should be the same as the page URLog:image
: should be the link to an image that visually describes the page
To use this component in your Next.js application, create an environment variable named NEXT_PUBLIC_BASE_URL
and change ' - Alamin Shaikh' to match your site's branding.
Now, let's see an example of using the CustomHead
component on a page.
import Hero from '@components/home/Hero';
import CustomHead from '@components/layout/CustomHead';
export default function HomePage() {
return (
<>
<CustomHead
pageSlug='/'
title='Full Stack JavaScript Developer - Alamin Shaikh'
content='I am a full stack JavaScript developer specializing in web application development. I write technical articles about JavaScript and freelancing.'
/>
<Hero />
</>
);
}
In the above code, we've used the CustomHead
component on the homepage to add metadata about the page.
Add metadata in the App Router
Global metadata
In the App Router, we add global metadata by exporting a metadata
object from the root layout.tsx
file.
export const metadata: Metadata = {
robots: {
index: true,
follow: true,
'max-snippet': -1,
'max-video-preview': -1,
'max-image-preview': 'large',
},
authors: [{ name: 'Alamin Shaikh' }],
keywords:
'JavaScript developer, TypeScript developer, Web application developer, React.js web developer, Next.js developer, Progressive web app developer, Node.js developer, Express.js backend developer, JavaScript backend developer, RESTful API developer, TypeScript backend implementation, Full stack JavaScript developer, Full stack TypeScript developer, MERN stack developer, React native developer, Mobile application developer, Native application developer, MongoDB database expert',
twitter: {
card: 'summary_large_image',
},
metadataBase: new URL('https://www.alaminshaikh.com'),
};
Copy the above metadata
object and paste it into the root layout.tsx
file of your project. Update the authors
, keywords
, and metadataBase
to match your project's details.
Local metadata
In the App Router, we add local metadata by exporting a metadata
object from the page.tsx
file.
export const metadata: Metadata = {
title: 'Full Stack JavaScript Developer | Alamin Shaikh',
description:
'I am a full stack JavaScript developer specializing in web application development. I write technical articles about JavaScript and freelancing.',
openGraph: {
url: '/',
type: 'website',
locale: 'en_US',
images: '/layout/og-image.png',
title: 'Full Stack JavaScript Developer',
siteName: 'Developing Superior Software for Leading Businesses',
},
alternates: {
canonical: '/',
},
};
As you can see in the above code, we export a metadata
object from the homepage with the necessary metadata specific to the page.
Once you've added the metadata, inspect the page elements, and you should find all the local and global metadata you've added to the page. If you find the elements, your setup is working as intended.
That's it! If you are interested in learning to add favicon in a Next.js application, I have an article on Add favicon in a Next.js application built with the Pages and the App Router that provides further insights. Happy learning!