Classification
- Change type: enhancement / remediation evidence contract
- Priority:P1
- Expected value: very high — turns Fix Arm output into one reviewable, machine-checkable proof artifact
- Estimated effort: medium
- Implementation risk: medium — false claims of
fixed would corrupt audit truth - Recommendation:YES, strong product improvement after finding identity v2 is stable
- Depends on:
PhysShell/Own.NET#266 - Consumes derived lifecycle/evidence state from:
PhysShell/Own.NET#268 - Consumes agent evidence from:
PhysShell/007#42 and replay verification from PhysShell/007#43 when available
Problem
The Fix Arm already has the correct safety shape:
select -> dry-run -> apply -> re-audit -> reject regression -> tier gate
It also records a useful coverage ledger and reverts rejected/no-effect patches. However, the evidence that a remediation succeeded is spread across several artifacts:
- original finding(s);
- proposed diff;
- re-audit output;
- introduced/removed finding comparison;
- build/test logs;
- runtime evidence where available;
- optional agent run records;
- human review disposition.
A reviewer currently has to reconstruct the argument manually. Humans can do that, naturally, because apparently archaeology is now part of code review.
Goal
Emit one versioned, deterministic fix-proof.json for every attempted fix, including accepted, rejected, no-effect, unfixable and operational-error outcomes.
The proof packet must answer:
Which exact occurrence was targeted?
What evidence justified the target?
What patch was attempted?
Did the target disappear under comparable analysis inputs?
Did a semantic successor remain?
Were new findings introduced?
Which build/tests/runtime checks ran?
Was the agent execution replay-verified?
What remains unknown?
Proposed contract
Exact names are reviewable; the information must remain explicit.
{
"schema": 1,
"proof_id": "...",
"status": "ACCEPTED | REVIEW | REJECTED | NO_EFFECT | UNFIXABLE | ERROR",
"target": {
"pattern_id": "...",
"occurrence_id": "...",
"lineage_id": "...",
"rule": "OWN001",
"before_evidence_digest": "..."
},
"patch": {
"digest": "...",
"changed_files": [],
"changed_symbols": [],
"diff_artifact": "..."
},
"verification": {
"target_removed": true,
"semantic_successor_present": false,
"introduced_occurrences": [],
"build": {},
"tests": [],
"runtime_witness": null,
"reaudit_comparability": {}
},
"agent_run": {
"run_id": null,
"action_id": null,
"replay_report_digest": null
},
"provenance": {
"target_commit": "...",
"own_version": "...",
"ownaudit_version": "...",
"config_digest": "...",
"input_digest": "..."
},
"limitations": []
}Required semantics
target_removed is matched by occurrence/lineage identity, not (rule, basename, nearest line) once #266 is available.- Disappearance under a changed analyzer/config/input is not presented as a verified fix.
- A target disappearing while a semantic successor remains is not accepted as fixed.
- Any introduced actionable occurrence remains explicit and rejects automatic acceptance.
- Missing build/test/runtime checks remain
unknown/not-run; they are never treated as pass. - An agent process exiting zero is not remediation proof.
- Human review is an explicit disposition layered over machine evidence, not a rewritten machine verdict.
- Rejected/no-effect attempts still produce proof packets so failed strategies do not vanish from evaluation data.
Integration with the current Fix Arm
run_fix() should return or construct a proof model in addition to the existing FixResult/ledger output.
Suggested output layout:
artifacts/fix-runs/<proof-id>/
fix-proof.json
diff.patch
before-findings.json
after-findings.json
verification/
build.json
tests.json
runtime.json
logs/
The packet should reference large artifacts by relative path + digest rather than embedding unbounded logs.
Required controls
- Target removed, no new findings, comparable config, tests pass → accepted/review according to tier.
- Target removed but a new finding appears → rejected.
- Target line moves but lineage remains → no false remove/add pair.
- One repeated occurrence is fixed and another remains → only the targeted occurrence changes state.
- Re-audit uses a different config digest → inconclusive/rejected, not fixed.
- Target remains →
NO_EFFECT with reverted patch. - Applier throws after modifying the tree → rollback evidence and
ERROR proof retained. - Agent claims success but re-audit disagrees → machine verdict wins; claim remains provenance only.
- Runtime witness is unavailable → explicit limitation, never synthetic pass.
- Re-rendering the same normalized inputs produces byte-stable proof JSON.
Acceptance
Non-goals
- No new fix engine.
- No AI judge deciding whether a patch is correct.
- No automatic acceptance of T4 fixes.
- No replacement of the Finding Evidence Ledger.
- No requirement that every finding has a runtime witness.
- No storage of secrets or unbounded agent stdout in the proof JSON.
Classification
fixedwould corrupt audit truthPhysShell/Own.NET#266PhysShell/Own.NET#268PhysShell/007#42and replay verification fromPhysShell/007#43when availableProblem
The Fix Arm already has the correct safety shape:
It also records a useful coverage ledger and reverts rejected/no-effect patches. However, the evidence that a remediation succeeded is spread across several artifacts:
A reviewer currently has to reconstruct the argument manually. Humans can do that, naturally, because apparently archaeology is now part of code review.
Goal
Emit one versioned, deterministic
fix-proof.jsonfor every attempted fix, including accepted, rejected, no-effect, unfixable and operational-error outcomes.The proof packet must answer:
Proposed contract
Exact names are reviewable; the information must remain explicit.
{ "schema": 1, "proof_id": "...", "status": "ACCEPTED | REVIEW | REJECTED | NO_EFFECT | UNFIXABLE | ERROR", "target": { "pattern_id": "...", "occurrence_id": "...", "lineage_id": "...", "rule": "OWN001", "before_evidence_digest": "..." }, "patch": { "digest": "...", "changed_files": [], "changed_symbols": [], "diff_artifact": "..." }, "verification": { "target_removed": true, "semantic_successor_present": false, "introduced_occurrences": [], "build": {}, "tests": [], "runtime_witness": null, "reaudit_comparability": {} }, "agent_run": { "run_id": null, "action_id": null, "replay_report_digest": null }, "provenance": { "target_commit": "...", "own_version": "...", "ownaudit_version": "...", "config_digest": "...", "input_digest": "..." }, "limitations": [] }Required semantics
target_removedis matched by occurrence/lineage identity, not(rule, basename, nearest line)once #266 is available.unknown/not-run; they are never treated as pass.Integration with the current Fix Arm
run_fix()should return or construct a proof model in addition to the existingFixResult/ledger output.Suggested output layout:
The packet should reference large artifacts by relative path + digest rather than embedding unbounded logs.
Required controls
NO_EFFECTwith reverted patch.ERRORproof retained.Acceptance
fix-proof.jsonschema is documented and implemented.Non-goals