Skip to content

feat(scripts): widen docs-drift checker to the full config surface - #4682

Merged
JSONbored merged 1 commit into
mainfrom
fix/widen-docs-drift-checker-4617
Jul 10, 2026
Merged

feat(scripts): widen docs-drift checker to the full config surface#4682
JSONbored merged 1 commit into
mainfrom
fix/widen-docs-drift-checker-4617

Conversation

@JSONbored

Copy link
Copy Markdown
Owner

Summary

  • Widens scripts/check-docs-drift.mjs to check the full RepositorySettings field surface (not just the 13 hand-picked *GateMode fields) and every parseable FocusManifest leaf field — recursing into nested config types such as VisualConfig/SelfHostAiModelConfig (packages/gittensory-engine/src/focus-manifest.ts) — against .gittensory.yml.example. Before this PR only 13 of ~140+ config fields had any automated documentation guarantee.
  • A field passes when its literal name (or, for FocusManifest leaves, its snake_case yml spelling) appears anywhere in the example file, or via a small alias manifest (SETTINGS_ALIAS_MANIFEST / FOCUS_MANIFEST_ALIAS_MANIFEST) for the fields documented under a renamed/nested yml key — e.g. aiReviewCloseConfidence is documented as closeConfidence nested under gate.aiReview:. This mirrors the existing GATE_MODE_MANIFEST pattern already used for *GateMode fields.
  • Documents the concretely-known gaps the widened checker found:
  • agentGlobalFreezeOverride (the other field Widen check-docs-drift.mjs to cover the full config surface #4617 named) is deliberately left undocumented in the public example, not "fixed": it is settable only from the self-host operator's own private config (source: "api_record"), and test/unit/focus-manifest.test.ts's pre-existing .gittensory.yml.example field-exhaustiveness suite already excludes it from the public file for that exact reason (fix(manifest): keep freeze override operator-only #4391's scope-leak fix — documenting it publicly would wrongly suggest a repo maintainer can set it themselves). The widened checker records this as a reviewed exclusion (NOT_YML_CONFIGURABLE_SETTINGS_FIELDS) with the same rationale, rather than reintroducing the leak fix(manifest): keep freeze override operator-only #4391 already closed.

Scope

  • The PR title follows type(scope): short summary Conventional Commit format.
  • This PR is focused and does not mix unrelated backend, UI, MCP, docs, dependency, and deploy changes.
  • This follows CONTRIBUTING.md and does not reintroduce GitHub Pages, VitePress, site/, or CNAME.
  • Fixes Widen check-docs-drift.mjs to cover the full config surface #4617

Validation

  • git diff --check
  • npm run actionlint — not applicable, no .github/workflows/** changes.
  • npm run typecheck
  • npm run test:coverage — run scoped to the changed files (test/unit/check-docs-drift-script.test.ts, plus the two adjacent consumers of .gittensory.yml.example/config/examples/gittensory.full.yml: test/unit/focus-manifest.test.ts, test/unit/config-templates.test.ts), 655 tests green, 94%+ statement/branch coverage on scripts/check-docs-drift.mjs (only main()'s subprocess-only entrypoint lines are outside in-process v8 coverage, pre-existing before this PR). Also ran the full test/unit/ directory (13,213 tests) as an extra safety net given this PR touches two shared config example files — all green. scripts/** and test/** are Codecov-ignored paths, so this PR carries no codecov/patch coverage obligation.
  • npm run test:workers — not applicable, no test/workers/** or Workers-pool-relevant changes.
  • npm run build:mcp / npm run test:mcp-pack — not applicable, no MCP package changes.
  • npm run ui:openapi:check / npm run ui:lint / npm run ui:typecheck / npm run ui:build — not applicable, no apps/gittensory-ui/** or OpenAPI/schema changes.
  • npm audit --audit-level=moderate — 0 vulnerabilities, no dependency changes in this PR.
  • New/changed behavior has tests: unit tests for the two new extractor functions (including a test proving the widened extractor catches a field shape extractGateModeFields structurally cannot — the exact agentGlobalFreezeOverride shape), plus checkDocsDrift-level tests for the alias-manifest fallback, the exclusion list, the recursive-nesting catch (reproducing the review.visual.production_url gap shape structurally), and self-defense guards for both new extractors' low-count regex-breakage checks.
  • Also directly ran npm run docs:drift-check against the real repo state (both before and after the doc additions, and again after rebasing onto fresh main immediately before pushing) — confirmed it fails with exactly the 6 real gaps before the fix, and passes clean afterward: Docs-drift check ok: 21 feature flags, 19 commands, 13 gate-mode fields, 103 RepositorySettings fields, 81 FocusManifest fields all documented.

Safety

  • No secrets, wallet details, hotkeys, coldkeys, user PATs, private keys, raw trust scores, private rankings, or private maintainer evidence are exposed.
  • Public GitHub text stays sanitized, low-noise, and does not imply compensation guarantees or optimization tactics.
  • Auth, cookie, CORS, GitHub App, Cloudflare, or session changes include negative-path tests — n/a, no such changes.
  • API/OpenAPI/MCP behavior is updated and tested where needed — n/a, no API/schema changes.
  • UI changes use live API data or real empty/error/loading states — n/a, no UI changes.
  • Visible UI changes include a UI Evidence section — n/a, no visible UI changes (backend script + docs example files only).
  • Public docs/changelogs are updated where needed — .gittensory.yml.example and config/examples/gittensory.full.yml updated; CHANGELOG.md intentionally untouched (generated at release).

Notes

  • Deliberately did not touch test/unit/focus-manifest.test.ts's own pre-existing, TypeScript-compile-time-enforced .gittensory.yml.example field-exhaustiveness (#1670) suite, even though closing its remaining gap (its visual/aiModel tokens don't recurse into their own sub-fields) would have been an alternative, arguably more robust fix for the same underlying gap. That suite is a separate, valid, already-working mechanism; Widen check-docs-drift.mjs to cover the full config surface #4617 asks specifically to widen check-docs-drift.mjs, and touching both in one PR felt like unnecessary scope creep. Cross-referencing it, however, is exactly what caught the agentGlobalFreezeOverride false positive above.

…4617)

check-docs-drift.mjs only guaranteed docs for GITTENSORY_REVIEW_* env
flags and 13 hand-picked *GateMode fields, leaving ~90 other
RepositorySettings fields and the entire FocusManifest config surface
(packages/gittensory-engine) with zero automated documentation check.

Add two new checks: every RepositorySettings field (via a brace-depth
type-literal extractor, not a name-shape regex) and every parseable
FocusManifest leaf field (recursing into nested config types, e.g.
review.visual.production_url) against .gittensory.yml.example. Fields
documented under a renamed/nested yml key are recorded in two small
alias manifests (mirroring the existing GATE_MODE_MANIFEST pattern)
rather than flagged as false positives.

Document the two live-but-undocumented fields the widened checker
found: review.visual.production_url and four sibling review.ai_model.*
overrides, in .gittensory.yml.example and its byte-synced
config/examples/gittensory.full.yml counterpart. agentGlobalFreezeOverride
(the other field named in #4617) is deliberately excluded instead: it
is settable only from the operator's own private config, and
documenting it in the public example would reintroduce the #4391
scope-leak this repo already fixed once (test/unit/focus-manifest.test.ts's
existing SETTINGS_OPERATOR_ONLY_FIELDS list carries the same exclusion).
@superagent-security

Copy link
Copy Markdown
Contributor

Superagent didn't find any vulnerabilities or security issues in this PR.

@JSONbored JSONbored self-assigned this Jul 10, 2026
@JSONbored
JSONbored merged commit 8ad748b into main Jul 10, 2026
7 checks passed
@JSONbored
JSONbored deleted the fix/widen-docs-drift-checker-4617 branch July 10, 2026 11:49
@codecov

codecov Bot commented Jul 10, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 94.14%. Comparing base (2b4b5e3) to head (1832602).
⚠️ Report is 5 commits behind head on main.
✅ All tests successful. No failed tests found.

Additional details and impacted files
@@           Coverage Diff           @@
##             main    #4682   +/-   ##
=======================================
  Coverage   94.14%   94.14%           
=======================================
  Files         436      436           
  Lines       38525    38525           
  Branches    14046    14046           
=======================================
  Hits        36268    36268           
  Misses       1599     1599           
  Partials      658      658           
🚀 New features to boost your workflow:
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

carlh7777 pushed a commit to carlh7777/gittensory that referenced this pull request Jul 10, 2026
… 65536-char limit (JSONbored#4579)

* fix(db): raise the stored PR/issue body cap from 4000 to GitHub's own 65536-char limit

compactGitHubPayload silently truncated any PR/issue body over 4000 chars before
storing it -- with zero indication anything was cut -- and every body-content
check (screenshotTableGate's viewport/theme matrix parser, linked-issue
satisfaction, slop keyword matching) reads the stored copy, not a live GitHub
fetch. A body just past that threshold reads as "missing" evidence even when
the contributor's submission was genuinely complete.

Confirmed live on metagraphed#4682: a real, correctly-formatted 12-image
before/after table (5160 chars) got closed for "missing before/after
screenshot table" because only the first ~4000 chars (one row) were ever
persisted. The new cap matches GitHub's own issue/PR body limit, so it can
only ever bind on content GitHub itself was never going to accept.

* fix(db): log a structured trace whenever a PR/issue body actually gets truncated

The JSONbored#4682 incident's entire failure mode was silence -- the old 4000-char cap
quietly corrupted screenshotTableGate's matrix parser (and every other
body-content check) for an unknown period with zero log line, audit row, or
any other trace. The cap is now GitHub's own 65536-char limit so this should
never fire in practice, but if it ever does again, github_app.body_truncated_on_store
makes it immediately greppable instead of requiring manual DB archaeology.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Development

Successfully merging this pull request may close these issues.

Widen check-docs-drift.mjs to cover the full config surface

1 participant