iflytek/astron-agent · error · RuntimeException

WeChat message decryption failed

Error message

WeChat message decryption failed

What it means

decryptMessage wraps all decryption work in a try/catch; any exception during the (currently stubbed, mock-returning) decryption path is logged and rethrown as RuntimeException('WeChat message decryption failed', e). It is a generic wrapper, so the root cause is always in the chained cause exception.

Solutions

  1. Inspect the chained cause (`e.getCause()` in logs) — the RuntimeException is only a wrapper.
  2. Validate the encrypted payload is well-formed Base64/AES ciphertext matching WeChat's format before calling decryptMessage.
  3. Replace the TODO stub with the official WXBizMsgCrypt.decryptMsg so real messages decrypt instead of failing on mock logic.
  4. Confirm EncodingAESKey and AppId configuration are correct for the WeChat app.

Example fix

// before
throw new RuntimeException("WeChat message decryption failed", e);
// after
return ApiResult.fail(400, "WeChat message decryption failed: " + e.getCause());
// and implement:
// result = new WXBizMsgCrypt(token, aesKey, appId).decryptMsg(sig, ts, nonce, xml);
Defensive patterns

Strategy: try-catch

Validate before calling

boolean looksEncrypted = encryptData != null && Base64.getDecoder().decode(encryptData).length > 16;

Try / catch

try { return crypto.decryptMessage(sig, ts, nonce, enc); } catch (RuntimeException e) { log.error("decrypt failed, cause={}", e.getCause()); return ResponseEntity.status(500).body("decryption unavailable"); }

Prevention

When it happens

Trigger: Any exception thrown inside decryptMessage's try block — e.g. the IllegalArgumentException from the empty-payload guard when bypassed, Base64/AES failures in the future real implementation, or malformed encrypted data fed to the decrypt logic.

Common situations: Malformed or non-Base64 encrypted payloads posted to the callback; wrong EncodingAESKey once real decryption is implemented; the stub's mock path replaced with real WXBizMsgCrypt calls that fail on invalid signatures; corrupted message bodies from intermediary proxies.

Understand the failure class

Background: "API request failed": what wrapped HTTP errors from external APIs mean and how to find the real cause — this error's family across 29 libraries.

Related errors


AI-assisted analysis of iflytek/astron-agent@5e758547a8 (2026-09-12). Data as JSON: /api/errors/f6edb1d2737608ed. Report an issue: GitHub.

Appendix: source

Thrown at console/backend/hub/src/main/java/com/iflytek/astron/console/hub/util/wechat/WechatMessageCrypto.java:58

        try {
            // TODO: Implement actual WeChat message decryption logic here
            // In actual projects, should use the official WeChat WXBizMsgCrypt class
            log.warn("WeChat message decryption functionality needs to be implemented, currently returning mock data");

            // Return mock decrypted data
            return "<xml>" +
                    "<AppId><![CDATA[" + componentAppid + "]]></AppId>" +
                    "<InfoType><![CDATA[authorized]]></InfoType>" +
                    "<AuthorizerAppid><![CDATA[wx[example_appid]]]></AuthorizerAppid>" +
                    "<AuthorizationCode><![CDATA[auth_code_123]]></AuthorizationCode>" +
                    "<CreateTime>1234567890</CreateTime>" +
                    "</xml>";

        } catch (Exception e) {
            log.error("WeChat message decryption failed: msgSignature={}, timestamp={}, nonce={}",
                    msgSignature, timestamp, nonce, e);
            throw new RuntimeException("WeChat message decryption failed", e);
        }
    }

    /**
     * Verify message signature
     *
     * @param signature Signature
     * @param timestamp Timestamp
     * @param nonce Random number
     * @return Whether verification passed
     */
    public boolean verifySignature(String signature, String timestamp, String nonce) {
        if (!StringUtils.hasText(signature) || !StringUtils.hasText(timestamp) || !StringUtils.hasText(nonce)) {
            return false;
        }

        try {
            // TODO: Implement actual signature verification logic here

View on GitHub (pinned to 5e758547a8)