Skip to content

Implement SPEC-09: relaxation / least-worst under infeasibility (Stage 4)#21

Merged
IanMayo merged 1 commit into
mainfrom
claude/next-spec-12qusu
Jul 13, 2026
Merged

Implement SPEC-09: relaxation / least-worst under infeasibility (Stage 4)#21
IanMayo merged 1 commit into
mainfrom
claude/next-spec-12qusu

Conversation

@IanMayo

@IanMayo IanMayo commented Jul 13, 2026

Copy link
Copy Markdown
Contributor

What & why

Stage 4 of the build plan — least-worst (thesis B live). POST /relax turns an infeasible commitment set into an argument the commander weighs, never an error the machine hides or a scalar it optimises. On the Meridian R3m world (both approaches mined, causeway dropped) no plan satisfies C2, C3 and C4 together; /relax returns the three inclusion-minimal least-worst ways forward, each naming what it gives up.

Research-first (DEC-11 gate)

docs/research/04-relaxation.md is authored before implementation and decides:

  • Formalism = preemptive lexicographic priority over the must/should/prefer tiers, NO numeric weights. Weighted CSP, partial weighted MAX-SAT, and Archimedean goal programming are rejected on honesty grounds (DEC-19), not scale — a numeric sacrifice weight is a ratio the commander never issued. This spends ASSAY-FIND-2 at the build face.
  • Return the inclusion-minimal correction-set frontier, not one optimum (the MCS view of infeasibility) — ranked least-worst-first, the must-sacrifice kept but ranked last (G4: never silence).
  • sacrificed = exactly the violated commitments, grounded in the four-stop scale the reused scorer computes; tight/marginal are risks, not sacrifices.
  • Content-neutral, stated tie-break for same-tier sacrifices (C3/C4 are both should) — because encoding a civil-harm-vs-force-protection ranking into code is the value judgement DEC-19 exists to prevent, in non-numeric clothing.
  • The note also corrects course honestly: the SPEC-08 BASE generator routes clear of the banded regions and cannot enter the mined water, so SPEC-09 authors an R3m-responsive candidate set (route latitude, vignette §8) while the sacrifices stay computed by the scorer (DEC-10).

Changes

Specified via spec-kit (specs/009-relaxation/) and implemented:

  • src/tiers.ts — tier lexicography + inclusion-minimality over sacrifice sets + the stated tie-break (pure, no weights)
  • src/relaxCandidates.ts — authored R3m-responsive candidate plans (routes documented cell-by-cell)
  • src/relax.tsRelaxService (/relax): generate → score (reused ScoreService) → read violated sacrifice sets → inclusion-minimal → rank by tier → cited_in/sacrificed_in edges
  • src/components/s3Cards.ts — the S3 least-worst cards
  • new seam movement types; no schema change (RelaxationReport/RelaxationCandidate/Plan already exist)

Stage-4 exit (verified on Meridian)

/relax over R3m returns three inclusion-minimal least-worst candidates sacrificing C4, C3, C2 — each sacrificed non-empty and computed (re-scoring each plan violates exactly its set; the {C2,C4}/{C3,C4} supersets are inclusion-dropped), the C2 must-sacrifice ranked last but present, the C3/C4 same-tier tie stated in tie_break, every card in command language and traced back via cited_in/sacrificed_in (G3), never empty and never a silent drop (G4).

Invariants

G4 (least-worst, never silence) upheld by the report shape and validation (empty candidates/sacrificed fail validation); G2 (no decimal/verdict-token on the card face; margin in the trace drawer); G3 (complete backward chains); G1 (deterministic over (world stamp, commitment ids, seed, engine)); DEC-19 (ordinal tiers, no weights, stated tie-break).

Testing

  • npm test187 pass (163 baseline + 24 new: 13 tiers, 11 relax)
  • npm run typecheck — clean
  • npm run gallery — the "least-worst, never silence" demo moment renders the three R3m cards from the actual /relax

Register & propagation

No new register decision — the formalism is decided by DEC-19, the report shape by knowledge model §5/§8 and seam §7/§G (G4), the tie-break rule by DEC-19's own "state it explicitly." Batch-propagated in the same change: CLAUDE.md current-phase line, delivery-plan status, gallery.

🤖 Generated with Claude Code


Generated by Claude Code

…e 4)

Research note docs/research/04-relaxation.md (DEC-11 gate) decides the
soft-constraint formalism: preemptive lexicographic priority over the
must/should/prefer tiers with NO numeric weights — weighted CSP / MAX-SAT /
Archimedean goal programming rejected on honesty grounds (DEC-19). /relax
returns the inclusion-minimal correction-set frontier (not one optimum),
ranked least-worst-first with the must-sacrifice kept but ranked last;
`sacrificed` = exactly the `violated` commitments (computed by the reused
SPEC-07 scorer, not authored); a content-neutral, stated tie-break for
same-tier sacrifices; command-language narratives per MDMP / JP 5-0.

The note corrects course honestly: the SPEC-08 BASE generator routes clear
of the banded regions and cannot enter the mined water, so SPEC-09 authors
an R3m-responsive candidate set (route latitude, vignette §8) while the
sacrifices stay computed by the scorer (DEC-10).

SPEC-09 specified via spec-kit (specs/009-relaxation/) and implemented:
- src/tiers.ts — tier lexicography + inclusion-minimality over sacrifice
  sets + stated tie-break (pure, no weights)
- src/relaxCandidates.ts — authored R3m-responsive candidate plans
- src/relax.ts — RelaxService (/relax): generate -> score -> sacrifice ->
  inclusion-minimal -> rank -> cited_in/sacrificed_in edges
- src/components/s3Cards.ts — the least-worst cards
- new seam types; no schema change (RelaxationReport/Candidate/Plan exist)

Stage-4 exit holds on Meridian: /relax over R3m returns three
inclusion-minimal least-worst candidates sacrificing C4, C3, C2 (each
`sacrificed` non-empty, computed — re-scoring each plan violates exactly its
set; the {C2,C4}/{C3,C4} supersets are inclusion-dropped), the C2
must-sacrifice ranked last but present, the C3/C4 same-tier tie stated in
tie_break, every card traced back via cited_in/sacrificed_in (G3), never
empty and never a silent drop (G4).

187 tests pass (24 new), typecheck clean; the "least-worst, never silence"
demo moment renders in the gallery. Batch-propagated: CLAUDE.md current
phase, delivery-plan status, gallery. No new register decision.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0162hYgQuqj5XgzoccFr4fL5
@github-actions

github-actions Bot commented Jul 13, 2026

Copy link
Copy Markdown
PR Preview Action v1.8.1
Preview removed because the pull request was closed.
2026-07-13 18:55 UTC

@IanMayo IanMayo merged commit 036200b into main Jul 13, 2026
3 checks passed
@IanMayo IanMayo deleted the claude/next-spec-12qusu branch July 13, 2026 18:55
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants