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

ESP32 AES-128-ECB加密URL参数,Node.js解密密钥长度错误问题

解决Node.js AES-128-ECB解密时的密钥长度无效错误

问题背景

ESP32端基于mbedtls实现AES-128-ECB加密:将uint64_t变量转为字符串,使用密钥字符串"0123456789ABCDEF"加密后生成十六进制密文,作为URL查询参数传递给Node.js服务。但Node.js解密时始终抛出RangeError: Invalid key length错误,无法正常解密。

错误原因

ESP32和Node.js端对密钥的处理逻辑不一致:

  • ESP32端:mbedtls_aes_setkey_enc直接将密钥字符串的原始ASCII字节作为AES密钥。字符串"0123456789ABCDEF"包含16个ASCII字符,每个字符占1字节,总长度16字节(128位),正好符合AES-128的密钥长度要求。
  • Node.js端:原代码使用Buffer.from(key, 'hex')处理密钥,这会把密钥字符串当作十六进制格式解析。16个十六进制字符仅对应8字节数据,远小于AES-128所需的16字节,因此触发密钥长度无效错误。

修复方案

修改Node.js端的密钥处理逻辑,使其与ESP32端保持一致:直接将密钥字符串转为原始字节Buffer,而非按十六进制解析。同时需处理ESP32端的\0填充,解密后去除末尾的空字符。

修改后的Node.js解密代码

const crypto = require('crypto');

function decryptAES(ciphertextHex, key) {
    try{
        // 将密文十六进制字符串转为Buffer
        const ciphertext = Buffer.from(ciphertextHex, 'hex');
        // 直接将密钥字符串转为原始字节Buffer(与ESP32端逻辑一致)
        const keyBuffer = Buffer.from(key);
        // 创建AES-128-ECB解密对象(ECB模式无需IV,传入空Buffer)
        const decipher = crypto.createDecipheriv('aes-128-ecb', keyBuffer, Buffer.alloc(0));
        // 禁用自动填充(ESP32端手动用\0填充,需自行处理)
        decipher.setAutoPadding(false);
        // 解密
        let decrypted = decipher.update(ciphertext);
        decrypted = Buffer.concat([decrypted, decipher.final()]);
        // 转为字符串并去除末尾的\0填充字符
        const plaintext = decrypted.toString().replace(/\0+$/, '');
        return plaintext;
    }catch(error){
        console.log(error);
        return null;
    }
}

app.get('/testDecrypt', (req, res) => {
    const decryptedVariable = decryptAES(req.query.key, process.env.AES_KEY);
    console.log('Decrypted variable:', decryptedVariable , "Raw query variable: ", req.query.key, "AES key: ", process.env.AES_KEY);

    if(!decryptedVariable){
        return res.status(401).json({ message: 'Wrong variable!' });
    }
    return res.json({message:"ok"});
});

关键修改点说明

  1. 密钥处理:将Buffer.from(key, 'hex')改为Buffer.from(key),确保使用密钥字符串的原始ASCII字节作为AES密钥,长度为16字节(符合AES-128要求)。
  2. 填充处理:调用decipher.setAutoPadding(false)禁用Node.js crypto模块的自动填充,因为ESP32端是手动用\0填充至块大小,解密后需手动去除末尾的空字符(通过replace(/\0+$/, '')实现)。

验证结果

修改后,Node.js端可成功解密ESP32传来的密文,得到原始字符串"27483611521760",服务返回{"message":"ok"}。

内容的提问来源于stack exchange,提问作者Dr.Random

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.28 22:09:52