3.9 KiB
primitives/crypto-pwhash
(no submodules)
Purpose
cryptoPwhashStr and cryptoPwhashStrVerify expose libsodium's Argon2id password hashing via crypto_pwhash_str and crypto_pwhash_str_verify. Argon2id is the winner of the Password Hashing Competition (2015) and the recommended algorithm for password storage by OWASP and NIST SP 800-63B.
The encoded hash string includes the algorithm identifier, salt, and cost parameters — it is self-contained and safe to store directly in a database. This eliminates a class of bugs where the salt or parameters are stored separately and can become desynchronised.
Features
- Argon2id password hashing via
crypto_pwhash_str— salt generated internally. - Self-contained encoded output (≈97 chars) — includes algorithm, salt, opsLimit, memLimit.
- Constant-time verification via
crypto_pwhash_str_verify. - Configurable
opsLimitandmemLimit— defaults toOPSLIMIT_INTERACTIVE/MEMLIMIT_INTERACTIVE. - Async — calls
sodiumReady()internally. cryptoPwhashStrVerifyreturnsfalseon any failure, never throws.
Usage: Basic Example
import { cryptoPwhashStr, cryptoPwhashStrVerify } from "@suaveplan/crypto-sodium/primitives/pwhash";
const password = new TextEncoder().encode("user-password-here");
const hash = await cryptoPwhashStr(password);
// Store `hash` in your database. Later, at login:
const valid = await cryptoPwhashStrVerify(hash, password);
console.log(valid); // true
Usage: Advanced Example
Higher-security settings for sensitive credential storage:
import { cryptoPwhashStr, cryptoPwhashStrVerify } from "@suaveplan/crypto-sodium/primitives/pwhash";
const password = new TextEncoder().encode("admin-master-password");
// Sensitive account — use MODERATE or SENSITIVE preset values
// crypto_pwhash_OPSLIMIT_MODERATE = 3, MEMLIMIT_MODERATE = 268435456 (256 MiB)
const hash = await cryptoPwhashStr(password, {
opsLimit: 3,
memLimit: 268_435_456,
});
// Verification automatically reads cost parameters from the hash string
const ok = await cryptoPwhashStrVerify(hash, password);
// Password rehashing: if ok but hash uses lower-cost params, rehash
// (the encoded string embeds the params so you can detect this)
API Reference
cryptoPwhashStr(password, opts?): Promise<string>
Hashes password with Argon2id.
Parameters:
password: Uint8Array— Raw password bytes.opts.opsLimit?: number— CPU/iteration cost. Default:crypto_pwhash_OPSLIMIT_INTERACTIVE.opts.memLimit?: number— Memory cost in bytes. Default:crypto_pwhash_MEMLIMIT_INTERACTIVE.
Returns: Promise<string> — Argon2id-encoded hash string, safe for database storage.
cryptoPwhashStrVerify(hash, password): Promise<boolean>
Verifies password against an encoded hash string.
Parameters:
hash: string— Encoded hash fromcryptoPwhashStr.password: Uint8Array— Candidate password bytes.
Returns: Promise<boolean> — true if the password matches. Returns false (not throws) on any failure including malformed hash strings.
interface PwhashOptions
opsLimit?: numbermemLimit?: number
Implementation Notes
crypto_pwhash_str generates a random salt internally and encodes the full Argon2id parameter set into the output string. This is the $argon2id$v=19$... format, compatible with most password-hashing libraries. The salt is never exposed to the caller.
crypto_pwhash_str_verify uses constant-time comparison for the hash check. The try/catch maps libsodium exceptions (e.g., malformed hash strings, wrong length) to false for uniform API behaviour.
The interactive preset (OPSLIMIT_INTERACTIVE, MEMLIMIT_INTERACTIVE) is calibrated for ≈50 ms on typical hardware. Increase opsLimit and memLimit for stored API keys, encryption master passwords, or recovery codes.