# Two-Factor Authentication, Explained

> Why a password alone isn't enough anymore, how the common second factors actually work under the hood, and which ones to trust with your real accounts.


---

# Two-Factor Authentication, Explained

You've clicked "enable two-factor authentication" a hundred times without really knowing what it changes under the hood. You know it makes you type a code, or tap a notification, or plug in a little USB key - and you know it's "more secure." But if someone asked you *why* a six-digit code stops an attacker who already has your password, could you answer? This guide answers that, along with which second factor is actually worth your time and which one is quietly the weakest.

## The phases

1. [One secret isn't enough](01-one-secret-isnt-enough.md) - why passwords alone fail, and the something-you-know/have/are framework.
2. [How the common methods actually work](02-how-the-methods-work.md) - SMS codes, authenticator apps, and hardware keys, and why they're not equally safe.
3. [What this means for you](03-what-this-means-for-you.md) - what to actually turn on, backup codes, and the recovery tradeoff nobody mentions.


---

# One Secret Isn't Enough

Think about what a password actually is: a single string of characters that, if anyone else ever learns it, gives them everything you have. That's the whole design. One secret, and whoever holds it gets in - the system has no way to tell you apart from an attacker who happens to know the same string. For most of the internet's history, that was considered good enough. It isn't anymore, and the reasons aren't really about password strength.

## The password isn't the weak point - the secrecy is

A long, random, unique password is genuinely hard to guess. That was never really the problem. The problem is keeping any secret secret across millions of people, thousands of services, and years of time. Three things break that secrecy constantly, none of which have anything to do with how "strong" the password looks:

**Reuse.** Most people use the same handful of passwords across many sites, because remembering forty unique ones isn't realistic. So when one site gets breached, attackers don't just have access to that one site - they have a password they can try on your email, your bank, your work account. This is called **credential stuffing**: taking leaked username/password pairs from one breach and testing them everywhere else, automatically, at massive scale.

**Phishing.** An attacker doesn't need to crack your password if they can trick you into handing it over. A fake login page that looks exactly like your bank's, an urgent email about a "suspicious sign-in," a text that looks like it's from your delivery company - all designed to get you to type your real password into a page you don't control. The password itself was never weak; you handed it over voluntarily, believing you were somewhere safe.

**Breaches.** Companies get hacked. Databases of usernames and passwords leak - sometimes hashed properly, sometimes not, sometimes years before anyone notices. You did nothing wrong and your password was excellent, and it's still sitting in a file on a criminal forum because the company that stored it failed to protect it.

> None of these three break because your password was weak. They break because a password is a single fact, and single facts leak, get guessed, or get handed over by mistake.

## The fix: stop relying on one kind of proof

Two-factor authentication (2FA) - also called multi-factor authentication (MFA) when there are more than two - doesn't try to make secrets leak-proof. It assumes they *will* leak sometimes, and asks for a second, *different kind* of proof before letting anyone in. The security world groups proof into three categories:

- **Something you know** - a password, a PIN, the answer to a security question. Lives in your memory. Can be phished, guessed, or leaked from a breach.
- **Something you have** - your phone, a hardware key, a bank card. A physical object. An attacker across the world can't type in something they don't physically possess.
- **Something you are** - a fingerprint, a face scan. Biometrics. Hard to steal remotely, though not impossible to fake, and unlike a password you can't "reset" it if it's ever compromised.

2FA means combining proof from **two different categories**. A password plus a security question doesn't count - both are "something you know," so anyone who phishes one can probably get the other with the same trick. A password plus a code from your phone counts, because an attacker who steals your password over a phishing email still doesn't have your physical phone sitting in your pocket.

```mermaid
flowchart LR
  A["Something you know<br/>(password)"] --> D{Access granted}
  B["Something you have<br/>(phone, key)"] --> D
  C["Something you are<br/>(fingerprint)"] --> D
```

*What this diagram means:* logging in with 2FA means clearing at least two of these gates from two different categories - not two passwords, not two questions, but two genuinely different kinds of proof.

## Why this actually stops real attacks

Walk through the credential-stuffing scenario again, but now with 2FA turned on. An attacker buys a leaked list of email/password pairs from an old breach and runs them against your accounts. Your password is on that list - it's a real match. Without 2FA, that's it, they're in. With 2FA, the login pauses and asks for the second factor: a code from an app, a tap on a hardware key. The attacker doesn't have your phone. They don't have your key. The password being correct stopped being enough.

This is the entire value of 2FA in one sentence: it turns "steal one thing" into "steal two different kinds of things, from two different places, usually at the same time" - and that jump in difficulty is what keeps most opportunistic attackers out, even when your password has already leaked somewhere you don't know about.

2FA doesn't make your account unhackable - a sufficiently motivated, well-resourced attacker who steals your unlocked phone *and* knows your password can still get in. What it does is take you out of the pool of soft targets: the accounts that fall to automated, high-volume attacks that only try the one thing they have. That's most attacks. Phase 2 gets into which second factors resist even the harder, targeted attacks, and which ones are more theater than protection.


---

# How the Common Methods Actually Work

Not all "something you have" is created equal. A text message, an app on your phone, and a physical key all satisfy the same 2FA checkbox - but they're built on completely different mechanisms, and those mechanisms determine which real-world attacks each one survives. This is the part most people skip, and it's the part that actually matters when you're deciding what to turn on.

## SMS codes - the familiar one, and the weakest

You log in, the site texts you a six-digit code, you type it in. It feels secure because it involves your phone, a physical object only you should have. The catch is that the code doesn't actually depend on your phone at all - it depends on your **phone number**, and a phone number is a routing address controlled by your carrier, not a secret tied to a specific SIM card in your hand.

That distinction is exactly what **SIM-swap fraud** exploits. An attacker calls your mobile carrier, or bribes/tricks a support rep, and convinces them to move your phone number onto a SIM card the attacker controls - no access to your actual phone required. From that moment, every SMS code meant for you goes straight to the attacker instead. Combined with a leaked password, a SIM swap gives full account takeover, and the victim usually only finds out when their phone suddenly loses signal.

```mermaid
sequenceDiagram
  participant Attacker
  participant Carrier
  participant Victim
  Attacker->>Carrier: "I lost my SIM, please transfer my number"
  Carrier-->>Attacker: Number now routes to attacker's SIM
  Victim->>Victim: Phone loses signal, unaware why
  Attacker->>Attacker: Receives victim's SMS 2FA codes
```

*What this diagram means:* the weak link isn't cryptography, it's a phone company's customer support process. The code itself is never cracked - it's delivered to the wrong device because the routing underneath it got hijacked.

SMS also travels over the carrier network in a way that, in some setups, can be intercepted through other network-level tricks entirely separate from SIM swapping. None of this means SMS 2FA is worthless - it still stops the huge majority of automated credential-stuffing attacks, because most attackers running those at scale aren't going to individually target your phone carrier. But against anyone willing to make a phone call, it's the thinnest of the three options.

## Authenticator apps (TOTP) - no network required

Apps like Google Authenticator, Authy, or 1Password's built-in generator show a six-digit code that changes every 30 seconds. Unlike SMS, nothing gets transmitted to generate that code - it's computed entirely on your device, offline.

Here's the mechanism, conceptually (no need to work through the actual math): when you scan the QR code to set up 2FA, the service and your app agree on a **shared secret** - a long random string neither of you ever transmits again after that one setup moment. From then on, both your app and the service's server independently run the same algorithm on two inputs: that shared secret, and the current time. This is called **TOTP** - Time-based One-Time Password. Because both sides know the secret and both sides have a clock, they arrive at the same six-digit code without ever needing to talk to each other again.

```mermaid
flowchart LR
  S["Shared secret<br/>(set up once, via QR code)"] --> T["+ Current time"]
  T --> A["Your app computes: 493 821"]
  T --> B["Server computes: 493 821"]
  A -.matches.-> B
```

*What this diagram means:* the code your app shows and the code the server expects are calculated separately, from the same two ingredients, and they agree because both sides run the same formula. No code ever travels over SMS or the internet to get generated - only the one-time shared secret did, once, at setup.

This is why TOTP survives SIM swapping entirely: there's no phone number involved, so hijacking one does nothing. It's also why it works with your phone in airplane mode - the calculation needs a clock, not a signal. The one thing TOTP does depend on is that shared secret staying secret and the clocks staying roughly in sync (which is why setup usually warns you if your phone's clock drifts).

TOTP isn't immune to everything, though. A convincing phishing page can show you a fake login form, take both your password *and* the six-digit code you just typed, and relay both to the real site within the 30-second window before the code expires. This is called a **real-time phishing relay**, and it's the reason the next method exists.

## Hardware keys (WebAuthn) - phishing-resistant by design

A hardware security key (YubiKey, Google Titan, and similar) plugs into a USB port or taps over NFC, and you press a button on it to confirm a login. The mechanism behind it - a web standard called **WebAuthn** - is built specifically to close the one gap TOTP still has: it makes phishing structurally impossible, not just harder.

The key insight is *who* checks that you're on the real site. With a password or a TOTP code, **you** are the one deciding whether the page in front of you looks legitimate - and a good enough fake can fool a human. With WebAuthn, your **browser** performs that check automatically, as part of the protocol itself, before it ever lets the hardware key respond. The browser knows the actual domain it's connected to; a phishing site at `yourbank-login.com` is a different domain from `yourbank.com`, full stop, no matter how identical the page looks to a human eye.

```mermaid
sequenceDiagram
  participant You
  participant Browser
  participant Key as Hardware Key
  participant Real as Real Site
  participant Fake as Phishing Site
  You->>Browser: Visits fake-lookalike-site.com
  Browser->>Browser: Checks domain against key's registration
  Browser--xKey: Refuses to even ask the key to respond
  You->>Browser: Visits real-site.com
  Browser->>Key: Domain matches - ask for signature
  Key->>Real: Signed response, tied to this exact domain
```

*What this diagram means:* the hardware key never even gets asked to respond on the wrong domain, because the browser itself blocks that request before it reaches the key. There's no human judgment call to fool - the check happens in software, against the literal domain string, every single time.

That's the phrase "phishing-resistant" earning its keep: it's not that a human using a hardware key is more careful, it's that the deciding check moved from a person (who can be tricked) to the browser (which cannot be talked into ignoring a domain mismatch).

## The tradeoff across all three

```text
SMS codes         -> easiest to set up, no app needed, weakest (SIM-swap risk)
Authenticator app -> no network dependency, resists SIM swaps, still phishable in real time
Hardware key       -> phishing-resistant by design, requires buying/carrying a physical device
```

None of these are wrong choices in every situation - a bank account and a forum login don't carry the same stakes. What matters is knowing that "I have 2FA on" isn't one fact, it's a spectrum, and the method you picked determines exactly which attacks it stops.

```quiz
[
  {
    "q": "Why does a SIM-swap attack defeat SMS-based 2FA?",
    "choices": [
      "It cracks the six-digit code mathematically",
      "It reroutes your phone number to the attacker's SIM, so the code goes to them",
      "It intercepts the code from inside your phone's operating system",
      "It guesses the code using your carrier's default settings"
    ],
    "answer": 1,
    "explain": "The code isn't broken - it's delivered to the wrong device because the attacker convinced the carrier to move your number onto their SIM."
  },
  {
    "q": "What two inputs does a TOTP authenticator app combine to generate its six-digit code?",
    "choices": [
      "Your password and your username",
      "A shared secret set up once, and the current time",
      "Your phone number and the site's IP address",
      "A code sent by the server every 30 seconds"
    ],
    "answer": 1,
    "explain": "Both your app and the server independently compute the same code from a secret agreed at setup plus the current time - no network round trip needed to generate it."
  },
  {
    "q": "What makes hardware keys (WebAuthn) \"phishing-resistant\" in a way TOTP codes are not?",
    "choices": [
      "The key has a longer, harder-to-guess secret",
      "The browser checks the actual domain before the key responds, removing the human judgment call",
      "Hardware keys don't use cryptography at all",
      "The key refuses to work unless you're on your home network"
    ],
    "answer": 1,
    "explain": "With TOTP, a convincing fake page can still trick a human into typing a valid code into it. With WebAuthn, the browser itself verifies the domain before the key ever responds, so a lookalike site can't complete the exchange."
  }
]
```

Watch it animated: [two-factor authentication](/explainers/TwoFactor.dc.html)


---

# What This Means for You

Knowing how SMS, TOTP, and hardware keys differ is only useful if it changes what you actually do next. This phase is the practical payoff: what to turn on, what to keep in a safe place, and the one failure mode that catches people who did everything else right.

## What to actually enable

Given the tradeoffs from Phase 2, a simple ranking holds up in practice:

```text
1st choice: Hardware key (WebAuthn) or your phone's built-in passkey  -> for anything that matters
2nd choice: Authenticator app (TOTP)                                   -> the solid default everywhere else
3rd choice: SMS codes                                                  -> better than nothing, not much more
```

For accounts where a takeover would genuinely hurt - your primary email, your password manager, your bank, anything that could be used to reset *other* accounts - reach for a hardware key or a passkey if the service offers one. Your primary email deserves special attention here: it's usually the account every other "forgot your password" flow routes through, so it's worth more protection than an average account, not the same amount.

For everything else, an authenticator app is the right default. It's free, it takes two minutes to set up, and it closes off SIM-swap attacks entirely. If a site only offers SMS, turning it on is still meaningfully better than no second factor at all - keep in mind it's the weakest link, and avoid using that same phone number as the recovery method for your highest-value accounts if you can help it.

> If a service offers a choice, the ranking is hardware key/passkey, then authenticator app, then SMS - in that order, every time.

## Backup codes: the thing everyone ignores until they need it

When you set up 2FA, most services offer you a batch of one-time **backup codes** - usually eight to ten random strings meant to be used once each, in the exact scenario where your normal second factor isn't available. Your phone gets lost, stolen, factory-reset, or run over. Your hardware key falls out of your bag on a train. It happens more than people expect, and when it does, backup codes are the one thing standing between you and being locked out of your own account.

The habit that actually works: download them the moment they're offered, and store them somewhere that isn't the device they're meant to back up. A password manager's secure notes, a printed page in a drawer, anything except a screenshot saved on the same phone that just became your single point of failure. Skipping this step is the single most common way people turn a minor inconvenience - a lost phone - into a genuine crisis.

## The tradeoff nobody warns you about: lockout

2FA exists to keep attackers out - but a security measure with no escape hatch doesn't just block attackers, it can block *you*, permanently, with no way back in. If you lose your phone, lose your hardware key, and can't find your backup codes, you've built a lock that now has no key at all. Some services can verify your identity another way and restore access; many can't, or won't, because a convenient recovery path would hand attackers the same shortcut.

This is why "add 2FA" isn't automatically a pure win - it's a real design decision, and reasonable, well-run services put real thought into the recovery path so that a moment of bad luck doesn't become a permanent one. For a builder, that means recovery isn't an afterthought bolted on after shipping 2FA; it's part of the same feature. A few patterns that hold up:

- **Multiple registered factors.** Let a user register more than one hardware key, or both a hardware key and an authenticator app, so losing one device doesn't fully lock them out.
- **Backup codes, generated and shown once, with a clear "you can only see these now" warning.**
- **A deliberately slow, verified human recovery path** for the worst case - one that takes real effort to complete precisely so it can't be used as a shortcut by an attacker who merely knows the victim's name and email.

The plain summary: 2FA is a clear net win against the attacks that matter most day to day - reused passwords, phishing, breached credential lists. It earns its place on nearly every account you have. But it's not a switch you flip and forget; it's a lock, and every lock needs a thought-out way back in for the day you're the one standing outside it.
