NodeJs / Javascript AES 128 EBC加密与iOS AES 128 EBC加密不匹配

时间:2019-01-04 08:45:15

标签: javascript ios node.js angular cryptojs

在我们的Angular项目中,我们需要解密由iOS加密的文本/文件。

iOS团队正在使用带有ECB模式算法的AES 128位加密。

我尝试使用CryptoJS,aes-js并直接使用NodeJs中的Crypto类。

来自iOS的加密文本或解密的UTF8字符串的结果不匹配。我们获得了不同的价值。

iOS团队正在使用aes-commoncrypto库

在调用通用密码库之前,我们将字符串转换为iOS数据(Dataatype),即字节缓冲区并使用UTF8进行编码

加密-

let fileUrl = URL(fileURLWithPath: folderPath)
                    try? Utils.aes128Encryption(forData: 
textAnnotationText.data(using: .utf8))?.write(to: fileUrl)

解密-

 let _fileURL = documentsDirectory.appendingPathComponent( path)

do {
        if let decryptedData = Utils.aes128Decryption(forData: try Data(contentsOf: _fileURL)) {
                                            message = String(decoding: decryptedData, as: UTF8.self)
                                   }
}

CCCrypt(operation,
                  kCCAlgorithmAES128,
                  kCCOptionPKCS7Padding | kCCOptionECBMode,
                  keyPtr,
                  kCCBlockSizeAES128,
                  ivPtr,
                  [self bytes],
                  dataLength,
                  buffer,
                  bufferSize,
                  &numBytesEncrypted)

根据对以上代码的理解,iOS团队正在使用ECB模式算法。 输出:UTF8字符串,我们将其写入文档目录文件。

解决方案1: 使用CryptoJS:

let key = CryptoJS.enc.Utf8.parse(TESTKEY);
let iv = CryptoJS.lib.WordArray.create([0, 0]);
const encrypted = CryptoJS.AES.encrypt(message, key, {
        keysize: 256 / 8,
        iv: iv.toString(),
        mode: CryptoJS.mode.ECB,
        padding: CryptoJS.pad.Pkcs7
    });

const crypto64 = crypto.ciphertext.toString();

输出:Base64编码的字符串。 (与iOS加密文本不匹配)

解决方案2:使用AES Js:

let aesEcb = new aesjs.ModeOfOperation.ecb(Buffer.from(key, 'utf8'));
let textBytes = aesjs.utils.utf8.toBytes(str);
let encryptedBytes = aesEcb.encrypt(textBytes);

输出:我们收到错误消息“无效的纯文本大小(必须为16字节的倍数)”

解决方案3:使用加密解密器

fs.readFile('./sample_text.html', 'utf-8', function (err, data) {
    if (err) throw err;
    console.log(data);
    const d = crypto.createDecipheriv('aes-128-ecb', convertCryptKey(key), '')
    let ret = ''
    d.setAutoPadding(false);
    console.log(Buffer.from(data, 'utf8'));
    ret = d.update(data, 'binary', 'utf8')

    console.log(ret);
    decoded = Buffer.concat([ ret, d.final() ]);
    console.log(decoded);
});

function convertCryptKey(strKey) {
   const newKey = new Buffer([0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0])
   strKey = new Buffer(strKey)
   for (let i = 0; i < strKey.length; i++) newKey[i % 16] ^= strKey[i]
   return newKey
}

输出:与iOS加密的字符串或文件不匹配

0 个答案:

没有答案