security · Browser tool
Password Generator & Tester
Random passwords and passphrases drawn from the browser's cryptographic random source, with the arithmetic behind the strength figure shown rather than hidden.
Random password
Passphrase
The word list built into this page holds 512 words, so each word is worth exactly 9 bits. That is smaller than the EFF long list, which has 7,776 words and gives 12.9 bits per word, so a passphrase here needs roughly a third more words for the same strength.
Test a password you already use
Typed here, this value stays in the page and is never sent anywhere — but a shared or public machine is still the wrong place to type a live password. The figure below is an upper bound: it assumes the password was drawn at random from the characters it contains. A password built from a word and a year is far weaker than its character count suggests, which is why the notes above it matter more than the number.
Where the randomness comes from
Every character and every word on this page comes from crypto.getRandomValues, the browser's cryptographically secure random source. Math.random is not used anywhere, and it should never be used for a password: it is a fast pseudo-random generator whose internal state can be recovered from a handful of outputs.
Why modulo is not good enough
The obvious way to pick one of 72 characters is to take a random 32-bit number and reduce it modulo 72. That is subtly wrong. 232 is not a multiple of 72, so the first few characters of the alphabet come up slightly more often than the rest. The bias is tiny per character and it never washes out — it is a known skew an attacker can order their guesses around. This page uses rejection sampling instead: it discards any random value at or above the largest multiple of 72 below 232, then reduces. The loop occasionally runs twice; the result is exactly uniform.
What the entropy number means
Entropy here is length × log2(alphabet size), measured in bits. Twenty characters from a 72-character alphabet is about 123 bits. The figure describes the generator, not the string: it is how many bits of uncertainty an attacker faces who knows precisely how the password was made but not which one came out. Crack time follows from that, assuming on average half the space must be searched. The rate you choose matters more than most people expect — the same password that survives an online login form for centuries can fall in hours against a leaked database of fast unsalted hashes.
Forcing one of each class costs a little
Requiring at least one symbol, one digit and so on removes some strings from the pool, so the true entropy drops slightly below the figure shown. At twenty characters the loss is a small fraction of a bit and not worth worrying about; at eight characters with four required classes it is more noticeable. The option is off by default for that reason.
There is no breach check here
Asking whether a password appears in a known breach means sending something derived from it to the Have I Been Pwned range API. Even with the k-anonymity trick, where only the first five characters of the SHA-1 hash go over the wire, that is still a network request carrying data about your password — and this page makes no network requests at all, which is the whole point of it. So the check is absent rather than half-done. If you want it, run it knowingly on a site that tells you what it sends. A generated password of the length suggested here has effectively no chance of being in a breach list anyway; the check matters for passwords you chose yourself.