{"record":{"id":"fd3a0e613370dd79","repo":"nikivdev/code","slug":"invalid-sealer-id-prefix","errorCode":null,"errorMessage":"invalid sealer id prefix","messagePattern":"invalid sealer id prefix","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"src/sealer_crypto.rs","lineNumber":95,"sourceCode":"}\n\nfn decode_secret(value: &str) -> Result<[u8; 32]> {\n    let encoded = value\n        .strip_prefix(SECRET_PREFIX)\n        .ok_or_else(|| anyhow::anyhow!(\"invalid sealer secret prefix\"))?;\n    let bytes = bs58::decode(encoded)\n        .into_vec()\n        .map_err(|e| anyhow::anyhow!(\"invalid base58 secret: {e}\"))?;\n    bytes\n        .as_slice()\n        .try_into()\n        .map_err(|_| anyhow::anyhow!(\"invalid secret key length\"))\n}\n\nfn decode_id(value: &str) -> Result<[u8; 32]> {\n    let encoded = value\n        .strip_prefix(ID_PREFIX)\n        .ok_or_else(|| anyhow::anyhow!(\"invalid sealer id prefix\"))?;\n    let bytes = bs58::decode(encoded)\n        .into_vec()\n        .map_err(|e| anyhow::anyhow!(\"invalid base58 id: {e}\"))?;\n    bytes\n        .as_slice()\n        .try_into()\n        .map_err(|_| anyhow::anyhow!(\"invalid public key length\"))\n}\n\nfn derive_nonce(nonce_material: &[u8]) -> [u8; 24] {\n    let hash = blake3::hash(nonce_material);\n    let mut nonce = [0u8; 24];\n    nonce.copy_from_slice(&hash.as_bytes()[..24]);\n    nonce\n}\n","sourceCodeStart":77,"sourceCodeEnd":111,"githubUrl":"https://github.com/nikivdev/code/blob/a747e741ae92c09071d0ae946ab48488adcff1ce/src/sealer_crypto.rs#L77-L111","documentation":"decode_id strips the \"sealer_z\" prefix from a sealer ID string before base58-decoding the embedded 32-byte public key. Called by seal and unseal on sender/recipient id arguments, it throws this error when the value lacks the \"sealer_z\" prefix — typically a secret was passed where an ID was expected, or the ID was truncated.","triggerScenarios":"Calling seal or unseal with a sender/recipient id argument not starting with \"sealer_z\" — e.g. passing a sealerSecret_z string, a bare base58 public key, or an empty/placeholder id.","commonSituations":"Swapping id and secret variables in config, storing the public key without its prefix, or referencing a teammate by secret instead of their published sealer id.","solutions":["Pass the sealer ID exactly as published, beginning with \"sealer_z\".","If you have the raw 32-byte public key, encode as \"sealer_z\" + base58(bytes).","Check you are not passing the sealer secret (prefix sealerSecret_z) where the id belongs.","Re-fetch the teammate's sealer id from the shared source if it was truncated."],"exampleFix":"// before: secret passed as id\nlet id = decode_id(\"sealerSecret_zAbc...\")?;\n// after: actual sealer id\nlet id = decode_id(\"sealer_zDef456...\")?;","handlingStrategy":"validation","validationCode":"fn require_prefixed_id(s: &str) -> Option<&str> {\n    s.starts_with(\"sealer_z\").then_some(s)\n}","typeGuard":"fn has_id_prefix(s: &str) -> bool {\n    s.starts_with(\"sealer_z\")\n}","tryCatchPattern":"match seal(sender_secret, recipient_id, nonce, msg) {\n    Err(e) if e.to_string().contains(\"invalid sealer id prefix\") => {\n        eprintln!(\"id must start with 'sealer_z' — a secret was likely passed where an id is expected\");\n        return Err(e);\n    }\n    other => other?,\n}","preventionTips":["Publish and share sealer ids only in \"sealer_z...\" form.","Keep id and secret in separate, clearly named variables to avoid swapping them.","Validate prefix at config/CLI-arg parse time before any crypto call.","When distributing public keys, always include the \"sealer_z\" prefix."],"tags":["crypto","prefix","parsing","public-key"],"backgroundTag":"invalid-key-prefix","analyzedSha":"a747e741ae92c09071d0ae946ab48488adcff1ce","analyzedAt":"2026-09-01T22:43:55.719Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}