* feat(kernel): route proportional-decrease through construction proposals * docs: clarify PR #837 scope in lookback
42 lines
3.1 KiB
Markdown
42 lines
3.1 KiB
Markdown
# PR #837 Lookback — feat(kernel): route proportional-decrease through construction proposals
|
|
|
|
This lookback documents the design rationale, implementation details, and verification results for routing the proportional-decrease diagnostic path through typed `ConstructionProposal` objects.
|
|
|
|
## Rationale & Design Choices
|
|
|
|
### 1. Attaching `proposals` to `ProblemFrame`
|
|
We introduced the `proposals` field (`tuple[ConstructionProposal, ...]`) directly on the `ProblemFrame` class. This allows the frame representation to carry its candidate construction traces, linking surface evidence to the construction-affordance catalog in a self-contained manner.
|
|
|
|
### 2. Integration in `build_problem_frame`
|
|
To avoid circular imports and keep `ProblemFrameBuilder` clean, the proposals are attached in `build_problem_frame()` via a two-pass assembly:
|
|
1. Build the initial `ProblemFrame` with basic attributes.
|
|
2. Call `assess_contracts()` on the initial frame to retrieve `ContractAssessment` objects.
|
|
3. For each assessment whose candidate organ maps to a catalog family (via `get_contract_family_id()`), construct a `ConstructionProposal` via `make_proposal()`.
|
|
4. Recreate the `ProblemFrame` with the proposals tuple attached using `dataclasses.replace()`.
|
|
|
|
### 3. Exposing Public Accessors
|
|
We added the public helper `get_contract_family_id(candidate_organ: str) -> str | None` in `generate/problem_frame_contracts.py`. This avoids exposing the private mapping dict `_CONTRACT_REGISTRY` to external modules or test suites.
|
|
|
|
### 4. Scope & Boundary Clarification
|
|
PR #837 attaches assessment-backed proposal traces to `ProblemFrame` as a diagnostic trace. It does *not* make construction proposals drive relation binding or contract assessment, which remain decoupled at this stage.
|
|
|
|
|
|
## Tests Added
|
|
|
|
We introduced a dedicated test file `tests/test_proportional_decrease_proposal.py` covering:
|
|
- **Proposal trace existence**: Verifies that a `proportional_change.decrease_to_fraction` proposal is generated for proportional-decrease cases.
|
|
- **Exact evidence spans**: Asserts that proposal evidence spans correctly slice the original problem text.
|
|
- **Catalog alignment**: Verifies the proposal family ID, relation type, and candidate organ align with the catalog definition using public accessors.
|
|
- **Diagnostic-only constraints**: Validates that the underlying family has `diagnostic_only=True` and `serving_allowed=False`.
|
|
- **Blocked case handling**: Asserts that `FINAL_VALUE_CONFUSER` (a final-value question instead of a decrease-delta question) still produces a proposal trace but has a blocked status (not `"closed"`) and identifies `delta_decrease_target_unbound`.
|
|
- **Confuser exclusion**: Verifies that `AFFINE_CONFUSER` produces no proportional-decrease proposal trace.
|
|
|
|
## Verification Results
|
|
|
|
- All 54 tests pass successfully.
|
|
- Parity of adequacy metrics verified:
|
|
- Train runnable contracts remain `2` (`0005`, `0046`).
|
|
- Holdout runnable contracts remain `0`.
|
|
- Serving counts verified:
|
|
- Train: `30 correct / 20 refused / 0 wrong` (wrong_ids: `[]`)
|
|
- Holdout: `5 correct / 495 refused / 0 wrong` (wrong_ids: `[]`)
|