binarywang/WxJava · error · SecurityException

解析AES KEY失败,请检查ApiSignatureAesKey是否正确

Error message

解析AES KEY失败,请检查ApiSignatureAesKey是否正确

What it means

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.

Source

Thrown at weixin-java-miniapp/src/main/java/cn/binarywang/wx/miniapp/api/impl/BaseWxMaServiceImpl.java:970

    jsonObject.addProperty("_n", rndStr);
    jsonObject.addProperty("_appid", appId);
    jsonObject.addProperty("_timestamp", timestamp);

    String plainText = jsonObject.toString();
    log.debug("URL:{}加密前请求数据:{}", url, plainText);
    String urlPath;
    if (url.contains("?")) {
      urlPath = url.substring(0, url.indexOf("?"));
    } else {
      urlPath = url;
    }
    String aad = urlPath + "|" + appId + "|" + timestamp + "|" + aesKeySn;
    byte[] realKey;
    try {
      realKey = Base64.getDecoder().decode(aesKey);
    } catch (Exception ex) {
      log.error("解析AESKEY失败 {}", aesKey, ex);
      throw new SecurityException("解析AES KEY失败,请检查ApiSignatureAesKey是否正确", ex);
    }
    byte[] realIv = generateRandomBytes(12);
    byte[] realAad = aad.getBytes(StandardCharsets.UTF_8);
    byte[] realPlainText = plainText.getBytes(StandardCharsets.UTF_8);

    try {
      // 加密内容 AES
      Cipher cipher = Cipher.getInstance("AES/GCM/NoPadding");
      SecretKeySpec aesKeySpec = new SecretKeySpec(realKey, "AES");
      GCMParameterSpec parameterSpec = new GCMParameterSpec(128, realIv);
      cipher.init(Cipher.ENCRYPT_MODE, aesKeySpec, parameterSpec);
      cipher.updateAAD(realAad);

      byte[] ciphertext = cipher.doFinal(realPlainText);
      byte[] encryptedData = Arrays.copyOfRange(ciphertext, 0, ciphertext.length - 16);
      byte[] authTag = Arrays.copyOfRange(ciphertext, ciphertext.length - 16, ciphertext.length);

      JsonObject reqData = new JsonObject();

View on GitHub (pinned to 1c43293a3c)

Solutions

  1. Verify the AES key is valid Base64 and decodes to exactly 32 bytes
  2. Remove any whitespace, PEM headers, or trailing characters from the key string
  3. Re-copy the AES key from the WeChat console ensuring no truncation or encoding changes

Example fix

// before
wxMaConfig.setApiSignatureAesKey("invalid-key!!!");

// after
wxMaConfig.setApiSignatureAesKey("dGhpcyBpcyBhIHZhbGlkIGJhc2U2NCBrZXk=");
Defensive patterns

Strategy: validation

Validate before calling

// Validate AES key is decodable Base64 before calling postWithSignature
String aesKey = wxMaConfig.getApiSignatureAesKey();
try {
  byte[] decoded = Base64.getDecoder().decode(aesKey);
  if (decoded.length != 32) {
    throw new IllegalStateException("AES key must decode to 32 bytes");
  }
} catch (IllegalArgumentException e) {
  throw new IllegalStateException("ApiSignatureAesKey is not valid Base64", e);
}
service.postWithSignature(url, jsonObject);

Type guard

private static boolean isValidAesKey(String aesKey) {
  if (aesKey == null || aesKey.isEmpty()) return false;
  try {
    return Base64.getDecoder().decode(aesKey).length == 32;
  } catch (IllegalArgumentException e) {
    return false;
  }
}

Try / catch

try {
  service.postWithSignature(url, jsonObject);
} catch (SecurityException e) {
  if (e.getMessage().contains("AES KEY")) {
    log.error("Invalid AES key — re-copy from WeChat console and verify Base64 encoding");
  } else {
    throw e;
  }
}

Prevention

When it happens

Trigger: Calling postWithSignature() when apiSignatureAesKey contains characters that are not valid Base64, or the key string has incorrect length/padding.

Common situations: Typo in AES key; key copied with extra whitespace, newlines, or PEM headers; key truncated during deployment; wrong encoding (hex instead of Base64).

Related errors


AI-assisted analysis of binarywang/WxJava@1c43293a3c (2026-08-14). Data as JSON: /api/errors/3426c24e85d63690. Report an issue: GitHub.