Phase 6 — Best-practices design¶
Design principles¶
- Functional core, imperative shell. Transition reducers stay pure; graph runners do I/O.
- Stable contracts at phase boundaries. Phase 6.5 depends on
VulnRemediationSut, not onbuild_vuln_loop. - Plugin-local behavior, shared ports. Graph topology is owned by the vuln-remediation plugin; reusable services stay under
src/codegenie/. - Illegal states are unrepresentable. Ledger state, node outcomes, and resume inputs use Pydantic discriminated unions.
- Tests mirror the graph. Unit tests cover reducers and transition tables; integration tests cover kill/resume and HITL interruption.
Proposed public surface¶
class VulnRemediationSut(Protocol):
async def run_case(self, request: VulnRemediationCase) -> VulnRemediationResult: ...
def digest(self) -> SutDigest: ...
run_case is the stable harness-facing operation. The default implementation may wrap a LangGraph builder, but that builder is private to Phase 6.
Why this fits the repo¶
- Mirrors the decorator/registry patterns already used by probes and task classes.
- Keeps new behavior additive under the narrowed extension-by-addition rule from production ADR-0039.
- Gives Phase 6.5 a real contract to test against before Phase 7 adds a second task class.