{"record":{"id":"30a032d7da61f370","repo":"spacedriveapp/spacedrive","slug":"system-channel-closed-trying-to-resume-not-running","errorCode":null,"errorMessage":"System channel closed trying to resume not running task","messagePattern":"System channel closed trying to resume not running task","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/task-system/src/system.rs","lineNumber":286,"sourceCode":"\t\t\t\tlet first_attempt_worker_id = task_work_table.worker_id();\n\t\t\t\tworkers[first_attempt_worker_id]\n\t\t\t\t\t.resume_task(task_id, tx)\n\t\t\t\t\t.await;\n\t\t\t\tlet res = rx\n\t\t\t\t\t.await\n\t\t\t\t\t.expect(\"Task system channel closed trying to resume not running task\");\n\n\t\t\t\tif matches!(res, Err(SystemError::TaskNotFound(_))) {\n\t\t\t\t\twarn!(\n\t\t\t\t\t\t%first_attempt_worker_id,\n\t\t\t\t\t\t\"Failed the first try to resume a not running task, trying again\",\n\t\t\t\t\t);\n\t\t\t\t\tworkers[task_work_table.worker_id()]\n\t\t\t\t\t\t.resume_task(task_id, ack)\n\t\t\t\t\t\t.await;\n\t\t\t\t} else {\n\t\t\t\t\tack.send(res)\n\t\t\t\t\t\t.expect(\"System channel closed trying to resume not running task\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t.in_current_span(),\n\t);\n\ttrace!(\"Task system resumed task\");\n}\n\n#[instrument(skip(workers, ack, task_work_table))]\nfn dispatch_pause_not_running_task_request<E: RunError>(\n\tworkers: &Arc<Vec<Worker<E>>>,\n\ttask_id: TaskId,\n\ttask_work_table: Arc<TaskWorktable>,\n\tack: oneshot::Sender<Result<(), SystemError>>,\n) {\n\tspawn(\n\t\t{\n\t\t\tlet workers: Arc<Vec<Worker<E>>> = Arc::clone(workers);","sourceCodeStart":268,"sourceCodeEnd":304,"githubUrl":"https://github.com/spacedriveapp/spacedrive/blob/6dfeccf2113039e35f2ce735f945e70dc3e4ea45/crates/task-system/src/system.rs#L268-L304","documentation":"In dispatch_resume_not_running_task_request, after the worker replies, the system forwards the result on the caller's oneshot ack channel. ack.send fails (and the spawned task panics) when the requesting side already dropped its receiver, i.e. the caller of resume went away before the answer arrived. The task-system treats these channels as infallible invariants, so a broken invariant aborts the dispatch task and the resume result is lost.","triggerScenarios":"The caller wrapped resume in a timeout/abort and dropped the future before the ack arrived; client disconnects right after requesting resume of a not-running task; shutdown racing an in-flight resume request.","commonSituations":"UI request with a short timeout cancelling as the system is mid-dispatch; daemon shutdown while task control requests are pending.","solutions":["Check whether the panic occurs only during shutdown/disconnect races: then the lost ack is benign and the caller is already gone","Find code that drops task-control futures early (timeout wrappers, abort handles) and keep them alive until the ack resolves","Patch the task-system to replace these expects with logged send failures: a dead ack receiver is recoverable, not fatal","Look for a preceding worker panic in the logs: worker death cascades into broken channel invariants"],"exampleFix":"// before: expect panics the dispatch task when the caller is gone\nack.send(res).expect(\"System channel closed trying to resume not running task\");\n\n// after: a dropped requester is not fatal\nif ack.send(res).is_err() {\n    warn!(%task_id, \"Resume ack receiver dropped; caller went away\");\n}","handlingStrategy":"validation","validationCode":"// Keep the requesting future alive until the ack arrives; never wrap task control in timeouts\nlet ack_rx = system.resume(task_id); // returns the oneshot receiver\nlet res = ack_rx.await; // hold this to completion — dropping early closes the channel\nassert!(matches!(res, Ok(_)), \"resume must get its ack\");","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Never abort or timeout task-control futures before their ack resolves","Treat 'System channel closed' panics as caller-lifecycle bugs, not worker bugs","Patch consumers of task-system to await acks in the same scope that issues requests"],"tags":["task-system","channel","concurrency","panic"],"backgroundTag":null,"analyzedSha":"6dfeccf2113039e35f2ce735f945e70dc3e4ea45","analyzedAt":"2026-08-16T11:26:17.074Z","schemaVersion":2},"datasetVersion":"2026-08-16T13:17:31.715Z"}