Search code examples
javagobase64hmacsha1

Go Hmac SHA1 generates hash different from Hmac SHA1 in Java


I'm just starting to learn Go and I'm trying to rewrite my existing small application from Java to Go.

I need to create Base64 hash of input string with key using Hmac SHA1 algorithm.

My Java code:

private String getSignedBody(String input, String key) {
    String result = "";
    try {
        SecretKeySpec signingKey = new SecretKeySpec(key.getBytes("UTF-8"), "HmacSHA1");
        Mac mac = Mac.getInstance("HmacSHA1");
        mac.init(signingKey);
        byte[] rawHmac = mac.doFinal(input.getBytes("UTF-8"));
        result = Base64.encodeToString(rawHmac, false);
    } catch (Exception e) {
        Logger.error("Failed to generate signature: " + e.getMessage());
    }
    return result;
}

My Go code:

func GetSignature(input, key string) string {
    key_for_sign := []byte(key)
    h := hmac.New(sha1.New, key_for_sign)
    h.Write([]byte(input))
    return base64.StdEncoding.EncodeToString(h.Sum(nil))
}

The problem is that Go code generates output that is not expected. For example, for input string "qwerty" and key "key" Java output will be RiD1vimxoaouU3VB1sVmchwhfhg= and Go output will be 9Cuw7rAY671Fl65yE3EexgdghD8=.

Where did I make mistakes in the Go code?


Solution

  • The Go code you provided gives exactly the same output as the Java code.

    Try it on the Go Playground.

    Output:

    RiD1vimxoaouU3VB1sVmchwhfhg=
    

    You made the mistake when you called your GetSignature() function. Call it like the linked example code:

    fmt.Println(GetSignature("qwerty", "key"))
    

    Your mistake was that you passed an empty input to your GetSignature() function. Calling it with empty "" input and "key" key produces the non-expected output you provided:

    fmt.Println(GetSignature("", "key"))
    

    Output:

    9Cuw7rAY671Fl65yE3EexgdghD8=