{"record":{"id":"138a4c7f1b333b97","repo":"astrid-runtime/astrid","slug":"kernel-refused-storage-lifecycle-request-error","errorCode":null,"errorMessage":"kernel refused storage lifecycle request: {error}","messagePattern":"kernel refused storage lifecycle request: (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/astrid-storage-provider-fskit/src/main.rs","lineNumber":301,"sourceCode":"    if !lease_is_live && requested_by != acting_principal {\n        bail!(\"stale mount recovery belongs to another acting principal\");\n    }\n    Ok(())\n}\n\nfn lease_from_response(body: AdminResponseBody) -> Result<StorageMountLeaseV1> {\n    match body {\n        AdminResponseBody::StorageMountLease(lease) => Ok(*lease),\n        AdminResponseBody::Error(error) => bail!(\"kernel refused storage mount: {error}\"),\n        _ => bail!(\"kernel returned an unexpected storage mount response\"),\n    }\n}\n\nfn into_success(body: AdminResponseBody) -> Result<serde_json::Value> {\n    match body {\n        AdminResponseBody::Success(value) => Ok(value),\n        AdminResponseBody::Error(error) => {\n            bail!(\"kernel refused storage lifecycle request: {error}\")\n        },\n        _ => bail!(\"kernel returned an unexpected storage lifecycle response\"),\n    }\n}\n\nfn unmount_status(body: AdminResponseBody) -> Result<bool> {\n    match body {\n        AdminResponseBody::Success(_) => Ok(true),\n        AdminResponseBody::Error(error)\n            if error.contains(\"was not found\") || error.contains(\"expired or revoked\") =>\n        {\n            Ok(false)\n        },\n        AdminResponseBody::Error(error) => {\n            bail!(\"kernel refused storage unmount authorization: {error}\")\n        },\n        _ => bail!(\"kernel returned an unexpected storage unmount response\"),\n    }","sourceCodeStart":283,"sourceCodeEnd":319,"githubUrl":"https://github.com/astrid-runtime/astrid/blob/affd8760f44190dbdfbec23403f4c4b642c33112/crates/astrid-storage-provider-fskit/src/main.rs#L283-L319","documentation":"The fskit provider sent a storage lifecycle admin request (mount, revoke, etc.) to the kernel over the AdminClient, and the kernel replied with an explicit AdminResponseBody::Error. The provider surfaces the kernel's own error text verbatim after a fixed prefix, so the root cause string comes from the kernel side.","triggerScenarios":"into_success() is called on responses to StorageMountRevoke (in unmount) and other lifecycle requests in execute(); any kernel-side rejection — unknown mount id, expired/revoked lease, permission denial, or internal kernel failure — returns AdminResponseBody::Error and is converted here via bail!.","commonSituations":"Unmounting a mount whose lease was already revoked by another process or an admin; stale lease id reused after kernel restart; kernel policy refusing revoke from a non-owning principal; kernel temporarily rejecting requests during shutdown.","solutions":["Read the {error} text embedded in the message; it names the kernel-side cause (e.g. lease 'was not found', 'expired or revoked').","Check whether the mount lease was already revoked or expired (call StorageMountStatus first, or treat 'was not found'/'expired or revoked' as already-unmounted).","Re-run mount to obtain a fresh lease, then retry the lifecycle operation with the new mount_id.","If the refusal is a permission issue, retry as the principal that originally requested the mount (requested_by)."],"exampleFix":"// before: blind revoke that may hit an expired lease\nlet body = client.request(AdminRequestKind::StorageMountRevoke { mount_id }).await?;\ninto_success(body)?;\n// after: skip revoke when the lease is already gone\nlet status = unmount_status(client.request(AdminRequestKind::StorageMountStatus { mount_id }).await?)?;\nif status {\n    into_success(client.request(AdminRequestKind::StorageMountRevoke { mount_id }).await?)?;\n}","handlingStrategy":"try-catch","validationCode":"let status = unmount_status(client.request(AdminRequestKind::StorageMountStatus { mount_id }).await?)?;\nif !status { return Ok(()); } // lease already gone; skip lifecycle call","typeGuard":"fn is_kernel_success(body: &AdminResponseBody) -> bool {\n    matches!(body, AdminResponseBody::Success(_))\n}","tryCatchPattern":"match into_success(body) {\n    Err(e) if e.to_string().contains(\"was not found\") || e.to_string().contains(\"expired or revoked\") => Ok(()),\n    Err(e) => return Err(e),\n    Ok(v) => Ok(v),\n}","preventionTips":["Check lease status (StorageMountStatus) before revoke/mount lifecycle calls.","Treat 'was not found' / 'expired or revoked' as idempotent success.","Always run mount/revoke under the principal that owns the lease.","Keep kernel and provider versions in lockstep to avoid new error strings."],"tags":["kernel","admin-client","storage-mount","lease"],"backgroundTag":"api-error-response","analyzedSha":"affd8760f44190dbdfbec23403f4c4b642c33112","analyzedAt":"2026-09-09T21:28:12.402Z","contentChangedAt":"2026-09-09T21:28:12.402Z","schemaVersion":2},"datasetVersion":"2026-09-14T11:17:12.474Z"}