0

我正在使用 Javascript Forge 获取一些数据的摘要,现在实验使用不同的文档,以下代码行总是返回相同的哈希:

function obtainData() {
    getDocument(getHash);
}

function getDocument(callback) {
    var file = dInput.files[0];
    var reader = new FileReader();
    reader.onload = function(e){
        var contents = e.target.result;
        var array = callback(contents)
        console.log(array.digest().toHex());
    }
    reader.readAsArrayBuffer(file);
}

function getHash(buffer) {
    digestHash = forge.md.sha256.create();
    digestHash.update(buffer);
    //always the same with different bytes everytime
    console.log(digestHash.digest().toHex());
    return digestHash;
}

为什么会这样?我错过了什么吗?

尝试了不同的浏览器,但仍然是相同的 digestHash 值

4

3 回答 3

2

Forge 库通常与 Uint8 一起使用。将内容转换为 Uint8Array 应该可以正常工作

reader.onload = function(e){
    var contents = e.target.result;
    var  binary = arrayBufferToString(contents);
    var array = callback(binary)
    console.log(array.digest().toHex());
}


function arrayBufferToString( buffer ) {
    var binary = '';
    var bytes = new Uint8Array( buffer );
    var len = bytes.byteLength;
    for (var i = 0; i < len; i++) {
        binary += String.fromCharCode( bytes[ i ] );
    }
    return binary;
}

使用 WebCryptographiApi 也是一个不错的解决方案

function obtainData() {
  getDocument(getHash);
}

function arrayBufferToString( buffer ) {
  var binary = '';
  var bytes = new Uint8Array( buffer );
  var len = bytes.byteLength;
  for (var i = 0; i < len; i++) {
    binary += String.fromCharCode( bytes[ i ] );
  }
  return binary;
}

function getDocument(callback) {
  var file = dInput.files[0];
  var reader = new FileReader();
  reader.onload = function(e){
    var contents = e.target.result;
    var array = callback(contents)
    console.log(array.digest().toHex());
  }
  reader.readAsArrayBuffer(file);
}

function getHash(buffer) {
  digestHash = forge.md.sha256.create();
  digestHash.update(arrayBufferToString(buffer));
  return digestHash;
}
<script src="https://cdn.rawgit.com/artjomb/96b970358e20410fa64daa2e844aeb0f/raw/5375e7171ef297d436d65b962149dcc0e1960b2b/forge_v0.6.39.min.js"></script>
<input id="dInput" type="file">
<button onclick="obtainData()">hash</button>

于 2016-06-18T13:53:57.947 回答
1

不同文档或数据的所有哈希值都相同的原因是,试图消化的方法总是引用包含数据的对象([object Object]),所以它总是会得到相同的结果。所以,为了规避这个问题,我决定使用 webcrypto。

function getHash(buffer) {
    console.log(buffer);
    var crypto = window.crypto || window.msCrypto;
    var digestHash;

    var promise = crypto.subtle.digest({name:"SHA-256"},
    convertStringToArrayBufferView(buffer));

    promise.then(function (result) {
        digestHash = convertArrayBufferToHexadecimal(result);
        console.log(digestHash);
    });

    return digestHash;
}

function convertStringToArrayBufferView(str) {
    var bytes = new Uint8Array(str.length);
    for(var i = 0; i < str.length; i++){
        bytes[i] = str.charCodeAt(i);
    }
    return bytes;
}

function convertArrayBufferToHexadecimal(buffer) {
    var data_view = new DataView(buffer);
    var i, len, hex = '', c;
    for(i = 0, len = data_view.byteLength; i<len; i+=1){
        c = data_view.getUint8(i).toString(16);
        if(c.length < 2){
            c = '0' + c;
        }
        hex += c;
    }

    return hex;
}

我在http://qnimate.com/上找到了这个解决方案。有一节关于使用 WebCrypto 进行散列。

于 2016-06-17T20:00:06.227 回答
0

尝试像这样确定digestHash的范围:

function getHash(buffer) {
    // in your post the below line is missing 'var'
    // without the below 'var' digestHash will be global
    var digestHash = forge.md.sha256.create(); 
    digestHash.update(buffer);
    //always the same with different bytes everytime
    console.log(digestHash.digest().toHex());
    return digestHash;
}
于 2016-06-16T22:01:13.723 回答