Split out of #88 (contract audit by @darlingm). These are places where two authoritative prompts state incompatible rules. A careful orchestrator survives all of them, which is why none has produced a visible failure — but each is a trap for the next person editing that step, and they're cheap to settle in one pass.
Verified, with the contradiction in each:
-
A3 — skills/hyperresearch.md:213 invariant 2 says "No re-synthesizing"; :235 says to spawn the synthesizer for "ONE compression pass". Scope the invariant to exclude the compression pass.
-
A4 — skills/hyperresearch-2-width-sweep.md:146 tells fetchers "fetch ONLY the URLs in your batch. Do not search for additional URLs", while skills/hyperresearch.md:224 invariant 12 makes citation-chasing MANDATORY and core/hooks.py:3096 tells them to collect leads. Decide whether the batch is closed, and say so in one place.
-
A7 — hyperresearch-4-loci-analysis.md:121 permits zero loci via a justified skip_loci; hyperresearch-7-source-tensions.md:89 hardcodes an exit criterion of "3–7 tensions" with no zero path.
-
A11 — hyperresearch-12-critics.md:60 says "If one fails, you can proceed with the partial set", then :66 requires all four findings files, and core/runs.py:456-465 hard-checks all four filenames. The permitted failure mode produces an unshippable run with no documented remedy.
-
A15 — hyperresearch-1-decompose.md:128 says short has no Opinionated Synthesis section; hyperresearch-11-synthesize.md:118 hardcodes that heading into the outline template.
-
B1 — hyperresearch-1-decompose.md:104 says "Do NOT include wrapper-contract requirements here", and the same file's own example at :75-77 includes one.
-
B15 — hyperresearch-16-readability-audit.md:62 says to write recommendations as a JSON array; the agent's schema at core/hooks.py:2612-2645 is an object with recommendations and summary keys.
-
B16 — core/hooks.py:1556 tells the polish auditor to strip YAML frontmatter unconditionally; :1585-1601 tells it to fix those fields in place if a wrapper requires them. The spawn contract at hyperresearch-15-polish.md:58-63 passes only draft_path and polish_log_path, so the agent is asked to branch on a contract it never receives.
-
B24 — hyperresearch-16-readability-audit.md:162 declares "Pipeline complete… You're done" before the ship gate, which skills/hyperresearch.md:209 and invariant 14 run afterwards.
-
A8 — hyperresearch-1-5-chapter-partition.md:5 and core/profiles.py:315 set chapters: (4,10); :36 of the same skill describes recording 1 chapter. This one is a documented escape hatch stated as a conflict — probably just needs a sentence saying so.
Also worth folding in while touching this area: hyperresearch-14-5-cite-check.md:17's one-line Goal claims exhaustive citation verification, while the frontmatter at :6-7 and the body at :36 correctly disclose sampling. Wording only, but it's the line most people read.
Unrelated small bug found in the same file: core/citecheck.py:180 computes keep_every = round(1 / 0.6) = 2, so a configured sample_rate of 0.6 actually samples 50%.
Split out of #88 (contract audit by @darlingm). These are places where two authoritative prompts state incompatible rules. A careful orchestrator survives all of them, which is why none has produced a visible failure — but each is a trap for the next person editing that step, and they're cheap to settle in one pass.
Verified, with the contradiction in each:
A3 —
skills/hyperresearch.md:213invariant 2 says "No re-synthesizing";:235says to spawn the synthesizer for "ONE compression pass". Scope the invariant to exclude the compression pass.A4 —
skills/hyperresearch-2-width-sweep.md:146tells fetchers "fetch ONLY the URLs in your batch. Do not search for additional URLs", whileskills/hyperresearch.md:224invariant 12 makes citation-chasing MANDATORY andcore/hooks.py:3096tells them to collect leads. Decide whether the batch is closed, and say so in one place.A7 —
hyperresearch-4-loci-analysis.md:121permits zero loci via a justifiedskip_loci;hyperresearch-7-source-tensions.md:89hardcodes an exit criterion of "3–7 tensions" with no zero path.A11 —
hyperresearch-12-critics.md:60says "If one fails, you can proceed with the partial set", then:66requires all four findings files, andcore/runs.py:456-465hard-checks all four filenames. The permitted failure mode produces an unshippable run with no documented remedy.A15 —
hyperresearch-1-decompose.md:128saysshorthas no Opinionated Synthesis section;hyperresearch-11-synthesize.md:118hardcodes that heading into the outline template.B1 —
hyperresearch-1-decompose.md:104says "Do NOT include wrapper-contract requirements here", and the same file's own example at:75-77includes one.B15 —
hyperresearch-16-readability-audit.md:62says to write recommendations as a JSON array; the agent's schema atcore/hooks.py:2612-2645is an object withrecommendationsandsummarykeys.B16 —
core/hooks.py:1556tells the polish auditor to strip YAML frontmatter unconditionally;:1585-1601tells it to fix those fields in place if a wrapper requires them. The spawn contract athyperresearch-15-polish.md:58-63passes onlydraft_pathandpolish_log_path, so the agent is asked to branch on a contract it never receives.B24 —
hyperresearch-16-readability-audit.md:162declares "Pipeline complete… You're done" before the ship gate, whichskills/hyperresearch.md:209and invariant 14 run afterwards.A8 —
hyperresearch-1-5-chapter-partition.md:5andcore/profiles.py:315setchapters: (4,10);:36of the same skill describes recording 1 chapter. This one is a documented escape hatch stated as a conflict — probably just needs a sentence saying so.Also worth folding in while touching this area:
hyperresearch-14-5-cite-check.md:17's one-line Goal claims exhaustive citation verification, while the frontmatter at:6-7and the body at:36correctly disclose sampling. Wording only, but it's the line most people read.Unrelated small bug found in the same file:
core/citecheck.py:180computeskeep_every = round(1 / 0.6) = 2, so a configuredsample_rateof 0.6 actually samples 50%.