Tasks: clean up after a work item is closed
Derived from the approved design.md and testing-plan.md.
mermaid
flowchart LR
T1["1 · keyword"] --> T2["2 · cleanup.py"]
T2 --> T3["3 · dispatcher seams"]
T3 --> T4["4 · control + close paths"]
T5["5 · graph node"] --> T6["6 · Runtime.cleanup"]
T6 --> T7["7 · GraphLink.on_cleanup"]
T7 --> T3
T4 --> T8["8 · CLI · HTTP · MCP"]
T8 --> T9["9 · schemas + config"]
T9 --> T10["10 · docs + capability docs"]Task list
[x] 1. Declare the
cleanupcontrol commandCLEANUP = "cleanup"incli/the_loop/control.py; add toCOMMANDS,DEFAULT_KEYWORDS("the-loop cleanup") and a newTEARDOWN_COMMANDS- Keep it out of
_ARMING_COMMANDS,SPAWN_COMMANDSandGRAPH_COMMANDS - Depends on: none
- Requirements: R2.1, R2.4
- Test: T1 —
pytest cli/tests/test_control.py -k cleanup(red→green)
[x] 2.
cli/the_loop/cleanup.py— the order and the reportHARNESS/TMUX/WORKSPACE/SESSION/PIECES,CleanupOutcome,cleanup_work_item(...)with the two injected seams- Never touches
WorkItemStore; per-piece error isolation; dry run - Depends on: 1
- Requirements: R1.1–R1.6, R4.1–R4.3, R6.1
- Test: T1 —
pytest cli/tests/test_cleanup.py(red→green)
[x] 3. Dispatcher seams:
_end_endpointand_remove_checkout- Unconditional harness-terminate + tmux kill for one endpoint; unconditional
Workspace.cleanupderived from the ref alone Dispatcher.cleanup_work_item(...)composing graph move →cleanup_work_item- Depends on: 2, 7
- Requirements: R1.1, R1.2, R4.2, R5.2
- Test: T2 —
pytest cli/tests/test_cleanup_integration.py(red→green)
- Unconditional harness-terminate + tmux kill for one endpoint; unconditional
[x] 4. Wire the two ingress triggers
_apply_control: aCLEANUPbranch that runs without a live session- The close path: cleanup when
event_actoris authorized, else emitcleanup.deferred - Depends on: 3
- Requirements: R2.2, R2.3, R3.1–R3.4, R6.2
- Test: T2, T8 —
pytest cli/tests/test_cleanup_integration.py(red→green)
[x] 5. The
cleanupnode in the two work-item-level loopspdlc-work-item-loop.yamlandpdlc-contribution-loop.yaml; notpdlc-pr-loop.yaml- Depends on: none
- Requirements: R5.1
- Test: T12 —
pytest cli/tests/test_graph_cleanup.py(red→green)
[x] 6.
Runtime.cleanup(work_item_id, ref, reason)- Enters the node, saves before the entry chain, emits
graph.cleaned;Nonewhen the graph has nocleanupnode, no state, or the pointer is already there - Depends on: 5
- Requirements: R5.2, R5.4
- Test: T12 —
pytest cli/tests/test_graph_cleanup.py(red→green)
- Enters the node, saves before the entry chain, emits
[x] 7.
GraphLink.on_cleanup+_guarded(require_started=False)- The one caller that skips the
_awaiting_startgate, documented in place - Depends on: 6
- Requirements: R5.2, R5.4
- Test: T12 —
pytest cli/tests/test_graph_cleanup.py -k link(red→green)
- The one caller that skips the
[x] 8. The operator surfaces
core.sessions:cleanupinCONTROL_VERBSand an_applybranchcommands/sessions_cmd.py: thecleanupsubparser and its help- HTTP/MCP inherit the verb through
control_session - Depends on: 4
- Requirements: R2.5
- Test: T3 —
pytest cli/tests/test_core_sessions.py cli/tests/test_api_routers_integration.py(red→green)
[x] 9. Schemas and shipped config
.the-loop/cli-config.schema.json:routing.control.keywords.cleanup.the-loop/harness-config.schema.json:cleanupinworkflow.phases.the-loop/harness-config.yaml, both templates underskills/the-loop/templates/- Depends on: 8
- Requirements: R2.1, R5.3
- Test: T13 —
pytest cli/tests/test_harness_gate.py cli/tests/test_docs_parity.py(red→green)
[x] 10. Documentation and capability docs
docs/config/cli/routing-options.md,docs/cli/commands/sessions.md,docs/cli/state.mddocs/capabilities/interactive-sessions.md,webhook-triggers.md,process-graph.mdskills/the-loop/reference/automation.md,workflow.md;README.md- Depends on: 9
- Requirements: R2.5, R5.3, R6.1
- Test: T13 —
pytest cli/tests/test_docs_parity.py(red→green)