{"record":{"id":"3426c24e85d63690","repo":"binarywang/WxJava","slug":"aes-key-apisignatureaeskey","errorCode":null,"errorMessage":"解析AES KEY失败，请检查ApiSignatureAesKey是否正确","messagePattern":"解析AES KEY失败，请检查ApiSignatureAesKey是否正确","errorType":"exception","errorClass":"SecurityException","httpStatus":null,"severity":"error","filePath":"weixin-java-miniapp/src/main/java/cn/binarywang/wx/miniapp/api/impl/BaseWxMaServiceImpl.java","lineNumber":970,"sourceCode":"    jsonObject.addProperty(\"_n\", rndStr);\n    jsonObject.addProperty(\"_appid\", appId);\n    jsonObject.addProperty(\"_timestamp\", timestamp);\n\n    String plainText = jsonObject.toString();\n    log.debug(\"URL:{}加密前请求数据:{}\", url, plainText);\n    String urlPath;\n    if (url.contains(\"?\")) {\n      urlPath = url.substring(0, url.indexOf(\"?\"));\n    } else {\n      urlPath = url;\n    }\n    String aad = urlPath + \"|\" + appId + \"|\" + timestamp + \"|\" + aesKeySn;\n    byte[] realKey;\n    try {\n      realKey = Base64.getDecoder().decode(aesKey);\n    } catch (Exception ex) {\n      log.error(\"解析AESKEY失败 {}\", aesKey, ex);\n      throw new SecurityException(\"解析AES KEY失败，请检查ApiSignatureAesKey是否正确\", ex);\n    }\n    byte[] realIv = generateRandomBytes(12);\n    byte[] realAad = aad.getBytes(StandardCharsets.UTF_8);\n    byte[] realPlainText = plainText.getBytes(StandardCharsets.UTF_8);\n\n    try {\n      // 加密内容 AES\n      Cipher cipher = Cipher.getInstance(\"AES/GCM/NoPadding\");\n      SecretKeySpec aesKeySpec = new SecretKeySpec(realKey, \"AES\");\n      GCMParameterSpec parameterSpec = new GCMParameterSpec(128, realIv);\n      cipher.init(Cipher.ENCRYPT_MODE, aesKeySpec, parameterSpec);\n      cipher.updateAAD(realAad);\n\n      byte[] ciphertext = cipher.doFinal(realPlainText);\n      byte[] encryptedData = Arrays.copyOfRange(ciphertext, 0, ciphertext.length - 16);\n      byte[] authTag = Arrays.copyOfRange(ciphertext, ciphertext.length - 16, ciphertext.length);\n\n      JsonObject reqData = new JsonObject();","sourceCodeStart":952,"sourceCodeEnd":988,"githubUrl":"https://github.com/binarywang/WxJava/blob/1c43293a3c2c9d7e91304b6d037fb017f680d0c6/weixin-java-miniapp/src/main/java/cn/binarywang/wx/miniapp/api/impl/BaseWxMaServiceImpl.java#L952-L988","documentation":"Thrown as SecurityException when Base64 decoding of the ApiSignatureAesKey fails in postWithSignature(). The AES key is expected to be a valid Base64-encoded 32-byte key. A decode failure means the key string contains invalid characters or has incorrect padding. The exception chains the original cause.","triggerScenarios":"Calling postWithSignature() when apiSignatureAesKey contains characters that are not valid Base64, or the key string has incorrect length/padding.","commonSituations":"Typo in AES key; key copied with extra whitespace, newlines, or PEM headers; key truncated during deployment; wrong encoding (hex instead of Base64).","solutions":["Verify the AES key is valid Base64 and decodes to exactly 32 bytes","Remove any whitespace, PEM headers, or trailing characters from the key string","Re-copy the AES key from the WeChat console ensuring no truncation or encoding changes"],"exampleFix":"// before\nwxMaConfig.setApiSignatureAesKey(\"invalid-key!!!\");\n\n// after\nwxMaConfig.setApiSignatureAesKey(\"dGhpcyBpcyBhIHZhbGlkIGJhc2U2NCBrZXk=\");","handlingStrategy":"validation","validationCode":"// Validate AES key is decodable Base64 before calling postWithSignature\nString aesKey = wxMaConfig.getApiSignatureAesKey();\ntry {\n  byte[] decoded = Base64.getDecoder().decode(aesKey);\n  if (decoded.length != 32) {\n    throw new IllegalStateException(\"AES key must decode to 32 bytes\");\n  }\n} catch (IllegalArgumentException e) {\n  throw new IllegalStateException(\"ApiSignatureAesKey is not valid Base64\", e);\n}\nservice.postWithSignature(url, jsonObject);","typeGuard":"private static boolean isValidAesKey(String aesKey) {\n  if (aesKey == null || aesKey.isEmpty()) return false;\n  try {\n    return Base64.getDecoder().decode(aesKey).length == 32;\n  } catch (IllegalArgumentException e) {\n    return false;\n  }\n}","tryCatchPattern":"try {\n  service.postWithSignature(url, jsonObject);\n} catch (SecurityException e) {\n  if (e.getMessage().contains(\"AES KEY\")) {\n    log.error(\"Invalid AES key — re-copy from WeChat console and verify Base64 encoding\");\n  } else {\n    throw e;\n  }\n}","preventionTips":["Validate the AES key is valid Base64 and decodes to 32 bytes at application startup","Store keys in a secure config vault to avoid copy-paste errors","Remove whitespace, newlines, and PEM headers from key strings","Use a startup health check that validates all crypto configuration"],"tags":["configuration","miniapp","security","crypto","api-signature"],"backgroundTag":null,"analyzedSha":"1c43293a3c2c9d7e91304b6d037fb017f680d0c6","analyzedAt":"2026-08-14T02:29:11.060Z","schemaVersion":2},"datasetVersion":"2026-08-14T05:17:29.042Z"}