如何在PHP中复制这种C#哈希?(toByteArray(),ComputeHash())
我试图在如何在PHP中复制这种C#哈希?(toByteArray(),ComputeHash()),c#,php,sha1,hmac,C#,Php,Sha1,Hmac,我试图在PHP中复制以下代码,这是我必须使用的API的示例代码(API和示例代码在C#中,我的应用程序在PHP5.3中)。我不是C#developer,所以在这方面遇到了麻烦 // C# Code I am trying to replicate in PHP var apiTokenId = 1887; var apiToken = "E1024763-1234-5678-91E0-T32E4E7EB316"; // Used to authenticate our request by t
PHP
中复制以下代码,这是我必须使用的API的示例代码(API和示例代码在C#
中,我的应用程序在PHP5.3
中)。我不是C#developer,所以在这方面遇到了麻烦
// C# Code I am trying to replicate in PHP
var apiTokenId = 1887;
var apiToken = "E1024763-1234-5678-91E0-T32E4E7EB316";
// Used to authenticate our request by the API (which is in C#)
var stringToSign = string.Empty;
stringToSign += "POST"+"UserAgent"+"http://api.com/post";
// Here is the issue, How can I do the following 3 lines in PHP?
// No "secret key" provided?.. How do I do this in PHP?
var hmacsha1 = new HMACSHA1(new Guid(apiToken).toByteArray());
// Make a byte array with ASCII encoding.
byte[] byteArray = System.Text.Encoding.ASCII.GetBytes(stringToSign);
// Finally, 'computeHash' of the above (what does this do exactly?!)
var calculatedSignature = Convert.ToBase64String(hmacsha1.ComputeHash(byteArray));
我已经尝试过使用我在网上找到的许多变体和其他功能,但是没有任何东西可以比较,我不知道我是否做对了
任何C#dev都可以运行上面的代码并发布生成的值,以便我可以使用它来检查/测试吗
我已经试着检查了,看看这些方法是怎么做的,但是我被卡住了(不确定它是否正确,因为我没有什么可以比较的)
PHP伪代码
这听起来很简单,但我不确定这些C#方法中的一些能做什么
这些C#
方法做什么/返回什么?
-计算到什么?。。归还什么ComputeHash(byteArray)
System.Text.Encoding.ASCII.GetBytes(stringToSign)代码>-返回什么
new-HMACSHA1(新的Guid(apiToken.toByteArray())代码>没有密钥?使用的密钥是什么
JSFiddle
但对于C#
?),以便查看每行的输出
更新-已添加赏金 在这方面仍然有问题,我已经设法在Visual Studio中测试了
C#
代码,但是在PHP
中生成相同的哈希时遇到了问题
我想。。。
。。上面的C#
代码(特别是创建SHA1
hash的3行代码)将被转换为PHP(查看上面发布的Pseudo code
I)。我应该能够使用PHP匹配C#
hash
如果您还有其他问题,请提问。当我不需要测试代码时,这很容易:p -这相当于HMACSHA1 c级 字符串hash_hmac(字符串$algo,字符串$data,字符串$key[,bool$raw_output=false]) 所以$algo=“sha1” $data是您的$stringToSign——因为它已经是ascii字符串(我希望如此)——C#只是取了相同的字节等价物 新Guid(apiToken).toByteArray()->这是Guid的16字节(16*8=128)表示形式,即32*4=128位。这是关键 $key是一个字符串,因此您需要$apiToken的等效ASCII字符串(即32个十六进制字符-第一条带/忽略中间的破折号)-E10247631234567891E0T32E4E7EB316(更正该键-它不能有“T”) 这将返回一个二进制字符串-您需要将其转换为base64编码
$final = base64_encode ($almostResult)
这应该可以做到…享受:)问题是GUID的字符串形式颠倒了GUID前3段中2个字符的十六进制数的顺序。有关更多信息,请参见示例中的注释: 以下代码应该可以工作:
$apiTokenId = 1887;
$apiToken = "E1024763-1234-5678-91E0-FF2E4E7EB316";
$stringToSign = '';
$hexStr = str_replace('-','',$apiToken);
$c = explode('-',chunk_split($hexStr,2,'-'));
$hexArr = array($c[3],$c[2],$c[1],$c[0],$c[5],$c[4],$c[7],$c[6],$c[8],$c[9],$c[10],$c[11],$c[12],$c[13],$c[14],$c[15]);
$keyStr = '';
for ($i = 0; $i < 16; ++$i) {
$num = hexdec($hexArr[$i]);
$keyStr .= chr($num);
}
$stringToSign .= "POST" . "UserAgent" . "http://api.com/post";
$hmacsha1 = base64_encode(hash_hmac('sha1',$stringToSign,$keyStr,true));
$apiTokenId=1887;
$apiToken=“E1024763-1234-5678-91E0-FF2E4E7EB316”;
$stringToSign='';
$hexStr=str_replace('-','$apitonk);
$c=爆炸('-',块分割($hexStr,2'-');
$hexArr=数组($c[3],$c[2],$c[1],$c[0],$c[5],$c[4],$c[7],$c[6],$c[8],$c[9],$c[10],$c[11],$c[12],$c[13],$c[14],$c[15];
$keyStr='';
对于($i=0;$i<16;++$i){
$num=hexdec($hexArr[$i]);
$keyStr.=chr($num);
}
$stringToSign.=“POST”。“用户代理”。"http://api.com/post";
$hmacsha1=base64_编码(hash_hmac('sha1',$stringToSign,$keyStr,true));
我已经用上面提供的C代码测试了这段代码,结果是一样的。但是,原始代码中指定的GUID无效,因此我不得不稍微更改它。我遇到了几乎相同的问题,在谷歌搜索之后,我发现了以下帖子: 在PHP中,字符串已经是字节数组了。您遇到的具体问题是什么
对我来说,解决方案只是
base64_encode('apikey')
您是否阅读了文档以了解您提出的任何问题?1) ComputeHash对字节数组进行散列,在本例中使用HMACSHA1。2) Encoding.ASCII.GetBytes返回以ASCII编码的字符串(作为字节)。3) 您正在向HMACSHA1.var apiToken=“E1024763-1234-5678-91E0-T32E4E7EB316”的构造函数提供密钥;那是打字错误吗?GUIDs不能有一个“t”-所有十六进制:)@JonSkeet我发现在问了这个问题后不久,我的问题是用PHP做等价的事情,我知道我需要hash_hmac func,但不知道我需要hexdec,现在想一想,这只是一个与PHP相关的问题,我只想掩盖我的私人问题,我用一些随机字符替换了它,你的眼睛很敏锐;)
$almostResult = hash_hmac ("sha1" , $stringToSign, $hexKey, true)
$final = base64_encode ($almostResult)
$apiTokenId = 1887;
$apiToken = "E1024763-1234-5678-91E0-FF2E4E7EB316";
$stringToSign = '';
$hexStr = str_replace('-','',$apiToken);
$c = explode('-',chunk_split($hexStr,2,'-'));
$hexArr = array($c[3],$c[2],$c[1],$c[0],$c[5],$c[4],$c[7],$c[6],$c[8],$c[9],$c[10],$c[11],$c[12],$c[13],$c[14],$c[15]);
$keyStr = '';
for ($i = 0; $i < 16; ++$i) {
$num = hexdec($hexArr[$i]);
$keyStr .= chr($num);
}
$stringToSign .= "POST" . "UserAgent" . "http://api.com/post";
$hmacsha1 = base64_encode(hash_hmac('sha1',$stringToSign,$keyStr,true));