3

I have below code in java documentation (it takes secret_key and data as input) :

javax.crypto.Mac mac = javax.crypto.Mac.getInstance("HmacSHA1")
mac.init(new javax.crypto.spec.SecretKeySpec(secret_key.getBytes(), "HmacSHA1"))
byte[] hexBytes = new org.apache.commons.codec.binary.Hex().encode(mac.doFinal(data.getBytes()))
String signature = new String(hexBytes, "UTF-8")

after doing some RnD online , i wrote equivalent python to :

decodedKey = secret_key.decode("hex")
hmac_val = hmac.new(decodedKey, data.encode('UTF-8'), hashlib.sha1)
signature = hmac_val.digest().encode('base64')

but on doing a post request with this signature value in header, i am getting

ValueError: Invalid header value 'XXXXXXXXXX'

is my python equivalent correct? it would be great help if someone can explain!

EDIT

Java

public static void main(String[] args) throws NoSuchAlgorithmException, InvalidKeyException, UnsupportedEncodingException {
        String secret_key = "c84766ca4a3ce52c3602bbf02ad1f7";
        String data = "some data";
        javax.crypto.Mac mac = javax.crypto.Mac.getInstance("HmacSHA1");
        mac.init(new javax.crypto.spec.SecretKeySpec(secret_key.getBytes(), "HmacSHA1"));
        byte[] hexBytes = new org.apache.commons.codec.binary.Hex().encode(mac.doFinal(data.getBytes()));
        String signature = new String(hexBytes, "UTF-8");
        System.out.println("signature : "+signature);
 }

o/p

signature : 2b565c0476eed0f350ddb3a2852a4cab91281bdc

Python :

In [1]: import hmac

In [2]: import hashlib

In [3]: secret_key = "c84766ca4a3ce52c3602bbf02ad1f7"

In [4]: data = "some data"

In [5]: decodedKey = secret_key.decode("hex")

In [6]: hmac_val = hmac.new(decodedKey, data.encode('UTF-8'), hashlib.sha1)

In [7]: signature = hmac_val.digest().encode('base64')

In [8]: signature
Out[8]: '3qE5SqSdvBEJcy8mSF+srqNXCd4=\n'

In [9]:
4
  • 5
    to err is human to forgive divine :) Commented Feb 17, 2016 at 18:44
  • Post the actual output from the two. Commented Feb 17, 2016 at 18:50
  • My first guess is that the data you're hashing isn't represented identically on both platforms. Feed each one an identical pregenerated byte sequence. Commented Feb 17, 2016 at 18:51
  • @chrylis : added edit, please see Commented Feb 17, 2016 at 19:29

3 Answers 3

1

Referrring to this thread :

Java method which can provide the same output as Python method for HMAC-SHA256 in Hex

minor tweeking for sha1, below is simple equivalent :

In [13]: print hmac.new(secret_key, data, hashlib.sha1).hexdigest()
2b565c0476eed0f350ddb3a2852a4cab91281bdc
Sign up to request clarification or add additional context in comments.

Comments

0

pycrypto has a hash function https://pypi.python.org/pypi/pycrypto

because of ValueError: Invalid header value 'XXXXXXXXXX' see this thread ValueError: Invalid header value 'H2O Python client/2.7.9 (default, Apr 2 2015, 15:33:21) \n[GCC 4.9.2]'

maybe the header in your post is not compatible with the library you use for the post

what libraries do you import in the python code ?

2 Comments

to get the same result the algorithms have to be equal down to bit level (endianness and so on) normally you could use a debugger (pdb, jdb) to step through each operation in the algorithm and see where the difference occurs. See this thread for the source code for javax.crypto stackoverflow.com/questions/18181023/… (java is always big-endian afaik)
why would i use some other language in my program when the same feature is present in my language?
0

if you want it easy try this: https://pythonhosted.org/pycrypto/Crypto.Hash.HMAC-module.html

maybe the encoding influences the result, [UTF-8] then [base-64]

1 Comment

getting ec0e4e884b0056d817efb56ab5920509 as output, so not correct, also, why not edit existing answer rather than posting a new one?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.