我一直在尝试将此Java程序移植到Node.js。我已经尝试了几种方法,但到目前为止仍无法完成。可能是由于我对密码学的了解有限。
我编写的Node.js程序就是这个。
var crypto = require('crypto');
var iv = crypto.randomBytes(8);
var encrypt = function(data, key) {
var decodeKey = crypto.createHash('sha512').update(key, 'utf-8').digest().slice(0, 24);
var cipher = crypto.createCipheriv('des-ede-cbc', decodeKey, iv);
return cipher.update(data, 'utf8', 'hex') + cipher.final('hex');
};
var data = 'abc101'
var key = '1785851816255252-8887772';
var cipher = encrypt(data, key);
console.log(cipher);
我一直收到以下错误:
Error: Invalid key length
我要移植的原始程序是这样的:
import java.security.MessageDigest;
import java.security.spec.KeySpec;
import java.util.Arrays;
import javax.crypto.Cipher;
import javax.crypto.SecretKey;
import javax.crypto.SecretKeyFactory;
import javax.crypto.spec.DESedeKeySpec;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;
import org.apache.commons.codec.binary.Base64;
public class PasswordEncryptor {
public static void main(String[] args) {
String passwd = "abc101";
String msgId = "1785851816255252-8887772";
String result = "";
try {
if (passwd == null && passwd.equals("") && msgId == null && msgId.equals("")) {
System.out.println("Wrong Inputs");
} else {
result = PasswordEncryptor.encryptPassword(msgId, passwd);
}
System.out.println(result);
} catch (Exception e) {
System.out.println("Exception in PasswordEncryption ::: " + e);
}
}
public static String encryptPassword(String msgId, String password) {
String finalValue = "";
try {
MessageDigest mDigest = MessageDigest.getInstance("SHA-512");
byte[] digestSeed = mDigest.digest(msgId.getBytes());
byte[] seedEncArray = Arrays.copyOf(digestSeed, 24);
Cipher cipher = Cipher.getInstance("DESede/CBC/PKCS5Padding");
SecretKeySpec skspec = new SecretKeySpec(seedEncArray, "DESede");
IvParameterSpec iv = new IvParameterSpec(new byte[8]);
cipher.init(Cipher.ENCRYPT_MODE, skspec, iv);
byte[] finalByteArray = cipher.doFinal(password.getBytes());
finalValue = new String(Base64.encodeBase64(finalByteArray));
} catch (Exception e) {
System.out.println("Exception in encryptPassword ::::" + e);
}
return finalValue;
}
}
感谢您的帮助。谢谢。
答案 0 :(得分:0)
nodejs调用OpenSSL,由于歇斯底里的葡萄干,其命名方案有一些奇怪的缺陷。 OpenSSL中的des-ede-$mode
实际上是Keying Option 2,也称为2键TDEA。对于“真实的”三键TDEA,在这种情况下,您必须要求des-ede3-$mode
des-ede3-cbc
。
此外,Java代码使用new byte[8]
作为IV值,该值是8字节全为零,但是您的nodejs代码使用随机字节。从密码学角度来讲,随机实际上是更好的方法,但是如果您的目标是产生与Java代码相同的结果,则需要复制其错误。
最后,当nodejs代码使用十六进制时,Java代码将结果编码为base64。这些在语义上是等效的,并且可以容易地相互转换,但是并不相同。如果您确实希望这样做,nodejs确实支持base64。
此外:Java代码中的尝试错误检查
if (passwd == null && passwd.equals("") && msgId == null && msgId.equals(""))
只是愚蠢的; Java String
不能同时是== null
和.equals("")
。所有这些&&
的log-,并且应该是||
的log-or。显然,该代码没有经过或测试的或主管的编写;如果我是你(不是我),我会避免与此有关。