Overview
Merlon Docs, a documentation system delivered as a toolchain and an Agent Skill, helps teams maintain large documentation in small shard files, compile them into canonical outputs, and validate before merge. It is built for LLM-assisted authoring, human review, and compiled output for agents and end-user readers.
This page is the mental model for the whole system. Use it to orient yourself before diving into command details, API modules, or config fields.
What problem it solves
Section titled “What problem it solves”Large Markdown guides are hard to edit, diff, and link correctly. A single README.md or guides.md with dozens of headings invites merge conflicts, broken cross-references, and orphan sections that no longer appear in the table of contents.
Merlon Docs inverts the workflow:
- Authors edit shards: one file per section, listed in the manifest (
index.mdorshards.md) of their guide. - Compile stitches shards: it normalizes heading levels and rewrites links.
- Validation catches drift: orphans and broken internal links or
#anchors, plus optional prose and style linters. - Compiled output serves consumers: compiled guides (some as publish outputs) and the optional monolith.
You never hand-maintain the compiled file. Shards are the source of truth. Each compiled guide is generated, whether it is {name}.md under outputDir or a publish output such as README.md.
Core vocabulary
Section titled “Core vocabulary”The glossary defines the core terms:
- Shard: one
.mdfile that becomes part of a guide (such as01-intro.md). - Guide: a directory of shards plus a manifest, named in
compileOrder. - Compiled guide: the file compile writes for one guide.
- Publish output: a compiled guide at its own
compile.outputFile, such as a package README. - Monolith: the optional single file that stitches the guides without
compile.outputFile. - Refs registry: GitHub-style heading slugs from compile output.
Paths and config: shards live under the docs root (--docs-root), one subdirectory per guide. Generated paths are relative to outputDir, which defaults to _build and is safe to delete. --config resolves from the directory you run the command in, not from the docs root (--config vs --docs-root). Path layout in Config essentials has every other path rule and default, and loadConfig(path, configBase) in the config API follows the same rules.
How the pieces fit together
Section titled “How the pieces fit together”flowchart TB
subgraph author["Authoring layer"]
shards["Shard .md files"]
index["index.md / shards.md"]
end
subgraph merlon["Merlon Docs"]
cli["@merlon-docs/merlon-docs-cli"]
core["@merlon-docs/merlon-docs-core"]
presets["@merlon-docs/merlon-docs-presets"]
config["merlon.config.json"]
end
subgraph outputs["Generated outputs"]
compiled["Compiled guides under outputDir"]
publish["Publish outputs"]
monolith["Optional monolith (outputFile)"]
refs["refs.json"]
end
subgraph validate["Validation"]
orphans["Orphan / manifest checks"]
peers["Peer linters optional"]
end
config --> cli
cli --> core
presets -.-> peers
shards --> core
index --> core
core --> compiled
core --> publish
core --> monolith
core --> refs
compiled --> validate
publish --> validate
monolith --> validate
shards --> validate
| Package | Role |
|---|---|
@merlon-docs/merlon-docs-cli |
Command-line entry point: compile, check, review, shard, refs, peer linter wrappers. |
@merlon-docs/merlon-docs-core |
Library behind the CLI: compile/assemble, refs, validation, shard orchestration, hooks. |
@merlon-docs/merlon-docs-presets |
Starter markdownlint configs and the MerlonDocs Vale style (opt-in via config / .vale.ini). |
The CLI is a thin wrapper over core. Integrators (CI, editors, agents) can call core directly or shell out to the CLI.
The pipeline in order
Section titled “The pipeline in order”Understanding this sequence explains why most commands exist:
[optional] merlon shard Split a source document into guide shards (md-tree) ↓ Edit shards + index.md ↓ merlon compile Assemble outputs, rewrite links, write refs.json ↓ merlon check Run the validation gateSplit (merlon shard) is the inverse path. Use it to bootstrap shards from an existing source document, not on every edit cycle.
What compile actually does
Section titled “What compile actually does”For each guide in compileOrder, core:
- Reads section files: from link order in the manifest (
index.md/shards.md). See Manifest compile order when the manifest mixes preamble example links with a## Sectionslist (compile.sectionsHeading). - Transforms each shard: demotes headings to fit the guide level and handles the preamble shard (
compile.preambleSection) as Project layout says. Then it runs the compile hooks (stripAnchors,codeEvidence,inlineInserts) by default. See Default compile hooks. Cross-guide link rewrite runs at assembly. See Cross-guide link rewriting. - Assembles the guide body: injects optional
compile.titleas a##heading followed by a blank line, then concatenates sections in order. When the first shard’s top heading matches the title, that duplicate heading is stripped. - Rewrites links: the link passes turn a shard’s links to other shards into
#slugtargets, in the same document or in another output. They rewrite a./or../link to any indexed shard, and a bare link to a shard the guide stitches. A link to a guide thatcompile.crossGuideLinks.ignoreGuidesnames keeps a path to the shard instead, except where a link to a shard the compiling guide stitches takes its in-document anchor. The passes then rebase the shard’s../paths, kept ones included, relative to the guide’s link base, except the ones Publish-relative exclusions lists, such as a path that leads to no file. - Marks broken links and re-aligns tables: by default, a BROKEN LINK marker replaces each
#fragmentlink that matches no heading or section slug in the compiled guide. A link to a missing file stays a link, and link lint reports it. Then core re-aligns each aligned table whose links changed width. See Tables after link rewriting. - Writes outputs: one compiled guide per guide (at
compile.outputFileor the default path), plus the monolith when top-leveloutputFileis set and at least one guide has nocompile.outputFile.
Guides with compile.outputFile are excluded from the monolith so you can publish npm READMEs, DEVELOPERS.md, or compiled review guides side by side.
What validation checks
Section titled “What validation checks”merlon check runs a fixed order of stages, from the orphan check to the coverage scan. A failure in one of the first three stops the run at once, while most later stages report a failure and let the run go on. Check gate lists the stages and when each one runs.
Config as the wiring layer
Section titled “Config as the wiring layer”merlon.config.json is the single contract between your repo layout and every command:
compileOrder: which guides exist and in what order they appear in the monolith.guides[].compile: per-guide manifest name, hooks, publish path, title, scope root, etc.outputFile: optional monolith path.refs: registry file path and slug algorithm.lint/vale: peer linter config paths and scan globs.
This repository uses Merlon Docs on its own docs under docs/, and its docs/merlon.config.json is an example of a multi-output layout. Guide directories lists the output each of its guides compiles to.
Where to go next
Section titled “Where to go next”- The Agent Skill and its workflows: Agent Skill and Skill workflows
- Commands and priority tiers: the Feature catalog and Personas and priority tiers
- Who runs which command: the Actors and obligations table in the usage model
- Intentional limits: the Design constraints, each with a one-line summary
- Install and daily commands: the Client CLI guide
- Programmatic API: the Client core guide
- Config fields: the config API
- Compile hooks: the Compile hooks overview
- Contributing to this repo: the Developer guide
- Performance SLOs at scale: the Performance goals page
- A publish landing example: this repository compiles its root
README.mdfromdocs/repo-readme/. Its copy follows the Publish landing style and the claim tiers in Benefit claims and evidence