Why PHP’s hash_hmac (‘sha256’) gives different results than Java sha256_HMAC… here is a solution to the problem.
Why PHP’s hash_hmac (‘sha256’) gives different results than Java sha256_HMAC
In PHP I have the following function:
base64_encode(hash_hmac('sha256', $data, $secret, false));
I’m trying to create a function in Java that will give the same result for the same “data” and “secret” arguments.
I tried using this function :
public static String base64sha256(String data, String secret) {
Mac sha256_HMAC = Mac.getInstance("HmacSHA256");
SecretKeySpec secret_key = new SecretKeySpec(secret.getBytes(), "HmacSHA256");
sha256_HMAC.init(secret_key);
byte[] res = sha256_HMAC.doFinal(data.getBytes());
return Base64.encodeToString(res, Base64.NO_WRAP);
}
But I get different results for the same input
Update: This feature works. Enjoy it.
public static String base64sha256(String data, String secret) {
String hash = null;
try {
Mac sha256_HMAC = Mac.getInstance("HmacSHA256");
SecretKeySpec secret_key = new SecretKeySpec(secret.getBytes("UTF-8"), "HmacSHA256");
sha256_HMAC.init(secret_key);
byte[] res = sha256_HMAC.doFinal(data.getBytes("UTF-8"));
hash = getHex(res);
hash = Base64.encodeToString(hash.getBytes("UTF-8"), Base64.NO_WRAP);
} catch (Exception e){}
return hash;
}
static final String HEXES = "0123456789abcdef";
public static String getHex( byte [] raw ) {
if ( raw == null ) {
return null;
}
final StringBuilder hex = new StringBuilder( 2 * raw.length );
for ( final byte b : raw ) {
hex.append(HEXES.charAt((b & 0xF0) >> 4))
.append(HEXES.charAt((b & 0x0F)));
}
return hex.toString();
}
Solution
When the fourth argument is false, the output of the PHP function is a lowercase hexadecimal number. However, your second Java version generates uppercase hexadecimal numbers. Either correct the case difference, or you can change the fourth parameter of hash_hmac to true, which will probably match your first Java version.