TOTP Secret Generator
Generate a random Base32 secret (160 bits) for TOTP/HOTP (Google Authenticator, Authy, 1Password). Also creates a ready otpauth:// URL.
β
TOTP secrets explained
A TOTP secret is the shared symmetric key that an authenticator app (Google Authenticator, Authy, 1Password, Bitwarden, Microsoft Authenticator) and your server both hold so that they can independently compute the same six-digit code every 30 seconds. The algorithm is specified in RFC 6238 (2011), which extends the older HOTP standard (RFC 4226) by replacing the counter with a time-based moving factor. Each code is the result of HMAC-SHA1(secret, floor(unix_time / 30)) truncated to six digits β no network round-trip is required at the moment the user types it.
The RFC recommends a secret of 160 bits (20 bytes), which matches the output size of SHA-1; many services accept anything between 80 and 160 bits, but going below 128 bits weakens the scheme against brute-force search of the key space. The bytes are encoded in Base32 (RFC 4648, no padding, alphabet A-Z2-7) precisely because the characters 0, 1, 8 and 9 are excluded β they are visually ambiguous when a user has to type the key by hand from a screenshot or a printed setup sheet.
The otpauth URI and QR enrollment
To onboard a user, servers usually emit an otpauth:// URI rendered as a QR code:
otpauth://totp/Acme:[email protected]?secret=JBSWY3DPEHPK3PXP&issuer=Acme&algorithm=SHA1&digits=6&period=30
The query string carries the Base32 secret, the human-readable issuer, the HMAC algorithm (SHA-1 is universal; SHA-256 and SHA-512 are allowed but rarely supported by mobile apps), the number of digits (6 by default, 8 occasionally) and the step in seconds (30 by default). On the server side, the verifier accepts the current window plus one window before and one after β that one-step tolerance absorbs the inevitable clock drift between the user's phone and the server.
Hardening checklist
- Generate the secret with a CSPRNG (
crypto.randomBytes(20)in Node,secrets.token_bytes(20)in Python). - Display the secret once during enrollment; never log it and never store it in plain text β encrypt it at rest the same way you would a password hash key.
- Reject a code that was already consumed within the same 30-second window to neutralise replay attacks over a leaked terminal.
- Emit one-time recovery codes at enrollment so the user can sign in if the phone is lost.
- Rate-limit the verify endpoint β six digits is only one in a million, brute force is realistic without throttling.
Travel and clock drift
TOTP depends on a synchronised UTC clock on both ends; the user-facing time zone is irrelevant because the algorithm hashes a UTC-based step counter. In practice, problems show up only when the phone's clock is set manually, when it has been offline for days with a weak crystal, or when a desktop OS skipped its NTP sync after suspend. If a user reports "the code is always wrong", check device time before anything else β server-side, log the step offset of accepted codes for a few days to spot devices drifting outside the Β±1 window.
FAQ
Does the authenticator app need internet to produce codes? No. TOTP is fully offline β both sides only need a synchronised clock and the shared secret. That is the killer property over SMS or email codes, which depend on a delivery channel.
I lost my phone β can I recover the account? Only via the recovery codes issued at enrollment, an admin reset, or a backup channel. The secret itself cannot be recovered from a code; that is the whole point of HMAC.
Is TOTP really better than SMS 2FA? Yes. SMS is vulnerable to SIM swap, SS7 interception and phishing of the delivered code. TOTP keeps the secret on the device and never transmits anything that could be intercepted.
Why SHA-1 in 2026? The HMAC construction is not affected by the SHA-1 collision attacks (which target the unkeyed hash). Every authenticator app supports SHA-1 universally; switching to SHA-256 breaks compatibility with most consumer apps for no measurable security gain.
Is the secret generated here sent anywhere? No. Generation happens entirely in your browser using crypto.getRandomValues() β nothing crosses the network.
Related Tools
Handwriting Generator
Convert typed text into an image with handwriting appearance. Useful for adding a personal touch to digital work.
Resume Generator
Fill a simple printable A4 CV from a form with personal data, education and experience.
Favicon Generator
Generate a favicon from text/emoji in all common sizes (16, 32, 48, 64, 192, 512). PNG download.