我正在尝试在Java(Android)中设置安全的哈希密钥。它没有得到与php side相同的结果(我将其用作参考并且可以正常工作)。
我已经经历了许多类似的问题,但是(只有一个,我尝试过,但是不起作用)没有一个能解决清楚的问题。这是我测试过的代码。
// php code
$secureHash = 'ABCD';
$secret = '123AE45F';
echo '<br> using pack--';
echo hash_hmac('sha256', $secureHash, pack('H*', $secret));
echo '<br> without using pack--';
echo hash_hmac('sha256', $secureHash, $secret, false);
带包装的结果:f7a009f2c3e654fa48296917ab6372ecb7aa2a24c43fccb70af743f66b6dba55
不带包装的结果:fc602f0f6faf2072be9c0b995ee3d603f61414c4beb027b678c90946db6903a2
// Java code
private String getHashCode(String message, String secretKey) {
Mac mac;
String result = null;
try {
byte[] byteKey = secretKey.getBytes(StandardCharsets.UTF_8);
final String hmacSHA256 = "HmacSHA256";
mac = Mac.getInstance(hmacSHA256);
SecretKeySpec keySpec = new SecretKeySpec(secretKey.getBytes(), hmacSHA256);
sha256HMAC.init(keySpec);
byte[] mac_data = sha256HMAC.doFinal(message.getBytes(StandardCharsets.UTF_8));
result = bytesToHex(mac_data);
System.out.println("getHashCode: result " + result);
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (InvalidKeyException e) {
e.printStackTrace();
}
return result;
}
在Java代码中,我得到的输出为
fc602f0f6faf2072be9c0b995ee3d603f61414c4beb027b678c90946db6903a2
与不带包装的php代码相同。如何获得与PHP相同的输出,即在Java代码中使用pack('H*', $secret)
?
答案 0 :(得分:0)
感谢@rolfl的this stackoverflow answer,而不是密钥上的string.getBytes java函数,我用他的函数来获取字节,
public byte[] hexToString(String hex) {
// hexToString that works at a byte level, not at character level
byte[] output = new byte[(hex.length() + 1) / 2];
for (int i = hex.length() - 1; i >= 0; i -= 2) {
int from = i - 1;
if (from < 0) {
from = 0;
}
String str = hex.substring(from, i + 1);
output[i/2] = (byte)Integer.parseInt(str, 16);
}
return output;
}
现在我得到了与php相同的十六进制类型密钥。