no-math-random-crypto
Disallow Math.random() for cryptographic purposes (tokens, keys, secrets, salts, IVs)
Detects Math.random() used in a cryptographic context in Node.js code. Math.random() is a non-cryptographic PRNG: its output is predictable and must never seed tokens, keys, passwords, salts, IVs, nonces, or session identifiers. This rule is part of eslint-plugin-node-security and provides LLM-optimized error messages with fix suggestions.
🚨 Security rule | 💡 Provides suggestions | ⚠️ Set to error in recommended
Migrated from the deprecated standalone
cryptoplugin intoeslint-plugin-node-security, which now ships every cryptography rule that plugin had — including this one.
Rule Details
The rule flags Math.random() only when the value flows into a cryptographic context, so benign randomness (shuffles, jitter, sampling, UI) does not trigger it. A context is treated as cryptographic when the result is:
- assigned to a variable or property whose name matches
token,key,secret,password,salt,iv,nonce,seed,session,csrf,otp,pin,auth,verify, etc.; or - returned from a function whose name suggests credential/token generation.
❌ Incorrect
function generateSessionToken() {
return Math.random().toString(36).substring(2); // CWE-338: predictable token
}
const apiKey = Math.random().toString(36);✅ Correct
import { randomBytes, randomUUID } from 'node:crypto';
function generateSessionToken() {
return randomBytes(32).toString('hex');
}
const requestId = randomUUID();
// Non-crypto randomness is fine — not flagged
const j = Math.floor(Math.random() * deck.length);Options
| Option | Type | Default | Description |
|---|---|---|---|
allowInTests | boolean | true | Allow Math.random() in test files. Default: true |
secretWords | string[] | ["token","tokens","key","keys","secret","secrets","password","passwd","salt","iv","nonce","seed","hash","cipher","auth","session","csrf","otp","pin","code","codes","verify","signature","credential","jwt","encryption","apikey","passphrase","mnemonic"] | Words that name a security value in this codebase. Replaces the default list. |
correlationIdWords | string[] | ["request","req","correlation","trace","span","transaction","txn","message","msg","event","job","run","task","batch","element","node","row","record","instance","component","widget","dom","operation","call","invocation","frame","render"] | Words that mark a trailing id as a correlation id rather than a credential. Replaces the default list. |
{
"node-security/no-math-random-crypto": ["error", { "allowInTests": false }]
}allowInTests(defaultfalse) — whentrue, allowsMath.random()in*.test.*/*.spec.*files.
When Not To Use
If your codebase never uses Math.random() for anything security-sensitive and you want zero overhead, you can disable it — but the context-aware heuristic is designed to stay silent on non-crypto randomness, so leaving it on error is recommended.
Further Reading
Did this rule catch something? Star the repo to get new CWE coverage as we ship it — or follow the AI-code-security benchmarks behind these rules.