_meta.js File
In Nextra, the site and individual page structure can be configured via the
co-located _meta files. Those configurations affect the overall layout of your
Nextra theme, especially the navigation bar and the sidebar:

Organizing files
Nextra allows you to organize files in the following ways:
-
In Next.js’
appdirectory:
Nextra gathers allpagefiles, includingpage.mdandpage.mdxfiles as well as_metafiles. -
In Nextra’s
contentdirectory:
Nextra collects all.mdand.mdxfiles, along with_metafiles.
Below the same file-based routing structure is represented for content and
app-only directories:
- Using
- layout.jsx
- _meta.js
- index.mdx
- legal.md
- _meta.js
- contact.md
- index.mdx
content directory- Using
- _meta.js
- page.mdx
- _meta.js
- layout.jsx
- page.mdx
page.mdx filesYou can combine both organizational ways for your project:
- the
contentdirectory with.mdxfiles - the
appdirectory withpagefiles
pageMap structure
Afterward, Nextra generates a pageMap array containing information about your
entire site’s routes and directories structure. Features such as the navigation
bar and sidebar can be generated based on the pageMap information.
The generated pageMap will be:
[
// content/_meta.js
{ "data": {} },
// content/index.mdx
{ "name": "index", "route": "/", "frontMatter": {} },
// content/contact.md
{ "name": "contact", "route": "/contact", "frontMatter": {} },
{
// content/about
"name": "about",
"route": "/about",
"children": [
// content/about/_meta.js
{ "data": {} },
// content/about/index.mdx
{ "name": "index", "route": "/about", "frontMatter": {} },
// content/about/legal.md
{ "name": "legal", "route": "/about/legal", "frontMatter": {} }
],
"title": "About"
}
]And the global pageMap will be imported to each page by Nextra. Then,
configured theme will render the actual UI with that pageMap.
API
The title and order of a page shown in the sidebar/navbar can be configured in
the _meta file as key-value pairs.
import type { MetaRecord } from 'nextra'
/**
* type MetaRecordValue =
* | TitleSchema
* | PageItemSchema
* | SeparatorSchema
* | MenuSchema
*
* type MetaRecord = Record<string, MetaRecordValue>
**/
const meta: MetaRecord = {
// ...
}
export default metatitle type
When specifying a title in _meta file, you can define it as either a simple
string or a JSX element.
type TitleSchema = string | ReactElementFor the below file structure:
- Using
- layout.jsx
- _meta.js
- about.mdx
- contact.mdx
- index.mdx
content directory- Using
- _meta.js
- layout.jsx
- page.mdx
page.mdx filesThe following _meta file defines pages titles:
import { GitHubIcon } from 'nextra/icons'
export default {
index: 'My Homepage',
// You can use JSX elements to change the look of titles in the sidebar, e.g. insert icons
contact: (
<Italic className="my-class">
<GitHubIcon height="20" />
Contact Us
</Italic>
),
about: {
// Alternatively, you can set title with `title` property
title: 'About Us'
// ... and provide extra configurations
}
}
// Custom component for italicized text
function Italic({ children, ...props }) {
return <i {...props}>{children}</i>
}Pages
In _meta file you can define how the pages are shown in the sidebar, e.g. for
the following file structure:
- Using
- layout.jsx
- _meta.js
- about.mdx
- contact.mdx
- index.mdx
content directory- Using
- _meta.js
- layout.jsx
- page.mdx
page.mdx filesexport default {
index: 'My Homepage',
contact: 'Contact Us',
about: 'About Us'
}If any routes are not listed in the _meta file, they will be appended to the
end of the sidebar and sorted alphabetically (except for index key which
comes first if it’s not specified in _meta file).
type PageItemSchema = {
type: 'page' | 'doc' // @default 'doc'
display: 'normal' | 'hidden' | 'children' // @default 'normal'
title?: TitleSchema
theme?: PageThemeSchema
}type: 'page' option
By defining a top-level page or folder as type: 'page', it will be shown
as a special page on the navigation bar, instead of the sidebar. With this
feature, you can have multiple “sub docs”, and special pages or links such as
“Contact Us” that are always visible.
For example, you can have 2 docs folders frameworks and fruits in your
project. In your top-level _meta file, you can set everything as a page,
instead of a normal sidebar item:
- Using
- layout.jsx
- react.mdx
- svelte.mdx
- vue.mdx
- apple.mdx
- banana.mdx
- _meta.js
- about.mdx
- index.mdx
content directory- Using
- _meta.js
- layout.jsx
- page.mdx
page.mdx filesexport default {
index: {
title: 'Home',
type: 'page'
},
frameworks: {
title: 'Frameworks',
type: 'page'
},
fruits: {
title: 'Fruits',
type: 'page'
},
about: {
title: 'About',
type: 'page'
}
}And it will look like this:
You can also hide links like Home from the navbar with the
display: 'hidden' option.
You can have external links in the navbar, similar to the links section:
export default {
contact: {
title: 'Contact Us',
type: 'page',
href: 'https://example.com/contact'
}
}display: 'hidden' option
By default, all MDX routes in the filesystem will be shown on the sidebar. But
you can hide a specific pages or folders by using the display: 'hidden'
configuration:
export default {
contact: {
display: 'hidden'
}
}The page will still be accessible via the /contact URL, but it will not be
shown in the sidebar.
theme option
You can configure the theme for each page using the theme option. For example,
you can disable or enable specific components for specific pages:
export default {
about: {
theme: {
sidebar: false
}
}
}This option will be inherited by all child pages if set to a folder.
| Option | Type | Default Value | Description |
|---|---|---|---|
breadcrumb | boolean | true | Show or hide breadcrumb navigation. |
collapsed | boolean | false | Indicates whether the item in sidebar is collapsed by default. |
footer | boolean | true | Specifies whether to display the footer. |
layout | 'default' | 'full' | 'default' | Defines the layout style. |
navbar | boolean | true | Specifies whether to display the navbar. |
pagination | boolean | true | Determines if pagination controls are shown. |
sidebar | boolean | true | Specifies whether to display the sidebar. |
timestamp | boolean | true | Indicates if “last updated” timestamps are displayed. |
toc | boolean | true | Determines whether a table of contents is displayed. |
typesetting | 'default' | 'article' | 'default' | Configures the text typesetting style. |
Layouts
By default, each page has layout: 'default' in their theme config, which
is the default behavior. You might want to render some page with the full
container width and height, but keep all the other styles. You can use the
'full' layout to do that:
export default {
about: {
theme: {
layout: 'full'
}
}
}Typesetting
The typesetting option controls typesetting details like font features,
heading styles and components like <li> and <code>. There are
'default' and 'article' typesettings available in the docs theme.
The default one is suitable for most cases like documentation, but you can use
the 'article' typesetting to make it look like an elegant article page:
export default {
about: {
theme: {
typesetting: 'article'
}
}
}Folders
Folders can be configured in the same way as pages.
For example, the following top-level _meta file contains the meta information
for the top-level pages and folders.
The nested _meta file contains the
meta information for pages in the same folder:
- Using
- layout.jsx
- _meta.js
- apple.mdx
- banana.mdx
- _meta.js
- about.mdx
- contact.mdx
- index.mdx
content directory- Using
- _meta.js
- _meta.js
- layout.jsx
- page.mdx
page.mdx filesexport default {
index: 'My Homepage',
contact: 'Contact Us',
fruits: 'Delicious Fruits',
about: 'About Us'
}export default {
apple: 'Apple',
banana: 'Banana'
}You can move directories around without having to change the _meta file
since information for pages are grouped together in directories.
With /index page
To create a folder with an index page, add asIndexPage: true to its front
matter.
For example, to create a /fruits route, setting asIndexPage: true tells
Nextra that /fruits is a folder with an index page. Clicking the folder in the
sidebar will expand it and display the MDX page.
- Using
- layout.jsx
- _meta.js
- apple.mdx
- banana.mdx
- index.mdx
- _meta.js
- about.mdx
- contact.mdx
- index.mdx
content directory- Using
- _meta.js
- page.mdx
- _meta.js
- layout.jsx
- page.mdx
page.mdx files---
title: All Fruits
sidebarTitle: 🍒 Fruits
asIndexPage: true
---Links
type LinkSchema = {
href: string
title?: TitleSchema
}You can add external links to the sidebar by adding an item with href in
_meta file:
export default {
github_link: {
title: 'Nextra',
href: 'https://github.com/shuding/nextra'
}
}You can use this option to link to relative internal links too.
Separators
type SeparatorSchema = {
type: 'separator'
title?: TitleSchema
}You can use a “placeholder” item with type: 'separator' to create a
separator line between items in the sidebar:
export default {
'###': {
type: 'separator',
title: 'My Items' // Title is optional
}
}Menus
You can also add menus to the navbar using type: 'menu' and the items
option:

type MenuItemSchema =
| TitleSchema
| { title: TitleSchema }
| (LinkSchema & { type?: 'page' | 'doc' })
| SeparatorSchema
type MenuSchema = {
type: 'menu'
title?: TitleSchema
items: Record<string, MenuItemSchema>
}export default {
company: {
title: 'Company',
type: 'menu',
items: {
about: {
title: 'About',
href: '/about'
},
contact: {
title: 'Contact Us',
href: 'mailto:hi@example.com'
}
}
}
}Fallbacks
In the type: 'page' option above, we have to define
the type: 'page' option for every page. To make it easier, you can use
the '*' key to define the fallback configuration for all items in this folder:
export default {
'*': {
type: 'page'
},
index: 'Home',
frameworks: 'Frameworks',
fruits: 'Fruits',
about: 'About'
}They are equivalent where all items have type: 'page' set.
_meta.global file
You can also define all your pages in a single _meta file, suffixed with
.global. The API remains the same as for folder-specific _meta files, with 1
exception: folder items must include an items field.
For the following structure, you might use the following _meta files:
- Using
- layout.jsx
- _meta.js
- apple.mdx
- banana.mdx
- _meta.js
- index.mdx
content directory- Using
- _meta.js
- _meta.js
- layout.jsx
- page.mdx
page.mdx filesexport default {
fruits: {
type: 'page',
title: '✨ Fruits'
}
}export default {
apple: '🍎 Apple',
banana: '🍌 BaNaNa'
}With single _meta.global file it can be defined as below:
export default {
fruits: {
type: 'page',
title: '✨ Fruits',
items: {
apple: '🍎 Apple',
banana: '🍌 BaNaNa'
}
}
}You can’t use both _meta.global and _meta files in your project.
Good to know
Sorting pages
You can use ESLint’s built-in sort-keys rule, append
/* eslint sort-keys: error */ comment at the top of your _meta file, and you
will receive ESLint’s errors about incorrect order.
Type of _meta keys
The type of your _meta keys should always be a string and not a number
because
numbers are always ordered first
in JavaScript objects.
For example, consider the following:
export default {
foo: '',
1992_10_21: '',
1: ''
}will be converted to:
export default {
'1': '',
'19921021': '',
foo: ''
}The .js, .jsx, or .tsx file extensions can be used for _meta file.