A time-based one-time password (TOTP) is a short code that changes every 30 seconds. Your authenticator app and the website both know a shared secret and the current time, so each can compute the same code on its own. The method is defined in RFC 6238, which builds on the counter-based HOTP in RFC 4226. Try it with the TOTP Generator.
The algorithm in five steps
- Turn time into a counter.
counter = floor(unix_time / 30). - HMAC the counter. Compute HMAC-SHA1 (or SHA-256/512) of the 8-byte big-endian counter, keyed with the secret. You can experiment with the HMAC Generator.
- Pick four bytes. The last nibble of the result is an offset; take the four bytes starting there.
- Clear the top bit. Mask with
0x7FFFFFFFso the number is positive. - Keep the last digits. Take the number modulo 10⁶ (for six digits), padded with zeros.
A verified example
The RFC 4226 test secret is the ASCII string 12345678901234567890, which in the Base32 form used by authenticator apps is GEZDGNBVGY3TQOJQGEZDGNBVGY3TQOJQ. For counters 0, 1 and 2, HOTP gives 755224, 287082 and 359152.
For TOTP, RFC 6238 uses time 59 seconds with a 30-second step and 8 digits:
| Step | Value |
|---|---|
| Counter | 59 ÷ 30 → 1 |
| HMAC-SHA1 | 75a48a19d4cbe100644e8ac1397eea747a2d33ab |
| Offset (last nibble) | 11 |
| Four bytes, top bit cleared | 1094287082 |
| Last 8 digits | 94287082 |
The six-digit version of the same code is 287082. Convert timestamps with the Unix Timestamp Converter to see which step a moment falls into.
What is in the QR code
The QR code holds an otpauth://totp/... link carrying the secret, issuer, number of digits, period and algorithm, for example otpauth://totp/Example:[email protected]?secret=GEZDGNBVGY3TQOJQGEZDGNBVGY3TQOJQ&issuer=Example&digits=6&period=30. Anyone who sees the secret can generate your codes, so treat it like a password.
Limits
| Method | Phishing resistant | Notes |
|---|---|---|
| SMS codes | No | Can be intercepted or SIM-swapped |
| TOTP app | No | Better than SMS, but a fake site can relay the code |
| Hardware key or passkey | Yes | Checks the site's real domain |
Common pitfalls
- Wrong clock. The most common cause of rejected codes.
- Losing the secret. Keep the backup codes or the original setup key somewhere safe, or you may be locked out.
- Pasting real secrets into web pages. Use the generator with test secrets only.
- Reusing a code. Each code is valid for one step; servers usually reject a replay.
See How to Generate Strong Passwords and Passphrases for the first factor, and HMAC and Multi-factor authentication (MFA) for definitions.