ssg-docgen
v1.0.9
Published
Static site doc generation utility library
Downloads
22
Maintainers
Readme
SSG Docgen
A simple utility that parses a folder of files into a json readable format. Useful for static site generation where you want to decouple documentation from your implementation.
Usage
import SSGDocgen from 'ssg-docgen';
const parser = new SSGDocgen('/docsFolder', plugins);
// Parse specific file formats, for example markdown
parser.parseFile(['.md', '.MARKDOWN'], (data, fileInfo) => {
// fileInfo.ext === .md
return md.render(data);
});
// Generate all docs
parser.generate();
// Get a specific page
parser.getPage('my-page');
// Get only navigation
parser.getNavigation();
Concepts
A folder is considered a page by default, mimicking frameworks that support folder-based routing.
For files, only .json
files are rendered automatically, use parser.parseFile
to parse any custom formats, for example markdown
. Each example below is using remarkable
to parse .md
files.
What if I want to document individual components on my site?
A folder with the prefix $c-
is considered a component, a few things happen when parsing components;
- The component is bound to the page its present in and can not contain pages.
- Any file inside the component folder will be bound to the component.
- A component automatically generates anchor links to the page structure so that you can anchor it on the page.
Let's say I want to have a page containing a hero component. This is the folder structure;
page1
$c-hero
props.json
description.md
will output;
{
"navigation": [
{
"id": "page1",
"label": "Page1",
"links": null,
"url": "/page1"
}
],
"pages": {
"/page1": {
"id": "page1",
"title": "Page1",
"components": [
{
"title": "Hero",
"id": "page1/hero",
"items": null,
"description": "<p>content from description.md</p>",
"props": {
"any": "data from props.json"
}
}
],
"anchors": [
{
"title": "Hero",
"id": "page1/hero",
"href": "#page1/hero"
}
]
}
}
}
Nested components
Let's say you have a component that contains multiple child components. You can nest them like this:
page1
$c-examples/
example1/
description.md
props.json
example2/
description.md
props.json
will output;
{
"navigation": [
{
"id": "page1",
"label": "Page1",
"links": null,
"url": "/page1"
}
],
"pages": {
"/page1": {
"id": "page1",
"title": "Page1",
"components": [
{
"title": "Examples",
"id": "page1/examples",
"items": [
{
"title": "Example1",
"id": "page1/examples/example1",
"description": "<p>content from description.md</p>\n",
"props": {
"any": "data from props.json"
}
},
{
"title": "Example2",
"id": "page1/examples/example2",
"description": "<p>content from description.md</p>\n",
"props": {
"any": "data from props.json"
}
}
]
}
],
"anchors": [
{
"title": "Examples",
"id": "page1/examples",
"items": [
{
"title": "Example1",
"id": "page1/examples/example1",
"href": "#page1/examples/example1"
},
{
"title": "Example2",
"id": "page1/examples/example2",
"href": "#page1/examples/example2"
}
]
}
]
}
}
}
What about custom plugins?
There are times when you want to customize the output of a folder. Here we have the concept of plugins that you pass into the parse function.
A plugin is simple. It can be triggered by naming a folder with this syntax: ${myPlugin}
. Then you will pass your plugin object into the parser instance as a second parameter.
const myPlugins = {
'myPlugin': (props) => {
// do something
return { title: 'My plugin', data: any }
}
}
new SSGDocgen(`/docsFolder`, myPlugins);
The function myPlugin
will be called whenever an instance of ${myPlugin}
is found when parsing. A plugin is expected to return an object with:
title
: Used to name the output of the folder ${myPlugin}
data
: Can be anything, markdown, json data, for example.
Plugin props
props
will be given to you with some useful context of where this function was called and extra info:
props.file
: current fileprops.path
: current pathprops.page
: current pageprops.dir
: current directory
Using typescript
When using typescript you can import these types to your application.
import type {
PageContent,
Component,
AnchorLinks,
NavItem,
GetNavigationOutput,
GenerateOutput,
GetPageOutput,
PluginProps,
LibPlugin,
LibPluginResponse,
FileResponse,
FileInfo
} from 'ssg-docgen/types'
Example usage;
import SSGDocgen from 'ssg-docgen';
import type {
GenerateOutput,
PageContent,
NavItem,
AnchorLinks,
LibPlugins,
PluginProps
} from 'ssg-docgen/types';
// Plugins
const myPlugins: LibPlugins = {
'myPlugin': (props: PluginProps) => {
// do something
return {
title: 'My plugin',
data: "hello world"
}
}
}
const parser = new SSGDocgen('/docsFolder', myPlugins);
const res:GenerateOutput = parser.generate();
const pages:PageContent = res.pages;
const navigation:NavItem[] = res.navigation;
const anchors:AnchorLinks[] = pages.anchors;