blockstack
Version:
The Blockstack Javascript library for authentication, identity, and storage.
64 lines (55 loc) • 1.8 kB
text/typescript
import Ripemd160Polyfill from 'ripemd160-min'
import { isNodeCryptoAvailable } from './cryptoUtils'
type NodeCryptoCreateHash = typeof import('crypto').createHash
export interface Ripemd160Digest {
digest(data: Buffer): Buffer
}
export class Ripemd160PolyfillDigest implements Ripemd160Digest {
digest(data: Buffer): Buffer {
const instance = new Ripemd160Polyfill()
instance.update(data)
const hash = instance.digest()
if (Array.isArray(hash)) {
return Buffer.from(hash)
} else {
return Buffer.from(hash.buffer)
}
}
}
export class NodeCryptoRipemd160Digest implements Ripemd160Digest {
nodeCryptoCreateHash: NodeCryptoCreateHash
constructor(nodeCryptoCreateHash: NodeCryptoCreateHash) {
this.nodeCryptoCreateHash = nodeCryptoCreateHash
}
digest(data: Buffer): Buffer {
try {
return this.nodeCryptoCreateHash('rmd160').update(data).digest()
} catch (error) {
try {
return this.nodeCryptoCreateHash('ripemd160').update(data).digest()
} catch (_err) {
console.log(error)
console.log('Node.js `crypto.createHash` exists but failing to digest for ripemd160, falling back to js implementation')
const polyfill = new Ripemd160PolyfillDigest()
return polyfill.digest(data)
}
}
}
}
export function createHashRipemd160() {
const nodeCryptoCreateHash = isNodeCryptoAvailable(nodeCrypto => {
if (typeof nodeCrypto.createHash === 'function') {
return nodeCrypto.createHash
}
return false
})
if (nodeCryptoCreateHash) {
return new NodeCryptoRipemd160Digest(nodeCryptoCreateHash)
} else {
return new Ripemd160PolyfillDigest()
}
}
export function hashRipemd160(data: Buffer) {
const hash = createHashRipemd160()
return hash.digest(data)
}