You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Node.js用AES-256-CTR解密WebCrypto AES-256-GCM加密内容结果异常

问题根因

  1. 核心错误是加密模式不匹配:AES-GCM和AES-CTR是两种完全不同的分组密码工作模式,加密逻辑存在本质差异,用GCM加密得到的密文不可能通过CTR模式解密出正确明文,这是解密结果乱码的核心原因,和密钥、IV是否正确无关。
  2. 你误以为客户端加密时没有生成authTag是错误认知:WebCrypto的AES-GCM加密输出的encrypted ArrayBuffer本身就已经包含了默认16字节的authTag,直接追加在密文末尾,你之前拼接数据时已经把authTag一起打包进了传输内容,不存在没有authTag的情况。

正确实现方案

可选优化:客户端加密显式指定authTag长度

显式指定authTag长度可以避免前后端对齐问题,默认值为128位(即16字节):

async function encrypt(text: string) {
    const encodedText = new TextEncoder().encode(text);

    const aesKey = await generateAesKey();
    const iv = window.crypto.getRandomValues(
      new Uint8Array(SERVER_ENCRYPTION_IV_LENGTH)
    );

    const encrypted = await window.crypto.subtle.encrypt(
      {
        name: 'AES-GCM',
        iv,
        tagLength: 128 // 显式指定authTag长度
      },
      aesKey,
      encodedText
    );

    const concatenatedData = new Uint8Array(
      iv.byteLength + encrypted.byteLength
    );
    concatenatedData.set(iv);
    concatenatedData.set(new Uint8Array(encrypted), iv.byteLength);

    return arrayBufferToBase64(concatenatedData)
}

后端改用AES-256-GCM模式解密

从传输的加密数据中拆分出IV、密文、authTag三部分即可正常解密:

import crypto from 'crypto';

export function decrypt(sharedKey: string, message: string) {
  const messageBuffer = Buffer.from(message, 'base64');
  const iv = messageBuffer.subarray(0, 16);
  // 加密数据末尾16字节为authTag,中间部分为实际密文
  const authTag = messageBuffer.subarray(-16);
  const encryptedData = messageBuffer.subarray(16, -16);

  const decipher = crypto.createDecipheriv(
    'aes-256-gcm',
    Buffer.from(sharedKey, 'base64'),
    iv
  );
  // 传入authTag做完整性校验
  decipher.setAuthTag(authTag);

  const decrypted = Buffer.concat([decipher.update(encryptedData), decipher.final()]);
  // 直接转utf8返回明文即可,不需要多余的编码转换
  return decrypted.toString('utf8');
}

额外注意事项

  • 如果你的IV长度不是16字节,调整上述代码中iv的截取长度即可
  • AES-GCM自带密文完整性校验,篡改密文、IV、authTag任意内容都会直接抛出解密失败错误,安全性远高于CTR模式,不要为了简化步骤改用CTR
  • 原后端解密逻辑中多余的binary转hex再转base64的操作属于无效编码转换,会额外破坏明文内容,不需要保留。

内容的提问来源于stack exchange,提问作者Ali Torki

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.04 06:51:00