Autogenerated
Docusaurus can create a sidebar automatically from your filesystem structure: each folder creates a sidebar category, and each file creates a doc link.
type SidebarItemAutogenerated = {
type: 'autogenerated';
dirName: string; // Source folder to generate the sidebar slice from (relative to docs)
};
Docusaurus can generate a full sidebar from your docs folder:
export default {
myAutogeneratedSidebar: [
{
type: 'autogenerated',
dirName: '.', // '.' means the current docs folder
},
],
};
An autogenerated
item is converted by Docusaurus to a sidebar slice (also discussed in category shorthands): a list of items of type doc
or category
, so you can splice multiple autogenerated
items from multiple directories, interleaving them with regular sidebar items, in one sidebar level.
A real-world example
Consider this file structure:
docs
├── api
│ ├── product1-api
│ │ └── api.md
│ └── product2-api
│ ├── basic-api.md
│ └── pro-api.md
├── intro.md
└── tutorials
├── advanced
│ ├── advanced1.md
│ ├── advanced2.md
│ └── read-more
│ ├── resource1.md
│ └── resource2.md
├── easy
│ ├── easy1.md
│ └── easy2.md
├── tutorial-end.md
├── tutorial-intro.md
└── tutorial-medium.md
And assume every doc's ID is just its file name. If you define an autogenerated sidebar like this:
export default {
mySidebar: [
'intro',
{
type: 'category',
label: 'Tutorials',
items: [
'tutorial-intro',
{
type: 'autogenerated',
dirName: 'tutorials/easy', // Generate sidebar slice from docs/tutorials/easy
},
'tutorial-medium',
{
type: 'autogenerated',
dirName: 'tutorials/advanced', // Generate sidebar slice from docs/tutorials/advanced
},
'tutorial-end',
],
},
{
type: 'autogenerated',
dirName: 'api', // Generate sidebar slice from docs/api
},
{
type: 'category',
label: 'Community',
items: ['team', 'chat'],
},
],
};
It would be resolved as:
export default {
mySidebar: [
'intro',
{
type: 'category',
label: 'Tutorials',
items: [
'tutorial-intro',
// Two files in docs/tutorials/easy
'easy1',
'easy2',
'tutorial-medium',
// Two files and a folder in docs/tutorials/advanced
'advanced1',
'advanced2',
{
type: 'category',
label: 'read-more',
items: ['resource1', 'resource2'],
},
'tutorial-end',
],
},
// Two folders in docs/api
{
type: 'category',
label: 'product1-api',
items: ['api'],
},
{
type: 'category',
label: 'product2-api',
items: ['basic-api', 'pro-api'],
},
{
type: 'category',
label: 'Community',
items: ['team', 'chat'],
},
],
};
Note how the autogenerate source directories themselves don't become categories: only the items they contain do. This is what we mean by "sidebar slice".
Category index convention
Docusaurus can automatically link a category to its index document.
A category index document is a document following one of those filename conventions:
- Named as
index
(case-insensitive):docs/Guides/index.md
- Named as
README
(case-insensitive):docs/Guides/README.mdx
- Same name as parent folder:
docs/Guides/Guides.md
This is equivalent to using a category with a doc link:
export default {
docs: [
{
type: 'category',
label: 'Guides',
link: {type: 'doc', id: 'Guides/index'},
items: [],
},
],
};
Naming your introductory document README.md
makes it show up when browsing the folder using the GitHub interface, while using index.md
makes the behavior more in line with how HTML files are served.
If a folder only has one index page, it will be turned into a link instead of a category. This is useful for asset collocation:
some-doc
├── index.md
├── img1.png
└── img2.png
Customizing category index matching
It is possible to opt out any of the category index conventions, or define even more conventions. You can inject your own isCategoryIndex
matcher through the sidebarItemsGenerator
callback. For example, you can also pick intro
as another file name eligible for automatically becoming the category index.
export default {
plugins: [
[
'@docusaurus/plugin-content-docs',
{
async sidebarItemsGenerator({
...args,
isCategoryIndex: defaultCategoryIndexMatcher, // The default matcher implementation, given below
defaultSidebarItemsGenerator,
}) {
return defaultSidebarItemsGenerator({
...args,
isCategoryIndex(doc) {
return (
// Also pick intro.md in addition to the default ones
doc.fileName.toLowerCase() === 'intro' ||
defaultCategoryIndexMatcher(doc)
);
},
});
},
},
],
],
};