graphql-engine/docs/wiki/rst-vs-mdx-guide/table-of-contents.mdx
Rikin Kachhia cc30f08f6e docs: move docs-new to docs
PR-URL: https://github.com/hasura/graphql-engine-mono/pull/4261
GitOrigin-RevId: 3d80068acdd61b5350fc36ec3444db47508f9c09
2022-04-13 12:01:50 +00:00

336 lines
10 KiB
Plaintext

---
sidebar_position: 5
---
import TOCInline from '@theme/TOCInline';
import Tabs from '@theme/Tabs';
import TabItem from '@theme/TabItem';
import Link from '@docusaurus/Link';
import { CustomTOCList, CustomTOCListSection, CustomTOCListHead, CustomTOCListContent } from "@site/src/components/CustomTOCList";
# Table of Contents
Two ways to list table of contents.
1. List the contents within the same document.
2. List contents for different documents. Say, an index page.
<br />
Below is auto listed TOC for this document
<TOCInline toc={toc} />
## Full Table of Contents
This is the simplest way and is autogenerated on usage of `TOCInline` component from docusaurus.
<Tabs>
<TabItem value="sphinx" label="Sphinx - RST" default>
```rest
.. contents:: Table of contents
:backlinks: none
:depth: 2
:local:
```
Please refer [reStructured text `content` Directives](https://docutils.sourceforge.io/docs/ref/rst/directives.html#table-of-contents) for more insights into syntax and usage of `contents` directive.
</TabItem>
<TabItem value="docusaurus" label="Docusaurus - MDX">
```jsx
import TOCInline from '@theme/TOCInline';
<TOCInline toc={toc} />
```
Please refer docusaurus [Inlince TOC docs](https://docusaurus.io/docs/markdown-features/inline-toc) for more insights into syntax and usage of `TOCInline`.
Please use this `CustomTOCListHead` component to add custom heading like stuff for TOC.
```jsx {1,3}
import { CustomTOCListHead } from "@site/src/components/CustomTOCList";
<CustomTOCListHead>Table of Contents</CustomTOCListHead>
<TOCInline toc={toc} />
```
Will see more about this component in below sections.
</TabItem>
</Tabs>
:::info
- The `:depth:` param can be controlled by [`toc_min_heading_level` and `toc_max_heading_level`](https://docusaurus.io/docs/api/plugins/@docusaurus/plugin-content-docs#toc_min_heading_level) meta for individual files and [`minHeadingLevel` and `maxHeadingLevel`](https://docusaurus.io/docs/api/themes/configuration#table-of-contents) for global theme config in docusaurus as given in docs.
- The `:backlinks:` seems to be set to `none` for all and also there is no direct replacement in MDX via Docusaurus. So, can be ignored.
- The `:local` can be ignored as well cause the `TOCInline` component works only for local (same) document
:::
:::caution Important Note
Please ignore top level TOC (the one at beginning of file). Only add for sub section TOCs. This is to avoid redundancy as TOC is available on right sidebar.
:::
## Partial (Sub) Table of Contents
If one individual section requires to have its own TOC. Below is how it can be achieved in docusaurus.
So, a bit of good and bad news :(.
Unlike Sphinx, changing `depth` (`minHeadingLevel` or `maxHeadingLevel`) value for auto generated TOC will not auto generate a sub table of content for that particular section.
```rest {3}
.. contents:: Table of contents
:backlinks: none
:depth: 1
:local:
```
### Subitem
Good news is its doable though. Need to do this manually using `filterTOC` prop for the `TOCInline` component.
To only list the sub section list from below Table of Contents,
<TOCInline toc={toc} />
Literally, count the number of items as `0-based index` and use that index to render only that sub-toc.
In this case, `1` is index for this section.
```jsx {4}
// Render only the "Partial (Sub) Table of Contents" and its subitems if any.
<TOCInline
toc={toc}
filterTOC={tocTree => ([ tocTree[1] ])}
/> // Note that the prop value is inside an array "[ toc[2], ... ]".
```
<TOCInline toc={toc} filterTOC={tocTree => ([ tocTree[1] ])} />
If it has children they will be rendered too.
### Sub-Subitem
The children alone of a subitem can be rendered too. Read more about the TOCItem
```jsx {4}
// Render only the subitems(children) of "Partial (Sub) Table of Contents".
<TOCInline
toc={toc}
filterTOC={tocTree => toc[1].children}
/> // Note that the prop value is now not an explicit array as children is a list.
```
<TOCInline toc={toc} filterTOC={tocTree => tocTree[1].children} />
:::caution
The `filterTOC` prop return value should always be an array.
```jsx
filterTOC={tocTree => ([ toc[2], ... ])} or filterTOC={tocTree => toc[1].children}
```
:::
:::danger `filterTOC` prop is not avaiable by default - it is custom implemented
The `TOCInline` and `TOCItems` components are [swizzled](https://docusaurus.io/docs/swizzling) and custom logic is added.
The custom added logic (`src/theme/TOCInline`, `src/theme/TOCItems`) is indicated by comments - `// Customization START` and `// Customization END`. If reswizzled in future only these blocks need an update.
[`toc` is a flat array](https://docusaurus.io/docs/markdown-features/inline-toc#custom-table-of-contents) and has no concept of nested tree children structure. This behavior is changed in `2.0.0-beta.16`.
Please check the [Breaking changes that forced us to swizzle](https://docusaurus.io/changelog/2.0.0-beta.16#-breaking-change)
:::
## Custom Table of Contents
Custom/Manually generated TOC can be a simple list or a group of lists (like an root index page)
### Simple List
<Tabs>
<TabItem value="sphinx" label="Sphinx - RST" default>
```rest
.. toctree::
:maxdepth: 1
:titlesonly:
allow-lists
api-limits
disable-graphql-introspection
rotating-admin-secrets
```
Please refer [reStructured text `toctree` Directive](https://www.sphinx-doc.org/en/master/usage/restructuredtext/directives.html#table-of-contents) for more insights into syntax and usage of `toctree` directive.
</TabItem>
<TabItem value="docusaurus" label="Docusaurus - MDX">
Unfortunately, there is no direct alternative for this in either MDX or Docusaurus.
So, have to rely on simple MDX links and manually find file paths, similar to how we handle refs in [Links](/rst-vs-mdx-guide/links.mdx#internal-links).
```markdown
- [Allow Lists](/graphql/cloud/security/allow-lists.mdx)
- [API Limits](/graphql/cloud/security/api-limits.mdx)
- [Disable GraphQL Introspection](/graphql/cloud/security/disable-graphql-introspection.mdx)
- [Rotating Admin Secrets](/graphql/cloud/security/rotating-admin-secrets.mdx)
```
or if this needs to be done nested in a react component that doesn't support MDX.
```jsx
import Link from '@docusaurus/Link';
import {
CustomTOCList, CustomTOCListSection, CustomTOCListHead, CustomTOCListContent,
} from "@site/src/components/CustomTOCList";
<CustomTOCList>
<CustomTOCListSection>
<CustomTOCListContent>
<Link to="/docs/graphql/cloud/security/allow-lists">Allow Lists</Link>
<Link to="/docs/graphql/cloud/security/api-limits">API Limits</Link>
<Link to="/docs/graphql/cloud/security/disable-graphql-introspection">Disable GraphQL Introspection</Link>
<Link to="/docs/graphql/cloud/security/rotating-admin-secrets">Rotating Admin Secrets</Link>
</CustomTOCListContent>
</CustomTOCListSection>
</CustomTOCList>
```
:::caution Watchout the link type
If you notice, we have added extension to the paths in link where as in `<Link />` component we didn't.
Thats beacuse, the MDX links are treated as file-paths and is resolved to generated url paths automatically by docusaurus.
On the other hand, the path in `Link` component should already be a url path as it cannot resolve file-paths.
Best practice is to keep the directory/file path structure and url structure same to avoid the maintenance burden when using both types of syntax.
:::
</TabItem>
</Tabs>
#### Result UI
will render something like below.
### Group of Lists
Its a list of simple lists (UI wise).
<Tabs>
<TabItem value="sphinx" label="Sphinx - RST" default>
```rest
.. container:: toc-list
.. container:: toc-list-section
.. container:: toc-list-head
API Security
.. container:: toc-list-content
- :ref:`api_limits`
- :ref:`allow_lists`
.. container:: toc-list-section
.. container:: toc-list-head
Reference
.. container:: toc-list-content
- :ref:`cloud_api_reference`
- :ref:`glossary`
- :ref:`hasurapro_cli`
```
Please refer [reStructured text `toctree` Directive](https://www.sphinx-doc.org/en/master/usage/restructuredtext/directives.html#table-of-contents) for more insights into syntax and usage of `toctree` directive.
</TabItem>
<TabItem value="docusaurus" label="Docusaurus - MDX">
Unfortunately, there is no direct alternative for this in either MDX or Docusaurus. So, have to list these links manually using this `CustomTOCList` component.
```jsx
import Link from '@docusaurus/Link';
import {
CustomTOCList, CustomTOCListSection, CustomTOCListHead, CustomTOCListContent,
} from "@site/src/components/CustomTOCList";
<CustomTOCList>
<CustomTOCListSection>
<CustomTOCListHead>API Security</CustomTOCListHead>
<CustomTOCListContent>
<Link to="/root/relative/path/to/cloud-api-reference">API Limits</Link>
<Link to="/root/relative/path/to/allow-lists">Allow Lists</Link>
</CustomTOCListContent>
</CustomTOCListSection>
<CustomTOCListSection>
<CustomTOCListHead>Reference</CustomTOCListHead>
<CustomTOCListContent>
<Link to="/root/relative/path/to/cloud-api-reference">Cloud API Reference</Link>
<Link to="/root/relative/path/to/glossary">Glossary</Link>
<Link to="/root/relative/path/to/hasurapro-cli">Hasura Pro CLI</Link>
</CustomTOCListContent>
</CustomTOCListSection>
</CustomTOCList>
```
</TabItem>
</Tabs>
#### Result UI
will render something like below. Please note that links will be broken as they are just samples.
<CustomTOCList>
<CustomTOCListSection>
<CustomTOCListHead>API Security</CustomTOCListHead>
<CustomTOCListContent>
<Link to="#cloud-api-reference">API Limits</Link>
<Link to="#allow-lists">Allow Lists</Link>
</CustomTOCListContent>
</CustomTOCListSection>
<CustomTOCListSection>
<CustomTOCListHead>Reference</CustomTOCListHead>
<CustomTOCListContent>
<Link to="#cloud-api-reference">Cloud API Reference</Link>
<Link to="#glossary">Glossary</Link>
<Link to="#hasurapro-cli">Hasura Pro CLI</Link>
</CustomTOCListContent>
</CustomTOCListSection>
</CustomTOCList>
<hr />
:::tip How to use links within React?
- Please refer [Links in React](/rst-vs-mdx-guide/links.mdx#links-in-react) section in Links.
```jsx
import Link from '@docusaurus/Link';
<Link to="/wiki/rst-vs-mdx-guide/links#root-relative-links">Root Relative Links</Link>
```
- Please refer the [Root Relative Links](/wiki/rst-vs-mdx-guide/links#root-relative-links) section too.
:::