Documentation Plugin
The documentation plugin (@functional-examples/documentation) generates markdown documentation from scanned examples. It provides template-based generation, prose helpers for embedding code, and guide rendering with cross-example references.
Installation
npm install @functional-examples/documentation
Setup
import { createDocumentationPlugin } from '@functional-examples/documentation';
import { createJavaScriptPlugin } from '@functional-examples/javascript';
import type { Config } from 'functional-examples';
/**
* Configuration demonstrating the documentation plugin.
*
* The documentation plugin:
* - Adds the `generate` CLI command
* - Enables template-based doc generation
* - Provides prose helpers (file(), region())
*/
const config: Config = {
plugins: [
createJavaScriptPlugin(),
createDocumentationPlugin({
outputDir: 'generated-docs',
format: 'markdown',
}),
],
scan: {
include: ['src/**/*'],
exclude: ['**/node_modules/**', '**/dist/**'],
},
};
export default config;
Plugin Options
| Option | Type | Default | Description |
|---|---|---|---|
outputDir | string | 'docs' | Directory for generated documentation |
format | 'markdown' | 'mdoc' | 'markdown' | Output format |
enableExtractor | boolean | false | Enable markdown file extraction |
Generating Documentation
The documentation plugin adds the documentation CLI command:
#!/usr/bin/env bash
# Demonstrates generating documentation from scanned examples
cd "$(dirname "$0")"
# Generate markdown documentation from all scanned examples
npx functional-examples documentation
This renders templates for each scanned example, producing markdown files in the configured output directory.
What Gets Generated
Here's what the default template produces for a single example:
---
generated: true
---
# Sample for Documentation
A simple example demonstrating documentation generation
## `src/sample.ts`
### Region: `setup`
```typescript
import { readFileSync } from 'node:fs';
/**
* Read and parse a configuration file.
*/
export function loadConfig(path: string): Record<string, unknown> {
const content = readFileSync(path, 'utf-8');
return JSON.parse(content);
}
Region: usage
// Load configuration from a JSON file
const config = loadConfig('config.json');
console.log('Loaded config:', config);
Notice the structure: frontmatter, title from metadata, description, then each file's regions rendered as fenced code blocks with syntax highlighting. This output is verified by a snapshot assertion in the example's test suite.
### Built-in vs Custom Templates
The plugin ships with a default template that renders example metadata, files, and regions. You can override templates via the `templates` option for custom formatting.
## Prose Helpers
When rendering guides or README files, the documentation plugin provides Eta template helpers:
### File Embedding
<%= example('my-example').file('path/to/file.ts') %>
Embeds the entire file contents as a fenced code block with syntax highlighting.
### Region Embedding
<%= example('my-example').region('regionName') %>
Embeds a named code region (marked with `#region` / `#endregion` in source).
## Guide Rendering
The documentation plugin powers the guide rendering system. Guides use Eta tags to reference live example code:
```markdown
Here's how to configure the scanner:
```typescript title="scan.ts"
/**
* Basic example: Scanning for examples programmatically
*/
import { scan } from 'functional-examples';
async function main() {
// scan() auto-discovers config and plugins
const result = await scan();
console.log(`Found ${result.examples.length} examples:`);
for (const example of result.examples) {
console.log(` - ${example.title} (${example.id})`);
}
if (result.errors.length > 0) {
console.log(`\n${result.errors.length} errors occurred:`);
for (const error of result.errors) {
console.log(` - ${error.path}: ${error.message}`);
}
}
}
main().catch(console.error);
When rendered, the tag is replaced with the actual file contents from the scanned examples. This ensures documentation stays in sync with real code.
## Metadata Options
Examples can control documentation generation via the `docs` metadata field:
| Field | Type | Description |
|-------|------|-------------|
| `docs.skip` | `boolean` | Exclude this example from generated docs |
| `docs.outputName` | `string` | Override the output filename |
| `docs.template` | `string` | Use a specific template |
| `docs.hunks` | `object` | Configure which regions to include |
```yaml
# In meta.yml
docs:
skip: true # Don't generate a docs page for this example
outputName: custom # Use 'custom.md' instead of 'id.md'
See also: Plugin Authoring for creating plugins that contribute to docs, CI Integration for generating docs in CI.