I am trying to create a signature using the HMAC-SHA256 algorithm and this is my code. I am using US ASCII encoding.
final Charset asciiCs = Charset.forName("US-ASCII"); final Mac sha256_HMAC = Mac.getInstance("HmacSHA256"); final SecretKeySpec secret_key = new javax.crypto.spec.SecretKeySpec(asciiCs.encode("key").array(), "HmacSHA256"); sha256_HMAC.init(secret_key); final byte[] mac_data = sha256_HMAC.doFinal(asciiCs.encode("The quick brown fox jumps over the lazy dog").array()); String result = ""; for (final byte element : mac_data) { result += Integer.toString((element & 0xff) + 0x100, 16).substring(1); } System.out.println("Result:[" + result + "]");
The result that I am getting from the above code is:
f7bc83f430538424b13298e6aa6fb143ef4d59a14946175997479dbc2d1a3cd8
This is same as to that of shown in the wiki
HMAC_SHA256("key", "The quick brown fox jumps over the lazy dog") = 0x f7bc83f430538424b13298e6aa6fb143ef4d59a14946175997479dbc2d1a3cd8
except for the 0x
.
I am looking for ideas/comments if I am doing everything right or may be I can improve my code.
Setting up HMAC using the DashboardScroll to the Authentication options. Select HMAC (Signed Authetication Key) from the drop-down list. Configure your HMAC Request Signing settings. Select Strip Authorization Data to strip any authorization data from your API requests.
HMAC stands for Keyed-Hashing for Message Authentication. It's a message authentication code obtained by running a cryptographic hash function (like MD5, SHA1, and SHA256) over the data (to be authenticated) and a shared secret key.
Yes, using an HMAC with a sufficiently long secret key should prevent third-parties from being able to brute-force the hashed values and identify their original values. For HMAC-SHA256, a 256-bit key would be sufficient.
Here is my solution:
public static String encode(String key, String data) throws Exception { Mac sha256_HMAC = Mac.getInstance("HmacSHA256"); SecretKeySpec secret_key = new SecretKeySpec(key.getBytes("UTF-8"), "HmacSHA256"); sha256_HMAC.init(secret_key); return Hex.encodeHexString(sha256_HMAC.doFinal(data.getBytes("UTF-8"))); } public static void main(String [] args) throws Exception { System.out.println(encode("key", "The quick brown fox jumps over the lazy dog")); }
Or you can return the hash encoded in Base64:
Base64.encodeBase64String(sha256_HMAC.doFinal(data.getBytes("UTF-8")));
The output in hex is as expected:
f7bc83f430538424b13298e6aa6fb143ef4d59a14946175997479dbc2d1a3cd8
The 0x just denotes that the characters after it represent a hex string.
0x1A == 1Ah == 26 == 1A
So the 0x is just to clarify what format the output is in, no need to worry about it.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With