{"record":{"id":"8aeee889bc07e6dd","repo":"usebruno/bruno","slug":"decrypt-failed-invalid-algo","errorCode":null,"errorMessage":"Decrypt failed: Invalid algo","messagePattern":"Decrypt failed: Invalid algo","errorType":"validation","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/bruno-electron/src/utils/encryption.js","lineNumber":149,"sourceCode":"    throw new Error('Decrypt failed: unrecognized string format');\n  }\n  if (str.length === 0) {\n    return '';\n  }\n\n  // Find the index of the first colon\n  const colonIndex = str.indexOf(':');\n\n  if (colonIndex === -1) {\n    throw new Error('Decrypt failed: unrecognized string format');\n  }\n\n  // Extract algo and encryptedString based on the colon index\n  const algo = str.substring(1, colonIndex);\n  const encryptedString = str.substring(colonIndex + 1);\n\n  if ([ELECTRONSAFESTORAGE_ALGO, AES256_ALGO].indexOf(algo) === -1) {\n    throw new Error('Decrypt failed: Invalid algo');\n  }\n\n  if (algo === ELECTRONSAFESTORAGE_ALGO) {\n    if (safeStorage && safeStorage.isEncryptionAvailable()) {\n      return safeStorageDecrypt(encryptedString);\n    } else {\n      return '';\n    }\n  }\n\n  if (algo === AES256_ALGO) {\n    return aes256Decrypt(encryptedString, passkey || null);\n  }\n  throw new Error('Decrypt failed: Invalid algo');\n}\n\nfunction decryptStringSafe(str) {\n  try {","sourceCodeStart":131,"sourceCodeEnd":167,"githubUrl":"https://github.com/usebruno/bruno/blob/9bdd81c7bdc57006e5f5ebffb79321a8d979f712/packages/bruno-electron/src/utils/encryption.js#L131-L167","documentation":"Thrown by decryptString when the algo segment (str.substring(1, colonIndex)) is not '00' (ELECTRONSAFESTORAGE_ALGO) or '01' (AES256_ALGO). The prefix format is `$<algo>:<ciphertext>`; an unknown algo means the value is from an unsupported scheme or the prefix got corrupted.","triggerScenarios":"Value prefixed with an algo code other than '00'/'01' — e.g. a future scheme like '$02:', a hand-edited value, or a value whose leading char was stripped/changed so the algo slice is wrong.","commonSituations":"Version skew (data written by a newer Bruno using an algo this version doesn't recognize); manual edit of the secrets store; off-by-one corruption dropping the leading '$'.","solutions":["Validate the prefix with a regex like /^\\$(00|01):/ before decrypting.","Upgrade Bruno to a version that supports the algo, or re-create the secret in this version.","Use decryptStringSafe to capture and report the unsupported-algo case without crashing."],"exampleFix":"// before\nconst algo = str.substring(1, colonIndex);\nif ([ELECTRONSAFESTORAGE_ALGO, AES256_ALGO].indexOf(algo) === -1) {\n  throw new Error('Decrypt failed: Invalid algo');\n}\n\n// after: caller-side guard\nconst SUPPORTED = /^\\$(00|01):/;\nif (!SUPPORTED.test(stored)) throw new Error('Unsupported ciphertext prefix');\nconst plain = decryptString(stored);","handlingStrategy":"validation","validationCode":"const SUPPORTED = /^\\$(00|01):/;\nif (!SUPPORTED.test(stored)) {\n  throw new Error('Unsupported ciphertext prefix');\n}\nreturn decryptString(stored);","typeGuard":"function isKnownAlgoCipher(str) {\n  return /^\\$(00|01):/.test(String(str));\n}","tryCatchPattern":"try { return decryptString(stored); }\ncatch (err) {\n  if (err.message === 'Decrypt failed: Invalid algo') {\n    // value from a newer/unknown scheme; re-enter the secret\n    return null;\n  }\n  throw err;\n}","preventionTips":["Validate the algo prefix against the supported set before decrypting.","Upgrade Bruno to the version that wrote the value if a new algo appears.","Don't hand-edit the secrets store."],"tags":["encryption","format","version-skew"],"backgroundTag":null,"analyzedSha":"9bdd81c7bdc57006e5f5ebffb79321a8d979f712","analyzedAt":"2026-08-13T04:09:25.751Z","schemaVersion":2},"datasetVersion":"2026-08-13T04:17:16.726Z"}