housekeeping: typecheck scope, dead code, drifted duplicates, and five tests that cannot fail #122
Labels
No labels
already-shipped
bug
documentation
duplicate
enhancement
external-review
good first issue
help wanted
in progress
invalid
needs-decision
proposal
question
security
wontfix
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set.
Reference: crenshawdev/cadence-archived#122
Loading…
Add table
Add a link
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Low-severity residue from the v3.2.0 audit. None of these is a live defect; each is drift, dead weight, or a test that cannot fail. Grouped because they are all small and none earns its own issue.
Typecheck scope
The entire test suite is excluded from typechecking.
tsconfig.ci.json:15excludescadence-core/bin/**/*.test.mjs- roughly 13,000 lines including the 5,051-lineplanning.test.mjs- while every non-test file is checked. Tests are exactly where a stale-shape assumption survives, because a test that only reads the properties that still exist keeps passing after the shape changes underneath it.self-verifycannot see this class: it lints prose against code, not test shapes. Include them, or write in the file why not.@ts-checkpragmas are decorative. 40 of 41 non-test files carry// @ts-check, andtsconfig.ci.jsonsetscheckJs: true, which checks every included file regardless.review-provider.mjsis the one file without the pragma and is checked anyway. Harmless, except the tsconfig comment describes the pragmas as load-bearing ("the pragmas exist to catch real drift"). Either dropcheckJsand let them mean something, or drop them.strictNullChecksis worth pricing on its own.strict: falseis defensible for zero-dep scripts and the tsconfig says why. But two confirmed findings in this milestone (#117's unreadable-CONTEXT exemption, and theplan-sizeitem below) are null-versus-absent confusions, which is the classstrictNullChecksalone catches. Price it separately from full strict.Dead and unreachable
lib/config-merge.mjs:33readJSONhas zero callers. Repo-wide, including its own file and every test.readLayersuperseded it. Delete.lib/milestone-prune.mjs:60has an unreachable clause./^###? /already matches##and###, so/^## /is a strict subset and can never be the test that stops the loop.Worth a second look while in there: the loop also does not stop at
#or####, so a phase detail section followed by an h1 appendix is deleted to EOF. The shipped ROADMAP template never produces that shape, which is why this is not filed as a bug.Drifted duplicates
lib/planning-files.mjs:1164usesinwhere the sibling useshasOwnProperty.inwalks the prototype chain, sostatus: "constructor"or"toString"increments a phantom counter.lib/trace.mjs:444does the identical job withObject.prototype.hasOwnProperty.call(...)and states why. Same idiom, two implementations, one hardened. Observable effect today is nil; collapse the drift.self-verify.mjs:1211reads--rootwith an inlineindexOf.weight.mjs:46-53has aflagValue()written specifically to close this, and its docblock calls it "the quiet-wrong-number class... worse here than a hard error because the envelope looks correct".weight.test.mjspins three cases.self-verify.mjsgot none of it.--root "$TREE"with$TREEempty silently lints whatever the job is cd'd into. ImportflagValue.Envelope shape
planning.mjs:1456plan-sizereportswithin: truewhen ROADMAP.md is absent or unreadable.read(...) || ''makesphaseRequirements('')returnfound:false, thephase-too-bigcomparison is skipped, and the envelope carrieswithin: truebesiderequirements_found: false.The seam is honest and says so, and
workflows/plan.md:68does readrequirements_found, so the wiring holds today. The risk is the field name:withinis the boolean-shaped key, and a future caller reaching for it gets a pass from a file that does not exist. Omitwithin, or emitwithin: null, whenrequirements_foundis false.Tests that cannot fail
design-brief.test.mjs- five tests, no product code. The file importsnode:test,node:assert,node:fs,node:path,node:urland no Cadence module. Every assertion is overfixtures/verbatim.design-brief.md, which its own header describes as copied byte-for-byte and immutable: the file has a## 17. Open itemsheading, the table has five rows, the rows name five substrings, no status cell containsOPEN, the file contains exactly twoOPENoccurrences.These cannot fail on a Cadence regression, only on a hand-edit of a file nobody edits. They are a checksum on committed evidence wearing test clothing, and the header concedes the actual suppression rule is untested. Either drive the real
--briefsuppression path or delete them; a green test that cannot go red is worse than no test, because it reports coverage that does not exist.Not in scope
The rest of the suite is unusually strong and should not be swept along with this.
bm25.test.mjs:28hand-computes a score rather than snapshotting the implementation;retired-keys.test.mjsuses onetest()per row with a written rationale;review-provider.test.mjsdrives six real failure modes through an in-process transport seam;include-consumers.test.mjspins an empty register and drives both bounds from a synthetic row. This issue is about one file, not a testing-practices sweep.Fixed in v3.2.0 (PR #124). HYG-01, phase 4. tsconfig.ci.json states why the test suite is excluded and that checkJs, not the pragma, is what checks a file. readJSON and the unreachable /^## / clause are deleted, planning-files.mjs uses the hasOwnProperty idiom, self-verify reads --root through weight.mjs's flagValue rule with its seam catch arm, plan-size carries an explicit no-comparison-ran signal, and design-brief.test.mjs is gone with its fixture kept.
Verified through the phase UAT walk. The milestone audit traced 12/12 requirements with 0 broken and 36/36 acceptance criteria covered.