feat(scripts): widen docs-drift checker to the full config surface - #4682
Merged
Conversation
…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).
Contributor
|
Superagent didn't find any vulnerabilities or security issues in this PR. |
Codecov Report✅ All modified and coverable lines are covered by tests. 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:
|
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.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
scripts/check-docs-drift.mjsto check the fullRepositorySettingsfield surface (not just the 13 hand-picked*GateModefields) and every parseableFocusManifestleaf field — recursing into nested config types such asVisualConfig/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.SETTINGS_ALIAS_MANIFEST/FOCUS_MANIFEST_ALIAS_MANIFEST) for the fields documented under a renamed/nested yml key — e.g.aiReviewCloseConfidenceis documented ascloseConfidencenested undergate.aiReview:. This mirrors the existingGATE_MODE_MANIFESTpattern already used for*GateModefields.review.visual.production_url(named in Widen check-docs-drift.mjs to cover the full config surface #4617) — the maintainer's own most recently shipped visual-capture field, previously undocumented.review.ai_model.*overrides —ollama_model/openai_model/openai_compatible_model/anthropic_model(feat(selfhost): support per-repo model overrides for ollama/openai/anthropic providers #3902) — surfaced by the same widened check, undocumented for the same reason (nested in a different package's type). Added to.gittensory.yml.exampleand its byte-syncedconfig/examples/gittensory.full.ymlcounterpart (kept in lockstep pertest/unit/config-templates.test.ts's exact-match check).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"), andtest/unit/focus-manifest.test.ts's pre-existing.gittensory.yml.example field-exhaustivenesssuite 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
type(scope): short summaryConventional Commit format.CONTRIBUTING.mdand does not reintroduce GitHub Pages, VitePress,site/, orCNAME.Validation
git diff --checknpm run actionlint— not applicable, no.github/workflows/**changes.npm run typechecknpm 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 onscripts/check-docs-drift.mjs(onlymain()'s subprocess-only entrypoint lines are outside in-process v8 coverage, pre-existing before this PR). Also ran the fulltest/unit/directory (13,213 tests) as an extra safety net given this PR touches two shared config example files — all green.scripts/**andtest/**are Codecov-ignored paths, so this PR carries nocodecov/patchcoverage obligation.npm run test:workers— not applicable, notest/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, noapps/gittensory-ui/**or OpenAPI/schema changes.npm audit --audit-level=moderate— 0 vulnerabilities, no dependency changes in this PR.extractGateModeFieldsstructurally cannot — the exactagentGlobalFreezeOverrideshape), pluscheckDocsDrift-level tests for the alias-manifest fallback, the exclusion list, the recursive-nesting catch (reproducing thereview.visual.production_urlgap shape structurally), and self-defense guards for both new extractors' low-count regex-breakage checks.npm run docs:drift-checkagainst the real repo state (both before and after the doc additions, and again after rebasing onto freshmainimmediately 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
UI Evidencesection — n/a, no visible UI changes (backend script + docs example files only)..gittensory.yml.exampleandconfig/examples/gittensory.full.ymlupdated;CHANGELOG.mdintentionally untouched (generated at release).Notes
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 (itsvisual/aiModeltokens 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 widencheck-docs-drift.mjs, and touching both in one PR felt like unnecessary scope creep. Cross-referencing it, however, is exactly what caught theagentGlobalFreezeOverridefalse positive above.