GRP-002 Circular references
Overview
Section titled “Overview”Treats Markdown links between documents as a graph and validates that no cycle (a closed path such as A → B → C → A) exists. Detected cycles are reported as error. This is a project-scope rule and is evaluated across all documents loaded via include.
Only relative links to .md files are considered. Pure anchor links (#section) and external URLs are ignored.
Why it matters
Section titled “Why it matters”A cycle where document A references B, B references C, and C references A cannot be spotted by a human reading a single file. To keep dependencies coherent, the document graph should be a DAG (directed acyclic graph) — cycles confuse readers and make impact analysis on updates much harder. When AI generates documents in bulk, links can become unintentionally bidirectional and form cycles. This rule detects them.
Options
Section titled “Options”| Field | Type | Required | Description |
|---|---|---|---|
files | string | — | Glob of files included in cycle detection. If omitted, every document is included |
exclude | string[] | — | Array of globs for files to exclude from the graph |
The rule works even with no options at all. Use exclude to skip files that intentionally hold links in multiple directions, such as table-of-contents pages or index files.
Bad example
Section titled “Bad example”docs/a.md:
# ASee [B](./b.md).
docs/b.md:
# BSee [C](./c.md).
docs/c.md:
# CSee [A](./a.md).The cycle a.md → b.md → c.md → a.md triggers a violation.
docs/a.md line 2 error Circular reference detected: docs/a.md -> docs/b.md -> docs/c.md -> docs/a.md GRP-002After fix
Section titled “After fix”Cut “the weakest dependency” in the cycle. For example, replace the link from c.md to a.md with prose.
docs/c.md:
# C
This module is consumed by upstream documents.Configuration example
Section titled “Configuration example”{ "rule": "grp002", "options": { "files": "docs/**/*.md", "exclude": ["docs/index.md", "docs/sitemap.md"] }}Files listed in exclude are removed from the graph entirely as nodes. Cycles that pass through them are no longer detected, so reserve exclude for table-of-contents-style files that need bidirectional links.
Related rules
Section titled “Related rules”- REF-001 Broken links — Validates that linked files exist
- GRP-001 Traceability chain — Validates table-based ID reference chains
- GRP-003 Orphan documents — Detects files that no document references