Writing Documentation¶
Conflux documentation follows the Diataxis framework. Every page belongs to exactly one of four types. Match the type to the reader's need, not the subject matter. For a full explanation of the framework and why Conflux uses it, see The Diataxis Framework.
Choosing a Type¶
Ask yourself two questions:
- Is the reader learning or doing? → Tutorial (learning) / How-to (doing)
- Are they looking something up or wanting to understand? → Reference (lookup) / Explanation (understand)
A single subject may need all four types as separate pages.
Tools¶
| Tool | Purpose | Output |
|---|---|---|
| Zensical | General docs (guides, concepts, reference, tutorials) | docs/docs/ → rendered site |
| Scribe | API reference | Auto-generated via php artisan scribe:generate |
File & Navigation Conventions¶
- File names:
kebab-case.md - Place pages in a logical subfolder under
docs/docs/(e.g.explanation/frameworks,how-to-guides/,reference/) - Navigation is derived from folder structure — no manual config needed unless ordering matters
- Page title = first
# H1heading
Markdown Conventions¶
Zensical supports Material for MkDocs extensions.
Admonitions
!!! note "Optional title"
Content here.
!!! warning
Types: note, tip, info, success, warning, danger, failure, bug, example, quote
Tabbed content
Code blocks with line numbers
Scribe: Documenting API Endpoints¶
Scribe generates API docs from controller docblocks. Do not write manual Markdown pages for endpoints — add docblocks to the controller method instead, then regenerate:
Common annotations:
/**
* @group Orders
* @authenticated
*
* @bodyParam shop_id string required The shop UUID. Example: 01HXYZ...
*
* @response 200 {"id": "01HXYZ...", "status": "pending"}
*/
public function store(StoreOrderRequest $request): OrderResource
Architecture Decision Records (ADRs)¶
Significant architecture decisions — a new entity, a changed data-flow direction, an auth model change, anything a future reader would ask "why was it built this way?" about — get an ADR instead of an inline narrative admonition.
- Location:
docs/docs/adr/ - Naming: 4-digit zero-padded sequence + present-tense-imperative kebab-case title
- Template: Nygard-style —
Date+Status, thenContext/Decision/Consequences. No frontmatter (ADRs are not a Diataxis type). - An ADR is superseded, never edited in place: a changed decision gets a new ADR, and the old one
is marked
Status: Superseded by 00NN. - Add new ADRs to the nav in
zensical.tomlunder "Decisions" — the nav is the single listing;docs/docs/adr/index.mdstays a short intro, likeexplanation/index.mdandhow-to-guides/index.md.
What the gate enforces¶
The conventions above are checked automatically, so a forgotten nav entry or a number taken twice on parallel branches fails before it reaches master. Failure messages name the file and the rule number:
| Rule | Checked |
|---|---|
| 1 | Filename matches NNNN-kebab-case.md |
| 2 | Numbers are unique |
| 3 | Numbers are contiguous from 0001 |
| 4 | The H1 number matches the filename |
| 5 | Date: YYYY-MM-DD is present and real |
| 6 | Status: starts with Accepted, Proposed, Deprecated, Superseded by or Partially superseded by |
| 7 | An ADR referenced by a status exists |
| 8 | Context, Decision and Consequences are all present |
| 9 | There is no frontmatter |
| 10 | Every ADR has exactly one nav entry, and every entry points at a file that exists |
| 11 | Nav entries are ordered and labelled by number, with adr/index.md first |
| 12 | A number added in a merge request is not already taken on the target branch |
Rules 1 to 11 run in tests/Unit/Docs/AdrTest.php, so composer test catches them locally. Rule 12
runs as .gitlab/scripts/check-adr-numbers.sh in the quality stage: a branch that adds a
duplicate number is internally consistent on its own, so only a comparison against the target
branch can see the collision.
Rule 3 means a number cannot be skipped. If an ADR is drafted and dropped, either reuse its number for the next decision or adjust the test — a gap is not silently tolerated, because the common cause of one is a mistake.