java相当于php的hmac-SHA1

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1609899/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-12 17:46:30  来源:igfitidea点击:

java equivalent to php's hmac-SHA1

javaphpcryptographyhmac

提问by Bee

I'm looking for a java equivalent to this php call:

我正在寻找一个相当于这个 php 调用的 java:

hash_hmac('sha1', "test", "secret")

I tried this, using java.crypto.Mac, but the two do not agree:

我试过这个,使用java.crypto.Mac,但两者不同意:

String mykey = "secret";
String test = "test";
try {
    Mac mac = Mac.getInstance("HmacSHA1");
    SecretKeySpec secret = new SecretKeySpec(mykey.getBytes(),"HmacSHA1");
    mac.init(secret);
    byte[] digest = mac.doFinal(test.getBytes());
    String enc = new String(digest);
    System.out.println(enc);  
} catch (Exception e) {
    System.out.println(e.getMessage());
}

The outputs with key = "secret" and test = "test" do not seem to match.

key = "secret" 和 test = "test" 的输​​出似乎不匹配。

采纳答案by Dirk D

In fact they do agree.
As Hans Doggen already noted PHP outputs the message digest using hexadecimal notation unless you set the raw output parameter to true.
If you want to use the same notation in Java you can use something like

事实上,他们确实同意。
正如 Hans Doggen 已经指出的那样,除非您将原始输出参数设置为 true,否则 PHP 会使用十六进制表示法输出消息摘要。
如果你想在 Java 中使用相同的符号,你可以使用类似的东西

for (byte b : digest) {
    System.out.format("%02x", b);
}
System.out.println();

to format the output accordingly.

相应地格式化输出。

回答by Hans Doggen

Seems to me that PHP uses HEX notation for the bytes that Java produces (1a = 26) - but I didn't check the whole expression.

在我看来,PHP 对 Java 生成的字节使用十六进制表示法 (1a = 26) - 但我没有检查整个表达式。

What happens if you run the byte array through the method on thispage?

如果您运行通过对方法的字节数组,会发生什么这个网页?

回答by serg

Haven't tested it, but try this:

还没有测试过,但试试这个:

        BigInteger hash = new BigInteger(1, digest);
        String enc = hash.toString(16);
        if ((enc.length() % 2) != 0) {
            enc = "0" + enc;
        }

This is snapshot from my method that makes java's md5 and sha1 match php.

这是我的方法的快照,它使 java 的 md5 和 sha1 匹配 php。

回答by atomsfat

This is my implementation :

这是我的实现:

        String hmac = "";

    Mac mac = Mac.getInstance("HmacSHA1");
    SecretKeySpec secret = new SecretKeySpec(llave.getBytes(), "HmacSHA1");
    mac.init(secret);
    byte[] digest = mac.doFinal(cadena.getBytes());
    BigInteger hash = new BigInteger(1, digest);
    hmac = hash.toString(16);

    if (hmac.length() % 2 != 0) {
        hmac = "0" + hmac;
    }

    return hmac;

回答by dharan

You can try this in Java:

你可以在 Java 中试试这个:

private static String computeSignature(String baseString, String keyString) throws GeneralSecurityException, UnsupportedEncodingException {

    SecretKey secretKey = null;

    byte[] keyBytes = keyString.getBytes();
    secretKey = new SecretKeySpec(keyBytes, "HmacSHA1");

    Mac mac = Mac.getInstance("HmacSHA1");

    mac.init(secretKey);

    byte[] text = baseString.getBytes();

    return new String(Base64.encodeBase64(mac.doFinal(text))).trim();
}

回答by Krizko

My implementation for HmacMD5 - just change algorithm to HmacSHA1:

我对 HmacMD5 的实现 - 只需将算法更改为 HmacSHA1:

SecretKeySpec keySpec = new SecretKeySpec("secretkey".getBytes(), "HmacMD5");
Mac mac = Mac.getInstance("HmacMD5");
mac.init(keySpec);
byte[] hashBytes = mac.doFinal("text2crypt".getBytes());
return Hex.encodeHexString(hashBytes);

回答by Akhil

This way I could get the exact same string as I was getting with hash_hmac in php

这样我就可以得到与我在 php 中使用 hash_hmac 得到的完全相同的字符串

String result;

try {
        String data = "mydata";
        String key = "myKey";
        // Get an hmac_sha1 key from the raw key bytes
        byte[] keyBytes = key.getBytes();
        SecretKeySpec signingKey = new SecretKeySpec(keyBytes, "HmacSHA1");

        // Get an hmac_sha1 Mac instance and initialize with the signing key
        Mac mac = Mac.getInstance("HmacSHA1");
        mac.init(signingKey);

        // Compute the hmac on input data bytes
        byte[] rawHmac = mac.doFinal(data.getBytes());

        // Convert raw bytes to Hex
        byte[] hexBytes = new Hex().encode(rawHmac);

        //  Covert array of Hex bytes to a String
        result = new String(hexBytes, "ISO-8859-1");
        out.println("MAC : " + result);
}
catch (Exception e) {

}