{"record":{"id":"9a0aebf2ea1c4012","repo":"astrid-runtime/astrid","slug":"installed-capsule-hash-disagreement-installe","errorCode":null,"errorMessage":"installed capsule '{}' hash disagreement: installer={:?}, meta={:?}","messagePattern":"installed capsule '(.+?)' hash disagreement: installer=(.+?), meta=(.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/astrid-cli/src/commands/capsule/install_finish.rs","lineNumber":84,"sourceCode":"    let batch = BATCH_MODE.load(std::sync::atomic::Ordering::Relaxed);\n    let manifest_path = output.target_dir.join(\"Capsule.toml\");\n    let manifest = astrid_capsule::discovery::load_manifest(&manifest_path)\n        .context(\"re-reading manifest for post-install diagnostics\")?;\n\n    let capsule_id = CapsuleId::new(manifest.package.name.clone())?;\n    let meta = super::meta::read_meta(&output.target_dir)\n        .context(\"installed capsule has no readable meta.json\")?;\n    if manifest.package.version != meta.version || output.installed_version != meta.version {\n        bail!(\n            \"installed capsule '{}' version disagreement: manifest={}, meta={}, installer={}\",\n            capsule_id,\n            manifest.package.version,\n            meta.version,\n            output.installed_version\n        );\n    }\n    if output.wasm_hash != meta.wasm_hash {\n        bail!(\n            \"installed capsule '{}' hash disagreement: installer={:?}, meta={:?}\",\n            capsule_id,\n            output.wasm_hash,\n            meta.wasm_hash\n        );\n    }\n\n    let cli_commands: Vec<&astrid_capsule::manifest::CommandDef> = manifest\n        .commands\n        .iter()\n        .filter(|command| command.kind == astrid_core::kernel_api::CommandKind::Cli)\n        .collect();\n    if !cli_commands.is_empty() {\n        eprintln!(\"\\nThis capsule adds CLI commands:\");\n        for command in cli_commands {\n            let description = command.description.as_deref().unwrap_or(\"(no description)\");\n            eprintln!(\n                \"  {} — {description} (provider: {capsule_id})\",","sourceCodeStart":66,"sourceCodeEnd":102,"githubUrl":"https://github.com/astrid-runtime/astrid/blob/affd8760f44190dbdfbec23403f4c4b642c33112/crates/astrid-cli/src/commands/capsule/install_finish.rs#L66-L102","documentation":"After unpacking, finish_install compares the wasm hash reported by the installer (output.wasm_hash) against the hash recorded in the installed meta.json. A mismatch means the deployed wasm does not match what the installer computed/installed, so the install is aborted rather than trusted.","triggerScenarios":"finish_install (via install_from_local_path_for_principal or unpack_via_lib) sees output.wasm_hash != meta.wasm_hash after an install completes.","commonSituations":"The meta.json on disk is stale from a previous install of different wasm; a build tool replaced the wasm after hashing; corruption during unpack or copy; a distribution serving different bytes than hashed.","solutions":["Remove the capsule's target dir (and its meta.json) and re-install from a fresh build so hash and meta are written together.","Rebuild the capsule without touching the wasm between hashing and installation.","If installing from a remote source, re-download and compare the artifact hash; the served artifact may differ from the recorded one.","If it persists across clean installs, file a bug — the installer and meta writer are out of sync."],"exampleFix":"// before\nastrid capsule install ./capsule  # wasm edited after build -> hash mismatch with meta.json\n// after\nrebuild (astrid capsule build), do not modify the wasm, clean the target dir, then:\nastrid capsule install ./capsule","handlingStrategy":"validation","validationCode":"// verify the wasm artifact hash before install finishes\nlet expected = sha256_hex(&wasm_bytes);\nif let Ok(meta) = read_meta(&target_dir) {\n    if Some(&expected) != meta.wasm_hash.as_ref() {\n        std::fs::remove_dir_all(&target_dir)?;\n    }\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Do not modify or re-sign the wasm between build and install.","Install from freshly built artifacts, not cached copies of unknown provenance.","Verify downloads by checksum when installing from remote sources."],"tags":["capsule","install","hash-mismatch","integrity"],"backgroundTag":"checksum-mismatch","analyzedSha":"affd8760f44190dbdfbec23403f4c4b642c33112","analyzedAt":"2026-09-09T21:28:12.402Z","contentChangedAt":"2026-09-09T21:28:12.402Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}