{"record":{"id":"0937c72890db5359","repo":"jdx/mise","slug":"cached-rustc-action-descriptor-does-not-match-the","errorCode":null,"errorMessage":"cached rustc action descriptor does not match the invocation","messagePattern":"cached rustc action descriptor does not match the invocation","errorType":"exception","errorClass":"eyre::Report","httpStatus":null,"severity":"error","filePath":"src/cache/rustc.rs","lineNumber":301,"sourceCode":"        _ => bail!(\"cache agent returned an unexpected action lookup response\"),\n    };\n    if result.version != 1 || result.action != action.digest {\n        bail!(\"cached rustc action result has an invalid identity\");\n    }\n    let metadata_digest = result\n        .metadata\n        .ok_or_else(|| eyre::eyre!(\"cached rustc action result has no metadata\"))?;\n    let output_root_digest = result\n        .output_root\n        .ok_or_else(|| eyre::eyre!(\"cached rustc action result has no output root\"))?;\n    let roots = find_blobs(&[\n        action.digest.clone(),\n        metadata_digest.clone(),\n        output_root_digest.clone(),\n    ])?;\n    let cached_action = read_verified_blob(&roots[0], &action.digest, \"action descriptor\")?;\n    if cached_action != action.bytes {\n        bail!(\"cached rustc action descriptor does not match the invocation\");\n    }\n    let metadata: RustcMetadata =\n        read_canonical_blob(&roots[1], &metadata_digest, \"rustc metadata\")?;\n    if metadata.version != 1 || metadata.kind != \"rustc\" {\n        bail!(\"cached rustc metadata is unsupported\");\n    }\n    let directory: CacheDirectory =\n        read_canonical_blob(&roots[2], &output_root_digest, \"output directory\")?;\n    let files = validated_outputs(directory, outputs)?;\n    let cached_outputs = files\n        .iter()\n        .map(|(node, destination)| CachedOutput {\n            path: destination.clone(),\n            digest: node.digest.clone(),\n            mode: node.mode,\n        })\n        .collect();\n    let restored_output_files = files.len().try_into().unwrap_or(u64::MAX);","sourceCodeStart":283,"sourceCodeEnd":319,"githubUrl":"https://github.com/jdx/mise/blob/9dcfcaa0dc8747a2577d3270b69bb9d8313b2807/src/cache/rustc.rs#L283-L319","documentation":"The wrapper fetches the action-descriptor blob and requires it to be byte-identical to the action it just recomputed for this invocation. Equal digests with different bytes means non-deterministic serialization or a colliding/corrupted blob — either way the entry cannot be trusted and the wrapper bails (src/cache/rustc.rs:301).","triggerScenarios":"Action serialization changed between the recording and replaying mise builds (same digest recipe but different byte layout), or the blob store returned corrupted/mismatched bytes for the digest.","commonSituations":"mise upgrade altering canonical action bytes; disk corruption or partial writes in the blob store; two mise versions sharing one agent.","solutions":["Clear the blob/result cache and rebuild so descriptors are re-recorded with the current serializer","Confirm only one mise version is in use for agent and wrapper","If it recurs on a single version, capture the mismatch and report it — deterministic serialization is a mise invariant"],"exampleFix":null,"handlingStrategy":"fallback","validationCode":null,"typeGuard":null,"tryCatchPattern":"# Descriptor mismatch => corrupted/stale store: clear blobs, rebuild\nif grep -q 'action descriptor does not match the invocation' build.log; then\n  rm -rf \"$MISE_CACHE_STAGING_DIR\"; cargo build\nfi","preventionTips":["Include the mise version in cache keys/stores","Clear caches after serializer-affecting upgrades","Report deterministic-serialization mismatches — they are bugs"],"tags":["mise","rustc-cache","cache-corruption","digest-mismatch","serialization"],"backgroundTag":"cache-corruption","analyzedSha":"9dcfcaa0dc8747a2577d3270b69bb9d8313b2807","analyzedAt":"2026-08-17T14:28:50.624Z","schemaVersion":2},"datasetVersion":"2026-08-21T13:17:26.733Z"}