当前位置:  开发笔记 > 编程语言 > 正文

AES加密使用CryptoJS

如何解决《AES加密使用CryptoJS》经验,为你挑选了1个好方法。

我需要使用JavaScript实现AES加密.使用AES/CBC/NoPadding模式并创建了一个方法来完成16个长度块.我已经用Java解决了它.看起来像:

public static String encrypt(byte[] key, byte[] initVector, String value) {
    try {
        IvParameterSpec iv = new IvParameterSpec(initVector);
        SecretKeySpec skeySpec = new SecretKeySpec(key, "AES");
        Cipher cipher = Cipher.getInstance("AES/CBC/NoPadding");
        cipher.init(Cipher.ENCRYPT_MODE, skeySpec, iv);
        byte[] encrypted = cipher.doFinal(completeBlocks(value));
        return Base64.encodeBase64String(encrypted);
    } catch (NoSuchAlgorithmException | NoSuchPaddingException | InvalidKeyException | InvalidAlgorithmParameterException | IllegalBlockSizeException | BadPaddingException ex) {
        System.out.println("Error: " + ex);
    }

    return null;
}

/**
 * Completes 16 lenght blocks
 *
 * @param message
 *
 *
 */
static byte[] completeBlocks(String message) {
    try {

        int bytesLenght = message.getBytes("UTF-8").length;
        if (bytesLenght % 16 != 0) {
            byte[] newArray = new byte[bytesLenght + (16 - (bytesLenght % 16))];
            System.arraycopy(message.getBytes(), 0, newArray, 0, bytesLenght);
            return newArray;
        }

        return message.getBytes("UTF-8");

    } catch (UnsupportedEncodingException ex) {
        System.out.println("" + ex);
    }
    return null;
}

public static void main(String[] args) {

    String key = "253D3FB468A0E24677C28A624BE0F939";
    String strToEncrypt = "My Secret text";
    final byte[] initVector = new byte[16];
    String resultado = encrypt(new BigInteger(key, 16).toByteArray(), initVector, strToEncrypt.trim());
    System.out.println("ENCRYPTED:");
    System.out.println(resultado);
}

具有输入key = 253D3FB468A0E24677C28A624BE0F939,strToEncrypt = "My Secret text"和CEROS IV.它抛出

7StScX3LnPUly/VNzBes0w ==

我知道这是所需的输出.这是正确的!我尝试使用JavaScript复制它.我用过CryptoJs库.但我无法生成相同的Java输出.我试过了:

var text = "My Secret text";
var key = CryptoJS.enc.Base64.parse("253D3FB468A0E24677C28A624BE0F939");
var iv  = CryptoJS.enc.Base64.parse("                ");
var encrypted = CryptoJS.AES.encrypt(text, key, {iv: iv});
console.log(encrypted.toString());

var decrypted = CryptoJS.AES.decrypt(encrypted, key, {iv: iv});
console.log(decrypted.toString(CryptoJS.enc.Utf8));

使用相同的输入,我得到De+CvPVIyiBX2//EE6gXTg==输出.我究竟做错了什么?如何获得相同的Java输出?非常感谢!!



1> Alex K...:

假设您将修复诸如空IV之类的事情以及这是概念验证,您的代码将失败,因为:

    在Java中不使用填充,您需要在JS中使用相同的填充

    您在Java中手动填充空值,您需要在JS中执行相同的操作

    你base64解码密钥但它不是base64(它是一个十六进制的字节串)

    Java IV是一个空数组,但在JS中你使用空格(并错误地将其视为base64).

要在JS中复制输出:

CryptoJS.pad.NoPadding = {pad: function(){}, unpad: function(){}};

var text = "My Secret text\0\0";
var key  = CryptoJS.enc.Hex.parse("253D3FB468A0E24677C28A624BE0F939");
var iv   = CryptoJS.enc.Hex.parse("00000000000000000000000000000000");

var encrypted = CryptoJS.AES.encrypt(text, key, {iv: iv, padding: CryptoJS.pad.NoPadding});

console.log(encrypted.toString());

对于:

7StScX3LnPUly/VNzBes0w ==

推荐阅读
臭小子
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有