I would like to use the Fetch API in a browser extension to download a resource and compute a hash thereof. The following works (using crypto through Browserify)
fetch(url).then(function(response) {
return response.blob();
}).then(function(data) {
var a = new FileReader();
a.readAsBinaryString(data);
a.onloadend = function() {
var hash = crypto.createHash(hashType);
hash.update(a.result, 'binary');
return hash.digest('hex');
};
})
but has the disadvantage that I have to wait for a.onloadend
while the context in which I'd like to embed it requires a Promise
to be returned. Also, it seems quite weird to first fetch the entire blob, then read it into a FileReader
just to dump it into createHash
afterwards.
Any hints?
The crypto hash.update
method also takes a buffer, so there is no need to make a detour via a FileReader
. Just do
fetch(url).then(function(response) {
return response.arrayBuffer();
}).then(function(arrayBuffer) {
var buffer = require('buffer')(new Uint8Array(arrayBuffer));
var hash = require('crypto').createHash(hashType);
hash.update(buffer, 'binary');
return hash.digest('hex');
})
If that doesn't work, you can easily promisify a FileReader
:
function getResult(reader) {
return new Promise(function(resolve, reject) {
reader.onload = function() {
resolve(this.result);
};
reader.onerror = reader.onabort = reject;
});
}
and use it like this:
fetch(url).then(function(response) {
return response.blob();
}).then(function(data) {
var a = new FileReader();
a.readAsBinaryString(data);
return getResult(a);
}).then(function(result) {
var hash = crypto.createHash(hashType);
hash.update(result, 'binary');
return hash.digest('hex');
})
I think what you're asking for here is promise chaining. You can create a promise inside the then
handler and return it.
var yaypromise = fetch(url).then(function(response) {
return response.blob();
}).then(function(data) {
return new Promise(function(resolve, reject){
var a = new FileReader();
a.readAsBinaryString(data);
a.onloadend = function() {
var hash = crypto.createHash(hashType);
hash.update(a.result, 'binary');
resolve(hash.digest('hex'));
};
});
})
And then yaypromise
is probably the promise you're looking for. It will resolve with hash.digest('hex')
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With