Javascript Sha256 vs PHP Sha256:换行创建不同的哈希?

问题描述:

添加换行符时,我得到两个不同的哈希值。Javascript Sha256 vs PHP Sha256:换行创建不同的哈希?

在这个网站上http://www.xorbin.com/tools/sha256-hash-calculator有一个JavaScript Sha256哈希生成器。

当我运行一个散列 “ONETWO” 我得到:

25b6746d5172ed6352966a013d93ac846e1110d5a25e8f183b5931f4688842a1 

当我使用PHP

echo hash('sha256', 'onetwo'); 

我得到:

25b6746d5172ed6352966a013d93ac846e1110d5a25e8f183b5931f4688842a1 

但是当我运行一个哈希来自包含换行符(返回)的URL,例如:

'one 
two' 

我得到:

21066d108d5319ecb5a1fc4454f42ef22fc5f1c7df49c31d90294950e0ea8b2c 

但我在使用PHP,我得到:

29a776bb35efe730dabb1b1d3ad74dbf80cc3e9009e168241798ea73adca3dcf 

任何一个可以指出为什么会是这样?为什么添加换行符会产生不同的结果?

这是我的PHP/HTML代码,你会看到我正在使用表单并提交要散列的数据。

<!DOCTYPE HTML> 
<html> 
    <head> 
    <title>Sha256 Hash</title> 
    </head> 
    <body> 
    <div style="float: left;"> 
     Start here and insert text below to be hashed.<br /> 
     <form name="submit hash" action="" method="POST"> 
     <textarea name="text" style="border: thin solid #000; width: 500px; padding: 10px; height: 500px;"><? if($_SERVER['REQUEST_METHOD'] == 'POST') echo $_POST['text']; ?></textarea> 
     <br style="clear: both;" /> 
     <input type="submit" name="submit" value="submit" /> 
     </form> 
    </div> 
    <? if($_SERVER['REQUEST_METHOD'] == 'POST'): ?> 
    <div style="border: thin solid #000; margin: 10px; padding: 10px; float: left;"> 
     <br />sha256:&nbsp;&nbsp;<b><?= hash('sha256',$_POST['text']); ?></b><br /> 
    </div> 
    <? endif; ?> 
    </body> 
</html> 
+2

作为一个方面说明,你不应该在PHP中使用短标签(' ... ?>'),因为出于便携性原因不鼓励使用它们,请参阅http://php.net/manual/en/language.basic-syntax。 phptags.php –

+0

@SteveWilford,注意谢谢! – simianIII

@mrjoltcola是正确的。

从textarea获取值时,新行是\ r \ n(CRLF)。

var_dump(urlencode($_POST['text'])); 

这将打印string(12) "one%0D%0Atwo"如果输入

one 
two 

其中%:

您可以通过打印字符串的URL编码版本,你念想,在你的PHP代码验证此0D是回车的html代码和换行符的%0A,你可以看到here

现在要获得与javascript version中相同的哈希值,您必须删除回车符。你可以做到这一点在PHP这样的:

$string_to_be_hashed = preg_replace("/\r\n/", "\n", $_POST['text']); 

然后,如果你哈希$string_to_be_hashed你会得到预期的结果。

在javascript版本中,这也发生在内部。如果您检查hash256 source code,则有一个Utf8Encode(string)函数,其中第一行是string = string.replace(/\r\n/g,"\n");,它基本相同。

+0

WOW,很好的回答和非常深入的。我给了你绿色检查,因为你比mrjoltcola更深入。现在我有一个问题。\ n \ n用\ n替换\ r \ n很重要吗?或者javascript网站只是将它作为一个首选? – simianIII

+0

我想这是一个偏好问题.Windows系统将新行代表为\ r \ n,而Linux将其表示为'\ n'。其他系统使用[这里]提到的其他表示法(https://en.wikipedia.org/wiki/Newline#Representations)。我的意见是,如果你要散列一个文件让用户上传它或其他东西),那么不要改变任何东西,否则,如果你想创建类似于JavaScript网站的东西,那么你可以选择一个默认的行为,但也提供了一个复选框或东西,让用户选择一个不同的新线代表 –

+0

谢谢!!如果我可以给你提示在这个网站上,我会的。 – simianIII

我希望它是回车和线之间的差值饲料(\ r \ n VS \ n)的

你的PHP在线测试字符串可能只有\n

该网站一个可能有\r\n

其次,这些被认为是内容的一部分。哈希它不会忽略它。

+0

谢谢你的回答......我最终给绿色Mastermaster,因为他真的深入了。我还会给你一个投票,除非我还没有资格进行投票:-( – simianIII