docforge
docforge
Summary
Renderer-agnostic Python documentation compiler that converts Python docstrings into structured documentation for both humans (MkDocs) and machines (MCP / AI agents).
doc-forge statically analyzes source code, builds a semantic model of modules,
classes, functions, and attributes, and renders that model into documentation
outputs without executing user code.
Installation
Install using pip:
CLI usage
Generate an MkDocs site from a Python package:
Generate MCP JSON documentation:
Generate MkDocs site and MCP JSON documentation:
Serve MkDocs locally:
Serve MCP locally:
Core concepts
Loader
Extracts symbols, signatures, and docstrings using static analysis.
Semantic model
Structured, renderer-agnostic representation of the API.
Renderer
Converts the semantic model into output formats such as MkDocs or MCP JSON.
Symbol
Any documentable object
- module
- class
- function
- method
- property
- attribute
Architecture
doc-forge follows a compiler architecture:
Front-end:
Static analysis of modules, classes, functions, type hints, and docstrings.
Middle-end:
Builds a semantic model describing symbols and relationships.
Back-end:
Renders documentation using interchangeable renderers.
This architecture ensures deterministic documentation generation.
Rendering pipeline
Typical flow:
1 2 3 4 5 6 7 8 9 | |
Google-Styled Doc-Forge Convention (GSDFC)
GSDFC defines how docstrings must be written so they render correctly in MkDocs and remain machine-parsable by doc-forge and AI tooling.
- Docstrings are the single source of truth.
doc-forgecompiles docstrings but does not generate documentation content.- Documentation follows the Python import hierarchy.
- Every public symbol should have a complete and accurate docstring.
General rules
- Use Markdown headings at package and module level.
- Use Google-style structured sections at class, function, and method level.
- Use type hints in signatures instead of duplicating types in prose.
- Write summaries in imperative form.
- Sections are separated by
---
Notes subsection grouping
Group related information using labeled subsections.
Example:
1 2 3 4 5 6 7 8 9 10 11 12 13 | |
Example formatting
- Use indentation for examples.
- Indent section contents using four spaces.
- Use code blocks for example code.
Example
Single example:
1 2 3 4 5 6 | |
Multiple examples:
1 2 3 4 5 6 7 8 9 10 11 12 13 | |
Avoid fenced code blocks inside structured sections.
Separator rules
Use horizontal separators only at docstring root level to separate sections:
Allowed locations:
- package docstrings
- module docstrings
- major documentation sections
Do not use separators inside code sections.
Package docstrings
Package docstrings act as the documentation home page.
Recommended sections:
1 2 3 4 5 6 7 8 9 | |
Example
Package Doc String:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 | |
Module docstrings
Module docstrings describe a subsystem.
Recommended sections:
1 2 3 | |
Example
Module Doc String:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 | |
Class docstrings
Class docstrings define object responsibility, lifecycle, and attributes.
Recommended sections:
1 2 3 4 | |
Example
Simple Foo:
Complex Bar:
Function and method docstrings
Function docstrings define API contracts.
Recommended sections:
1 2 3 4 5 6 | |
Example
Simple process method:
Multiple Examples:
Property docstrings
Properties must document return values.
Example
Property Doc String:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | |
Attribute documentation
Document attributes in class docstrings using Attributes:.
Example
Attribute Doc String:
1 2 3 4 5 6 7 8 9 10 11 12 | |
Parsing guarantees
GSDFC ensures doc-forge can deterministically extract:
- symbol kind (module, class, function, property, attribute)
- symbol name
- parameters
- return values
- attributes
- examples
- structured Notes subsections
This enables:
- reliable MkDocs rendering
- deterministic MCP export
- accurate AI semantic interpretation
Notes
- doc-forge never executes analyzed modules.
- Documentation is generated entirely through static analysis.
Classes
GriffeLoader
Load Python modules using Griffe and convert them into doc-forge models.
This loader uses the Griffe introspection engine to analyze Python source
code and transform the extracted information into Project, Module,
and DocObject instances used by doc-forge.
Initialize the Griffe-backed loader.
Creates an internal Griffe loader instance with dedicated collections for modules and source lines.
Functions
load_module
Load and convert a single Python module.
The module is introspected using Griffe and then transformed into
a doc-forge Module model.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
path |
str
|
Dotted import path of the module. |
required |
Returns:
| Name | Type | Description |
|---|---|---|
Module |
Module
|
A populated |
load_project
Load multiple modules and assemble them into a Project model.
Each module path is introspected and converted into a Module
instance. All modules are then aggregated into a single Project
object.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
module_paths |
List[str]
|
List of dotted module import paths to load. |
required |
project_name |
str
|
Optional override for the project name. Defaults to the top-level name of the first module. |
None
|
skip_import_errors |
bool
|
If True, modules that fail to load will be skipped instead of raising an error. |
None
|
Returns:
| Name | Type | Description |
|---|---|---|
Project |
Project
|
A populated |
Raises:
| Type | Description |
|---|---|
ValueError
|
If no module paths are provided. |
ImportError
|
If a module fails to load and |
MCPRenderer
Renderer that generates MCP-compatible documentation resources.
This renderer converts doc-forge project models into structured JSON resources suitable for consumption by systems implementing the Model Context Protocol (MCP).
Functions
generate_sources
Generate MCP documentation resources for a project.
The renderer serializes each module into a JSON resource and produces
supporting metadata files such as nav.json and index.json.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
project |
Project
|
Documentation project model to render. |
required |
out_dir |
Path
|
Directory where MCP resources will be written. |
required |
MkDocsRenderer
Renderer that produces Markdown documentation for MkDocs.
Generated pages use mkdocstrings directives to reference Python modules, allowing MkDocs to render API documentation dynamically.
Functions
generate_readme
Generate a README.md file from the root module docstring.
Behavior:
- If
module_is_sourceis True,README.mdis written to the project root directory. - If False, README generation is currently not implemented.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
project |
Project
|
Project model containing documentation metadata. |
required |
docs_dir |
Path
|
Directory containing generated documentation sources. |
required |
module_is_source |
bool
|
Whether the module is treated as the project source root. |
None
|
generate_sources
Generate Markdown documentation files for a project.
This method renders a documentation structure from the provided project model and writes the resulting Markdown files to the specified output directory.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
project |
Project
|
Project model containing modules to document. |
required |
out_dir |
Path
|
Directory where generated Markdown files will be written. |
required |
module_is_source |
bool
|
If True, treat the specified module as the documentation root rather than nesting it inside a folder. |
None
|
Functions
discover_module_paths
Discover Python modules within a package directory.
The function scans the filesystem for .py files inside the specified
package and converts them into dotted module import paths.
Discovery rules:
- Directories containing
__init__.pyare treated as packages. - Each
.pyfile is treated as a module. - Results are returned as dotted import paths.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
module_name |
str
|
Top-level package name to discover modules from. |
required |
project_root |
Path
|
Root directory used to resolve module paths. If not provided, the current working directory is used. |
None
|
Returns:
| Type | Description |
|---|---|
List[str]
|
List[str]: A sorted list of unique dotted module import paths. |
Raises:
| Type | Description |
|---|---|
FileNotFoundError
|
If the specified package directory does not exist. |