Trust Model · optional · deletable
Extension Lanes
How optional integrations stay optional.
Optional power — live judges, trace backends, result exporters — must never contaminate the required path. Lanes solve that with a metadata-only framework: a lane declares what it does, and its real code is imported only when a host opts in. No required import ever loads a lane or a provider SDK.
What a lane declares
An ExtensionLane is metadata: a name and purpose, the
port it attaches to, the module and factory that build
its adapter, a boundary statement (what stays isolated), a
deletion_rule (what removing it leaves intact), and any prerequisites.
The LaneRegistry lists lanes without importing any of them; its
resolve() is the only place a lane’s concrete code is lazily imported.
A lane can run, skip, or block — never score
LaneResult status | Meaning |
|---|---|
| ran | The lane executed and produced evidence or output. |
| skipped | A prerequisite was missing — the lane stepped aside without failing the run. |
| blocked | The lane could not complete; it reports diagnostics, not a verdict. |
A LaneResult carries diagnostics but no score and no verdict. A
missing prerequisite raises MissingPrerequisite, which skips the lane — it
never fails the run. So a missing API key or backend degrades gracefully instead of breaking CI.
The built-in lanes
| Lane | Port | What it adds |
|---|---|---|
live-judge | JudgeModel | An HTTPS judge call via stdlib urllib — no provider SDK. |
trace-backend | TraceSource | Reads traces from a configured backend file. |
score-sink-export | ScoreSink | Publishes a read-only Scorecard export to a local dir. |
async-observation | TraceSource | Reads an async recording — observes, never orchestrates. |
deletion_rule states what removing its file leaves working — e.g.
deleting adapters/judge_live.py leaves the required judge suite green.
“Opt-in and deletable” is verified, not asserted: the required suite must pass with every lane
removed.