{"record":{"id":"311525fd02698203","repo":"Hmbown/CodeWhale","slug":"timeout-should-preserve-checkpoint","errorCode":null,"errorMessage":"timeout should preserve checkpoint","messagePattern":"timeout should preserve checkpoint","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/tui/src/tools/subagent/tests.rs","lineNumber":9034,"sourceCode":"        .expect(\"sub-agent task should finish\");\n    assert_eq!(\n        calls.load(Ordering::SeqCst),\n        SUBAGENT_API_TIMEOUT_MAX_RETRIES.saturating_add(1) as usize,\n        \"needs-input interruption must not park for continuation; the API call \\\n         is retried up to the timeout-retry budget, then stops\"\n    );\n\n    let interrupted = {\n        let manager = manager.read().await;\n        manager\n            .get_result(&agent_id)\n            .expect(\"agent should stay registered\")\n    };\n    assert!(matches!(interrupted.status, SubAgentStatus::Interrupted(_)));\n    let checkpoint = interrupted\n        .checkpoint\n        .as_ref()\n        .expect(\"timeout should preserve checkpoint\");\n    assert_eq!(checkpoint.reason, \"api_timeout\");\n    assert!(checkpoint.continuable);\n    assert_eq!(checkpoint.steps_taken, 1);\n    assert!(\n        checkpoint\n            .messages\n            .iter()\n            .any(|message| message_text(message).contains(\"Inspect checkpoint behavior\")),\n        \"checkpoint should preserve local child prompt: {checkpoint:?}\"\n    );\n    assert!(interrupted.needs_input.is_some());\n\n    let ctx = runtime.context.clone();\n    let worker_record = {\n        let manager = manager.read().await;\n        manager.get_worker_record(&agent_id)\n    };\n    let projection =","sourceCodeStart":9016,"sourceCodeEnd":9052,"githubUrl":"https://github.com/Hmbown/CodeWhale/blob/433685b2024e7bc4c99e1e2e326bcad39b4d9d65/crates/tui/src/tools/subagent/tests.rs#L9016-L9052","documentation":"Panic from `.expect(\"timeout should preserve checkpoint\")`: the Interrupted SubAgentResult has `checkpoint: None`. An API timeout must snapshot conversation state into a continuable checkpoint (reason \"api_timeout\", continuable true, steps_taken 1), and this assert shows no checkpoint was captured.","triggerScenarios":"The API-timeout interruption path completes without building/persisting a checkpoint on the result, or the checkpoint field is cleared before the result is stored.","commonSituations":"Refactor moving checkpoint construction to a path not taken on timeouts; checkpoint dropped during status transition to Interrupted; steps counter reset before snapshot.","solutions":["Ensure the timeout branch builds a checkpoint with reason \"api_timeout\" and continuable=true before storing the result","Check the Interrupted status transition doesn't clear the checkpoint field","Verify the step counter is incremented before the checkpoint snapshot is taken","Trace where SubAgentResult.checkpoint is set and confirm the timeout path reaches it"],"exampleFix":"// before\n.expect(\"timeout should preserve checkpoint\")\n// after\n.unwrap_or_else(|| panic!(\"Interrupted result has no checkpoint; status={:?}\", interrupted.status))","handlingStrategy":"type-guard","validationCode":null,"typeGuard":"fn preserved_checkpoint(r: &SubAgentResult) -> Option<&Checkpoint> {\n    r.checkpoint.as_ref().filter(|c| c.continuable)\n}","tryCatchPattern":"let checkpoint = interrupted.checkpoint.as_ref()\n    .unwrap_or_else(|| panic!(\"checkpoint lost on api_timeout interruption\"));","preventionTips":["Construct the checkpoint in the same function that sets Interrupted status","Assert checkpoint presence invariants at the manager boundary, not only in tests","Keep checkpoint fields (reason, continuable, steps) immutable once built"],"tags":["rust","subagent","checkpoint","continuity"],"backgroundTag":"missing-required-config-field","analyzedSha":"433685b2024e7bc4c99e1e2e326bcad39b4d9d65","analyzedAt":"2026-09-15T12:24:24.634Z","contentChangedAt":"2026-09-15T12:24:24.634Z","schemaVersion":2},"datasetVersion":"2026-09-22T01:17:13.364Z"}