Script Valley
JWT & Session Auth: Deep Dive
Authentication FundamentalsLesson 1.5

password hashing with bcrypt: why plain storage is catastrophic

plaintext password risks, one-way hashing, bcrypt algorithm, salt rounds, bcrypt.hash, bcrypt.compare, timing attacks, cost factor tuning

Password Hashing with bcrypt

bcrypt Password Hashing

Never store passwords. Store hashes. This is non-negotiable — database breaches happen, and plaintext passwords compromise users across every site they reuse that password.

bcrypt is the standard choice. It is deliberately slow (making brute-force expensive), generates a random salt per hash (preventing rainbow table attacks), and bundles the salt into the output string.

const bcrypt = require('bcrypt');

// Hashing on registration
const saltRounds = 12;
const hash = await bcrypt.hash(plainPassword, saltRounds);
// Store `hash` in DB, discard plainPassword

// Verifying on login
const isMatch = await bcrypt.compare(inputPassword, storedHash);
// Returns true or false — bcrypt extracts the salt automatically

Salt rounds (also called cost factor) control how slow hashing is. 10 is the old default; 12 is the current practical minimum for new projects. Higher = slower to hash but also slower for attackers. At 12, each hash takes ~250ms on modern hardware — acceptable for login, prohibitive for bulk attacks.

Never implement your own hashing. MD5 and SHA-1 are not password hashing algorithms — they are fast by design, which makes them useless here. Use bcrypt, argon2, or scrypt. bcrypt has the widest ecosystem support in Node.js.