| import crypto from 'crypto'; |
| |
| |
| const KEYLEN = 64; |
| const SALT_BYTES = 16; |
| export function hashPassword(password) { |
| const salt = crypto.randomBytes(SALT_BYTES); |
| const hash = crypto.scryptSync(password, salt, KEYLEN); |
| return `scrypt$${salt.toString('hex')}$${hash.toString('hex')}`; |
| } |
| export function verifyPassword(password, stored) { |
| const parts = stored.split('$'); |
| if (parts.length !== 3 || parts[0] !== 'scrypt') |
| return false; |
| const salt = Buffer.from(parts[1], 'hex'); |
| const expected = Buffer.from(parts[2], 'hex'); |
| let actual; |
| try { |
| actual = crypto.scryptSync(password, salt, expected.length); |
| } |
| catch { |
| return false; |
| } |
| |
| return actual.length === expected.length && crypto.timingSafeEqual(actual, expected); |
| } |
| |