var crypto = require('crypto') /** * @param {Number} len */ var random = (len = 32) => { var buf = crypto.randomBytes(len) return buf.toString('hex') } /** * * @param {string} str */ var sha256 = (str, tostr = 'base64') => { return crypto.createHash('sha256').update(str).digest(tostr) } /** * * @param {string} str */ var genPassHash = (str) => { var hash = random(16) var pass = sha256(str + hash) return `$${hash}$${pass}` } /** * * @param {string} plain * @param {string} hash */ var comparePass = (plain, hash) => { var match = hash.match(/^\$(.+?)\$(.+)$/) if (match == null || match.length < 3 || !match[1] || !match[2]) return false var pass = sha256(plain + match[1]) if (pass === match[2]) return true return false } const pbkdf2 = (pass, salt, count, len, tostr = false) => { let hlen = crypto.createHash('sha256').update('').digest().length let blockCount = Math.ceil(len / hlen) let s256 = (s) => { return crypto.createHash('sha256').update(s).digest() } let out = [] for (let i = 0; i < blockCount; i++) { let loopBuf = Buffer.alloc(4) loopBuf.writeInt32BE(i) let saltBuf = Buffer.from(salt) let last = Buffer.concat([saltBuf, loopBuf], saltBuf.length + loopBuf.length) let passBuf = Buffer.from(pass) last = s256(Buffer.concat([passBuf, last], passBuf.length + last.length)) let xor = Buffer.from(last) for (let j = 1; j < count; j++) { last = s256(Buffer.concat([passBuf, last], passBuf.length + last.length)) xor = last.map((t, idx) => { return t ^ xor[idx] }) } out.push(xor) } let olen = 0 for (let i in out) { olen += out[i].length } let raw = Buffer.concat([...out], olen) if (!tostr) { return raw.slice(0, len) } else { return Buffer.from(raw.slice(0, len)).toString('hex') } } module.exports = { random, sha256, genPassHash, comparePass, pbkdf2 }