{"record":{"id":"af26aee0a212c605","repo":"binarywang/WxJava","slug":"aes","errorCode":null,"errorMessage":"AES解密失败！","messagePattern":"AES解密失败！","errorType":"exception","errorClass":"RuntimeException","httpStatus":null,"severity":"error","filePath":"weixin-java-channel/src/main/java/me/chanjar/weixin/channel/util/WxChCryptUtils.java","lineNumber":47,"sourceCode":"\n  /**\n   * AES解密\n   *\n   * @param sessionKey    session_key\n   * @param encryptedData 消息密文\n   * @param ivStr         iv字符串\n   */\n  public static String decrypt(String sessionKey, String encryptedData, String ivStr) {\n    try {\n      AlgorithmParameters params = AlgorithmParameters.getInstance(\"AES\");\n      params.init(new IvParameterSpec(Base64.decodeBase64(ivStr)));\n\n      Cipher cipher = Cipher.getInstance(\"AES/CBC/NoPadding\");\n      cipher.init(Cipher.DECRYPT_MODE, new SecretKeySpec(Base64.decodeBase64(sessionKey), \"AES\"), params);\n\n      return new String(PKCS7Encoder.decode(cipher.doFinal(Base64.decodeBase64(encryptedData))), UTF_8);\n    } catch (Exception e) {\n      throw new RuntimeException(\"AES解密失败！\", e);\n    }\n  }\n\n}\n","sourceCodeStart":29,"sourceCodeEnd":52,"githubUrl":"https://github.com/binarywang/WxJava/blob/1c43293a3c2c9d7e91304b6d037fb017f680d0c6/weixin-java-channel/src/main/java/me/chanjar/weixin/channel/util/WxChCryptUtils.java#L29-L52","documentation":"WxChCryptUtils.decrypt performs AES/CBC/NoPadding decryption of WeChat-encrypted data (e.g. channel/miniapp user encryptedData) using a sessionKey and iv, both Base64-decoded. Any failure in key derivation, IV init, ciphering, or Base64 decoding is caught and rethrown as a generic RuntimeException. The original cause is attached as the exception's cause.","triggerScenarios":"Calling decrypt with a wrong/stale sessionKey, a mismatched iv, a malformed (non-Base64 or truncated) encryptedData, or data encrypted with a different algorithm/padding scheme.","commonSituations":"sessionKey expired because a new code2Session login occurred (keys are single-use per login); iv or encryptedData copied with truncation or encoding corruption; Unicode/percent-encoding mangled the payload in transit.","solutions":["Re-fetch a fresh sessionKey via the login (code2Session/jscode2session) flow immediately before decrypting — keys invalidate on each new login.","Verify encryptedData and iv are raw Base64 strings and have not been URL/JSON-escaped twice.","Inspect the wrapped cause (e.getCause()) to distinguish BadPaddingException / InvalidKeyException / decoding errors.","Ensure the encryptedData and iv come from the same WeChat callback/login response (they are paired)."],"exampleFix":"// before — stale key reused\nString plain = WxChCryptUtils.decrypt(oldSessionKey, encryptedData, iv);\n\n// after — fresh key per login\nWxMiniacppSessionResult s = service.jsCode2Session(jsCode);\nString plain = WxChCryptUtils.decrypt(s.getSessionKey(), encryptedData, iv);","handlingStrategy":"validation","validationCode":"if (sessionKey == null || ivStr == null || encryptedData == null\n    || !Base64.isBase64(sessionKey) || !Base64.isBase64(ivStr)) {\n  throw new IllegalArgumentException(\"sessionKey/iv/encryptedData missing or not Base64\");\n}\n// then decrypt","typeGuard":null,"tryCatchPattern":"try {\n  String plain = WxChCryptUtils.decrypt(sessionKey, encryptedData, iv);\n} catch (RuntimeException e) {\n  // e.getCause() reveals BadPaddingException / InvalidKeyException etc.\n  log.warn(\"AES decrypt failed, sessionKey may be stale\", e.getCause());\n  // re-fetch sessionKey and retry once, or fail the flow\n}","preventionTips":["Fetch a fresh sessionKey via code2Session immediately before each decrypt — keys invalidate on new logins.","Validate that encryptedData and iv are raw Base64 and paired from the same login response.","Log e.getCause() to distinguish wrong-key vs corrupted-data failures."],"tags":["crypto","aes","decryption","session-key","channel"],"backgroundTag":null,"analyzedSha":"1c43293a3c2c9d7e91304b6d037fb017f680d0c6","analyzedAt":"2026-08-14T02:29:11.060Z","schemaVersion":2},"datasetVersion":"2026-08-14T05:17:29.042Z"}