2fa-authenticationCOMP

TOTP vs HOTP: cómo funcionan de verdad las contraseñas de un solo uso (y cuál usa tu 2FA)

TOTP vs HOTP explicados: dos estándares OATH de contraseña de un solo uso basados en HMAC, pero TOTP se basa en el tiempo (RFC 6238) y HOTP en un contador (RFC 4226). Tabla comparativa, cuál usa realmente tu app de autenticación y cuál es más seguro.

Por Eric Gerard · Editor · PwdFortress6 min de lecturaFoto: Towfiqu barbhuiya — Unsplash

Si alguna vez te has preguntado qué son realmente esos códigos de 6 dígitos que rotan en tu app de autenticación — y por qué algunos tokens de hardware se comportan distinto — la respuesta se reduce a dos estándares muy parecidos: TOTP y HOTP.

¿Empiezas con el 2FA en general? Comienza por qué es la 2FA y cómo protege tus cuentas.

Respuesta corta

TOTP se basa en el tiempo: el código se deriva de la hora actual y cambia (y caduca) cada 30 segundos. HOTP se basa en un contador: el código se deriva de un contador que se incrementa cada vez que se usa un código, y sigue siendo válido hasta que se usa. Ambos son estándares OATH/IETF basados en HMAC. Tu app de autenticación casi con seguridad usa TOTP — es lo que implementan Google Authenticator, Authy, Aegis, Bitwarden Authenticator y la mayoría de los sitios. HOTP aparece sobre todo en algunos tokens de hardware.

HOTP: basado en un contador (RFC 4226)

HOTP — HMAC-based One-Time Password — es el algoritmo OATH original, definido en la RFC 4226 (2005). Cada código se calcula a partir de dos elementos:

  • Un secreto compartido (una semilla aprovisionada una vez, normalmente mediante un código QR)
  • Un contador que empieza en cero y se incrementa en uno cada vez que se consume un código

El dispositivo ejecuta HMAC-SHA1 (el valor por defecto) sobre el secreto y el contador, y luego trunca el resultado en un código numérico corto — 6 dígitos por defecto, 8 opcional.

La propiedad que define a HOTP es que el código no caduca. Sigue siendo válido hasta que se usa de verdad; el contador solo avanza cuando se acepta un código. Es cómodo cuando no hay un reloj fiable, pero tiene un fallo bien conocido: la desincronización. Si se generan códigos en el cliente sin enviarlos (alguien pulsa varias veces el botón de un token), el contador del cliente se adelanta al del servidor y ambos dejan de coincidir. Para recuperarse, los servidores implementan una ventana de look-ahead: prueban los siguientes valores de contador, y si uno coincide, avanzan su contador para resincronizarse.

TOTP: basado en el tiempo (RFC 6238)

Un candado abierto sobre el teclado de un portátil bajo una iluminación roja y verde
Un candado abierto sobre el teclado de un portátil bajo una iluminación roja y verde

TOTP — Time-based One-Time Password — está definido en la RFC 6238 (2011), y se entiende mejor como un caso particular de HOTP. En lugar de un contador de eventos, TOTP usa el tiempo actual dividido por un paso de tiempo (el paso por defecto es de 30 segundos) como contador. Mete ese contador derivado del tiempo en la misma construcción HMAC y obtienes un código que cambia automáticamente cada 30 segundos y caduca cuando se renueva la ventana.

Como el contador es el reloj y no tus acciones, TOTP nunca se desincroniza por códigos sin usar — no existe el problema de «pulsé el botón demasiadas veces». La contrapartida: requiere que los relojes del cliente y del servidor estén más o menos sincronizados. Los servidores absorben una ligera desviación con una pequeña ventana de tolerancia, aceptando normalmente el paso de tiempo anterior y el siguiente además del actual.

Todo lo demás calca a HOTP: HMAC-SHA1 por defecto (SHA-256 o SHA-512 también permitidos), 6 dígitos por defecto (8 opcional), y el secreto aprovisionado mediante un URI otpauth:// dentro de un código QR. Para comparar las apps que generan estos códigos, consulta nuestra comparativa de las mejores apps de autenticación.

Tabla comparativa

PropiedadHOTP (RFC 4226)TOTP (RFC 6238)
Factor móvilContador (evento)Tiempo (hora actual / paso)
¿El código caduca?No — válido hasta usarseSí — cada ~30 segundos
Paso de tiempo por defectoN/A30 segundos
Fallo principalDesincronización del contador (resync look-ahead)Desviación del reloj (ventana de tolerancia)
AlgoritmoHMAC-SHA1 (SHA-256/512 opcional)HMAC-SHA1 (SHA-256/512 opcional)
Dígitos6 por defecto (8 opcional)6 por defecto (8 opcional)
¿Necesita red?NoNo
Uso típicoAlgunos tokens de hardware, sin conexión/sin relojApps de autenticación, mayoría de sitios

Cuál usa tu 2FA

En la práctica rara vez eliges — lo decide el servicio. Y el servicio casi siempre elige TOTP. El código rotativo de 6 dígitos en Google Authenticator, Authy, Aegis, Bitwarden Authenticator o Microsoft Authenticator es TOTP. También lo es el código de prácticamente cada pantalla de configuración 2FA del tipo «escanea este código QR» que te encuentras en la web.

HOTP es la excepción. Lo encontrarás sobre todo en tokens de hardware — una YubiKey, por ejemplo, puede configurarse como OATH-HOTP — o en entornos donde no se puede garantizar una sincronización de tiempo fiable, que es exactamente el escenario donde un contador gana a un reloj. Una YubiKey, de hecho, sabe hacer varias de estas cosas: OATH-TOTP, OATH-HOTP, y el mucho más robusto FIDO2. Para el panorama completo, consulta nuestra guía completa de YubiKey y FIDO2.

Seguridad: cuál es más seguro

TOTP suele preferirse por una razón concreta: sus códigos caducan. Un código TOTP capturado por un atacante solo es útil durante los segundos que quedan hasta que se renueva la ventana, lo que mantiene corta la ventana de intercepción y reproducción. Un código HOTP, en cambio, sigue siendo válido hasta que se usa, así que un código HOTP interceptado pero no usado le da al atacante una ventana de reproducción mayor.

Pero ninguno de los dos algoritmos es una bala de plata. Tanto TOTP como HOTP son susceptibles de phishing. Si una página de inicio de sesión falsa te induce a teclear un código válido, un atacante puede retransmitir ese código al servicio real en tiempo real antes de que caduque. La caducidad de TOTP acorta esa ventana pero no la cierra. Es la limitación estructural de todos los esquemas OTP de secreto compartido.

Los únicos factores ampliamente desplegados que de verdad resisten el phishing son FIDO2 y los passkeys, porque vinculan la autenticación al origen del sitio real: una credencial retransmitida simplemente no funciona en el dominio del atacante. Para subir en la jerarquía de seguridad, lee qué es un passkey.

En resumen

TOTP y HOTP son la misma maquinaria HMAC con un factor móvil distinto: HOTP cuenta eventos, TOTP cuenta el tiempo. Los códigos HOTP nunca caducan pero su contador puede desincronizarse; los códigos TOTP caducan cada 30 segundos pero su reloj debe mantenerse más o menos alineado. El mundo se decantó por TOTP para el 2FA por app porque los códigos que caducan son el valor por defecto más seguro, y HOTP sobrevive sobre todo en tokens de hardware y escenarios sin conexión. Sea cual sea el que te entregue un servicio, recuerda la limitación común: ambos pueden sufrir phishing. Para las cuentas más importantes, una llave FIDO2 o un passkey resistentes al phishing son la capa más sólida.

Para definiciones en lenguaje claro de TOTP, HOTP, 2FA, passkey y llave de hardware, consulta el glosario de autenticación de PwdFortress.


PwdFortress explica los estándares de autenticación a partir de las RFC publicadas y la documentación pública. No inventamos resultados de pruebas ni estadísticas.

Preguntas frecuentes

¿Cuál es la diferencia entre TOTP y HOTP?

Ambos son estándares OATH/IETF de contraseña de un solo uso basados en HMAC. **HOTP** (RFC 4226) deriva cada código de un secreto compartido más un **contador** que se incrementa cada vez que se usa un código — el código sigue siendo válido hasta que se usa, sin límite de tiempo. **TOTP** (RFC 6238) es un HOTP donde el contador es el **tiempo actual dividido por un paso de tiempo** (30 segundos por defecto), así que el código cambia y caduca cada 30 segundos. En resumen: HOTP = basado en contador/evento, TOTP = basado en el tiempo.

¿Cuál usa mi app de autenticación, TOTP o HOTP?

Casi con seguridad **TOTP**. Google Authenticator, Authy, Aegis, Bitwarden Authenticator, Microsoft Authenticator y la gran mayoría de los sitios usan TOTP — el código de 6 dígitos que cambia cada 30 segundos. HOTP es mucho más raro; se ve sobre todo en algunos tokens de hardware (por ejemplo una YubiKey configurada como OATH-HOTP) o en contextos donde no hay una sincronización de reloj fiable.

¿TOTP o HOTP, cuál es más seguro?

TOTP suele preferirse porque sus códigos **caducan tras ~30 segundos**, lo que reduce la ventana en la que un código interceptado puede reproducirse. Los códigos HOTP siguen siendo válidos hasta que se usan, así que un código interceptado pero no usado tiene una ventana de reproducción mayor. Dicho esto, **ambos son susceptibles de phishing** — un atacante puede inducirte a introducir un código válido en un sitio falso y retransmitirlo en tiempo real. Solo FIDO2/passkeys resisten el phishing.

¿Por qué se desincroniza HOTP?

HOTP depende de un contador que el cliente y el servidor incrementan cada uno. Si generas códigos en el cliente sin enviarlos nunca (por ejemplo pulsando varias veces el botón de un token de hardware), el contador del cliente se adelanta al del servidor y los códigos dejan de coincidir. Para recuperarse, los servidores usan una **ventana de look-ahead**: prueban los siguientes valores de contador, y si uno coincide se resincronizan. TOTP evita esto porque el contador es el reloj, no tus acciones.

¿TOTP necesita conexión a internet?

No. Un código TOTP se calcula localmente a partir del secreto compartido y la hora actual, así que la generación funciona totalmente sin conexión. Eso sí, requiere que los relojes del cliente y del servidor estén más o menos sincronizados; los servidores suelen aceptar una pequeña ventana de tolerancia (a menudo más o menos un paso de tiempo) para absorber una ligera desviación del reloj.

¿Cómo se comparte el secreto OTP al principio?

Durante la configuración, el servicio muestra un código QR que codifica un URI `otpauth://` con el secreto compartido, el algoritmo (HMAC-SHA1 por defecto, a veces SHA-256/512), el número de dígitos (6 por defecto, a veces 8) y el tipo (`totp` o `hotp`). Tu app de autenticación lo escanea y guarda el secreto. A partir de ahí, ambos lados calculan el mismo HMAC y comparan el código resultante.