Encryption protects readable information by converting it into a form unauthorized parties cannot read. It makes it possible to move secrets across public networks and to protect sensitive stored data without requiring every attacker-proof detail of the underlying algorithms. section 3.0 section 3.1
For web applications, the practical question is where an attacker might obtain data: while it travels over a network, after it reaches a database or log file, or inside information kept in the browser. Encryption addresses confidentiality; hashing and digital signatures address related but different risks such as password storage and tampering detection. section 3.11 section 9.10
Apply encryption according to the data and threat involved:
- Protect data in transit with public-key encryption. Obtain and deploy a digital certificate, redirect HTTP traffic to HTTPS, and add HSTS. section 3.11
- Protect sensitive data at rest, including databases and log files, when exposure of stored files would reveal private information. section 3.11
- Keep confidential client-side session data encrypted or outside the session. A signature alone can reveal tampering but does not prevent a client from reading the contents. section 9.10
- Store password hashes rather than plain-text passwords. Use a strong hashing algorithm with salt and pepper so a stolen database is less useful to an attacker. section 3.11 section 3.8
A stolen password database
If an attacker obtains a database backup or leaked database credentials, plain-text passwords can be used to enter accounts and tried on other services. With hashed passwords, login checking recalculates the submitted password’s hash and compares it with the stored value, while recovering the original password is difficult. section 3.8
/**
* Unsign and decode the given `input` with `secret`,
* returning `false` if the signature is invalid.
*/
exports.unsign = function(input, secret){
var tentativeValue = input.slice(0, input.lastIndexOf('.')),
expectedInput = exports.sign(tentativeValue, secret),
expectedBuffer = Buffer.from(expectedInput),
inputBuffer = Buffer.from(input);
return (
expectedBuffer.length === inputBuffer.length &&
crypto.timingSafeEqual(expectedBuffer, inputBuffer)
) ? tentativeValue : false;
};
The listing shows signature verification for a client-supplied value: it rejects a modified value, but signature validation does not make session contents secret. Encrypt data the client must not read. section 9.10
Do not treat every cryptographic control as interchangeable. Encryption hides information; a digital signature or HMAC lets a server detect altered session state or JWT payloads; hashing supports password verification and integrity checking. Validate a JWT signature before treating it as an authentication token. section 3.11 section 9.10















