将C#哈希函数转换为PHP
本文关键字:PHP 转换 函数 哈希 | 更新日期: 2023-09-27 18:19:51
我在C#中有以下函数,这是一个需要转换为PHP的哈希函数。我在PHP中尝试了一些东西,但没有得到相同的结果(我对.NET一点都不好)
private static string GetSignature(string args, string privatekey)
{
var encoding = new System.Text.ASCIIEncoding();
byte[] key = encoding.GetBytes(privatekey);
var myhmacsha256 = new HMACSHA256(key);
byte[] hashValue = myhmacsha256.ComputeHash(encoding.GetBytes(args));
string hmac64 = Convert.ToBase64String(hashValue);
myhmacsha256.Clear();
return hmac64;
}
PHP中的一个(错误的)尝试是:
function encode($data,$key)
{
return base64_encode( hash_hmac('sha256', $data, $key ) );
}
答案
阻尼S8N下面建议的一个细微的变化对我有效。
function encode($data,$key)
{
iconv_set_encoding("input_encoding", "ASCII");
iconv_set_encoding("internal_encoding", "ASCII");
iconv_set_encoding("output_encoding", "ASCII");
return base64_encode( hash_hmac('sha256', $data, $key, true ) );
}
还请不要将hash_hmac的第四个参数设置为true,以将原始输出设置为二进制数据
我怀疑.net代码的第一行就是罪魁祸首。PHP对字符串本身没有编码,因此当进行哈希时,它要么对内部PHP字符串格式的字节进行哈希(不太可能,其他人能确认吗?),要么很可能首先转换为其他格式。在这种情况下,可能是unicode,它显然与.net请求的ASCII字符串中的字节不同。
我的建议是确保PHP也使用ASCII和iconv,以实现互操作性。
function encode($data,$key)
{
return base64_encode( hash_hmac('sha256', iconv( iconv_get_encoding( "internal_encoding"), "ASCII", $data ), iconv( iconv_get_encoding( "internal_encoding"), "ASCII", $key ) ) );
}
然而,我不能确定上面的代码是否会输出所需的散列,因为我没有.net来测试初始代码。但这可能会给你指明正确的方向。
如果这不起作用,iconv_get_encoding(
内部的值可能是罪魁祸首,也可以尝试"output_encoding"
或"input_encoding"
。也可能需要使用iconv_set_encoding(
将这些相同的值设置为ASCII。
祝你好运!
更新!这就是最终奏效的:
function encode($data,$key)
{
iconv_set_encoding("input_encoding", "ASCII");
iconv_set_encoding("internal_encoding", "ASCII");
iconv_set_encoding("output_encoding", "ASCII");
return base64_encode( hash_hmac('sha256', $data, $key, true ) );
}