Skip to main content

ADR-0007: Single Source of Truth for Documentation

Single Source of Truth

This ADR is automatically copied from docs/adr/0007-single-source-documentation.md in the repository. Edit the source file to update this page.


Status

Accepted

Context

This project has two categories of documentation:

1. Hybrid documentation (GitHub + Docusaurus)

Files that must render correctly in both contexts:

  • README.md - First thing visitors see on the repository
  • CONTRIBUTING.md - Guide for contributors
  • docs/adr/*.md - Architecture Decision Records

These files contain plain Markdown without embedded PlantUML/Mermaid diagrams. They are the primary source on GitHub and should also appear in the Docusaurus site.

2. Docusaurus-first documentation

Files in test-docusaurus-site/docs/examples/ that contain PlantUML/Mermaid diagrams:

  • Example pages (e.g., Little Red Riding Hood sequence diagrams)
  • Plugin architecture diagrams
  • Domain model examples

These are Docusaurus-only because GitHub does not render PlantUML (only limited Mermaid support). They require the remark-kroki-a11y plugin and Kroki service to generate images.

This ADR addresses the first category: hybrid documentation.

The challenge

For hybrid documentation, GitHub and Docusaurus have conflicting requirements:

  • GitHub renders plain Markdown files directly
  • Docusaurus requires front-matter (YAML header with id, title, etc.) for proper navigation
  • Docusaurus uses different link resolution (relative paths within the docs folder)

Maintaining two copies leads to:

  • Inconsistencies when one copy is updated but not the other
  • Double maintenance effort
  • Risk of outdated information

Options

Option 1: Duplicate documentation

Maintain separate files for GitHub and Docusaurus.

Pros:

  • Each context gets optimized content
  • No build-time processing needed

Cons:

  • Double maintenance
  • Inevitable inconsistencies
  • Violates DRY principle

Use Docusaurus docs as the source and symlink from root.

Pros:

  • Single source

Cons:

  • Front-matter visible on GitHub (ugly)
  • Symlinks don't work well on all platforms
  • Links in Docusaurus format don't work on GitHub

Option 3: GitHub as source, copy with transformation at build time

Maintain files in GitHub-friendly locations (root README.md, CONTRIBUTING.md, docs/adr/) and copy them to Docusaurus with transformations.

Pros:

  • Single source of truth
  • GitHub renders files natively (no front-matter clutter)
  • Docusaurus gets proper front-matter and navigation
  • Links can be transformed for each context

Cons:

  • Requires build-time script
  • Generated files must be gitignored
  • Slightly more complex setup

Option 4: Use Docusaurus plugin for external docs

Use a Docusaurus plugin that can import external Markdown files.

Pros:

  • No custom scripts needed

Cons:

  • Plugin dependency
  • Less control over transformations
  • May not handle all edge cases (links, front-matter)

Decision

We choose Option 3: GitHub as source, copy with transformation at build time.

The start-docs.sh script (and equivalent logic in the GitHub Actions workflow) copies:

  • README.mdtest-docusaurus-site/docs/readme.md
  • CONTRIBUTING.mdtest-docusaurus-site/docs/contributing.md
  • docs/adr/*.mdtest-docusaurus-site/docs/adr/*.md

During copy, the script:

  1. Prepends Docusaurus front-matter (id, title, sidebar_label, description)
  2. Adds an info admonition noting the file is auto-copied
  3. Transforms links:
    • docs/adr/README.md./adr/ (index page)
    • docs/adr/..../adr/... (relative Docusaurus paths)
    • CONTRIBUTING.md./contributing

The generated files are listed in .gitignore to prevent committing duplicates.

Consequences

Positive

  • Single source of truth for all documentation
  • GitHub users see clean Markdown without Docusaurus artifacts
  • Docusaurus site has proper navigation and styling
  • ADRs automatically appear in sidebar (using autogenerated directive)
  • New ADRs only need to be added to docs/adr/, no sidebar updates needed

Negative

  • Developers must run start-docs.sh to see documentation locally in Docusaurus
  • CI/CD pipeline must include the copy logic
  • Links in source files must use GitHub-relative paths (transformed at build time)

Neutral

  • The pattern is documented in README.md under "Single Source of Truth"
  • Info admonitions in Docusaurus pages indicate the source location

Actions

  1. ✅ Create start-docs.sh script with copy and transformation logic
  2. ✅ Update .github/workflows/deploy-docs.yml with same logic
  3. ✅ Add generated files to .gitignore
  4. ✅ Use autogenerated sidebar directive for ADRs
  5. ✅ Document the pattern in README.md

References