Après avoir Initialiser un projet Gatsby et importer vos fichiers markdown, vous pouvez créer automatiquement la table des matière d'un fichier markdown dans Gatsby.
// gatsby-node.jsexports.createPages = async ({ actions, graphql, reporter }) => {const { createPage } = actions;const result = await graphql(`{allMarkdownRemark {edges {node {idhtmlheadings {valuedepth}parent {... on File {name}}}}}}`);if (result.errors) {reporter.panicOnBuild('Error while running GraphQL query.');return;}const markdowns = result.data.allMarkdownRemark.edges;const noteTemplate = require.resolve('./src/templates/noteTemplate.js');markdowns.forEach(({ node }) => {const { id, html, headings } = node;createPage({path: `/${node.parent.name}`,component: noteTemplate,context: { id, html, headings },});});};
// src/components/toc.jsimport React from 'react';import { Link } from 'gatsby';import slugify from 'slugify';export default ({ headings = [], depthMin = 1, className = '' }) => {if (!headings.length) return false;return (<ul className={className}>{headings.filter(({ depth }) => depth >= depthMin).map(({ value }) => {const id = slugify(value, { lower: true, strict: true });return (<li key={value}><Link to={`#${id}`} title={value}>{value}</Link></li>);})}</ul>);};
// src/templates/noteTemplate.jsimport React from 'react';import Toc from '../components/toc';export default function Template({ pageContext }) {const { html, headings } = pageContext;return (<><Toc headings={headings} depthMin={2} /><div dangerouslySetInnerHTML={{ __html: html }} /></>);}
Pour créer automatiquement les id sur chaque header, il existe le plugin gatsby-remark-autolink-headers :
yarn add -D gatsby-remark-autolink-headers
// gatsby-config.jsmodule.exports = {plugins: [{resolve: 'gatsby-source-filesystem',options: {path: './content',},},{resolve: 'gatsby-transformer-remark',options: {plugins: [{resolve: 'gatsby-remark-autolink-headers',options: {icon: false,},},],},},],};