Decodificador de JWT

Decodifica cabeceras y cargas de JWT, con algoritmo y expiración

🔒 Tu token se decodifica completamente en tu navegador y nunca se envía a un servidor.

exp, nbf e iat se comprueban con el reloj de este dispositivo. Si difiere del servidor, aumenta el margen.

Pega un token arriba para ver el resultado decodificado aquí.

Acerca de Decodificador de JWT

Un JWT (JSON Web Token, RFC 7519) son tres cadenas base64url unidas por puntos: cabecera, carga útil (payload) y firma. Esta herramienta decodifica las dos primeras, las interpreta como JSON y convierte las claims exp, iat y nbf en fechas legibles.

No verifica la firma, y no podría hacerlo. Para comprobar una firma HS256 hace falta el secreto compartido del servidor; para RS256 o ES256, la clave pública del emisor. Un decodificador no recibe ninguna de las dos. Que el payload se vea bien solo demuestra que el token es base64url y JSON válidos; si merece confianza es algo que solo puede decidir el servidor que lo verifica.

Cualquiera puede leer un JWT

Base64url es una codificación, no un cifrado. Quien consiga el token, sea desde un log, una captura de tráfico o el localStorage del navegador, puede leer sus claims igual que esta página. Por eso un token firmado (JWS) no es lugar para contraseñas, números de identificación o reglas internas de permisos. Si el contenido debe ser secreto, el formato adecuado es JWE, un JWT cifrado con cinco partes separadas por puntos; si pegas uno aquí obtendrás un error de número de segmentos.

Lo que aporta la firma es integridad. Si cambias "role": "user" por "admin" y vuelves a codificar, el decodificador mostrará admin sin problema, pero un servidor bien implementado lo rechazará porque la firma ya no coincide.

Dos ataques que nacen de confiar en la cabecera alg

El valor alg está en la cabecera, que controla el atacante. El RFC 8725, el documento de buenas prácticas del IETF para JWT, describe dos fallos conocidos que ocurren cuando ese valor decide cómo se verifica el token.

  • alg: none. La sección 6 del RFC 7519 define un JWT 'no protegido' cuya firma es la cadena vacía. Algunas bibliotecas veían none y daban el token por válido sin comprobar nada. El segundo ejemplo de abajo tiene justo esa forma: nada después del último punto.
  • Confusión RS256/HS256. El servidor espera firmas RSA y tiene la clave pública del emisor. El atacante cambia alg a HS256 y firma el token falso con HMAC usando esa clave pública, que es pública, como secreto. Una implementación que obedezca la cabecera calculará el HMAC con la misma clave y aceptará la falsificación.
  • La solución para ambos: el verificador fija en el código los algoritmos permitidos. El RFC 8725 exige que las bibliotecas permitan indicar un conjunto de algoritmos admitidos y no usen ningún otro, y que cada clave se use con un solo algoritmo.
  • Un secreto HMAC débil es un tercer problema: si la clave HS256 es corta o fácil de recordar, basta un token capturado para averiguarla por fuerza bruta sin conexión (RFC 8725, sección 2.2).

exp, nbf, iat y el desfase de relojes

Las tres son NumericDate: segundos desde el 1970-01-01 UTC. Date.now() en JavaScript devuelve milisegundos, así que en los tokens hechos a mano es habitual acabar con un exp decenas de miles de años en el futuro o en enero de 1970. Si la fecha que ves aquí es absurda, revisa si sobra o falta un factor 1000.

Según el RFC 7519, un token no debe aceptarse a partir de exp ni antes de nbf. Ambas secciones permiten 'un pequeño margen, normalmente no más de unos minutos, para compensar el desfase de relojes'. Sin ese margen, un token emitido por un servidor cuyo reloj va 30 segundos adelantado puede ser rechazado por la API como todavía no válido en cuanto llega, aunque en cualquier decodificador se vea perfecto.

Las marcas de caducado y de aún no válido (antes de nbf) de esta página comparan exp y nbf con el reloj de tu propio ordenador. Si tu reloj está mal, las marcas también. Escribe un valor en el margen de desfase de reloj para admitir esos segundos de diferencia; por defecto es 0. Si iat está en el futuro, la herramienta avisa de que los relojes no coinciden. iat es solo la hora de emisión y no hace caducar el token; un token sin exp, según el estándar, no caduca nunca, y por eso muchas APIs rechazan los que no lo llevan.

Qué revisar cuando la API rechaza un token bien formado

Casi siempre es una claim concreta. aud (audiencia) debe coincidir con la API: es frecuente presentar a un servicio un token emitido para otro. iss debe coincidir con el emisor en el que confía la API, incluida la barra final que añaden algunos proveedores de identidad. Y si el kid de la cabecera nombra una clave que el servidor aún no ha descargado, por ejemplo justo después de una rotación de claves, la verificación falla aunque el token sea correcto.

Ejemplos

El token de ejemplo de jwt.io

Entrada
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c
Resultado
Cabecera {"alg":"HS256","typ":"JWT"} Payload {"sub":"1234567890","name":"John Doe","iat":1516239022} Emitido 2018-01-18 01:30:22 UTC; sin caducidad

No hay exp, así que no hay veredicto de caducidad. La firma se muestra tal cual; nada aquí indica si es correcta.

Un token alg: none

Entrada
eyJhbGciOiJub25lIiwidHlwIjoiSldUIn0.eyJzdWIiOiJhZG1pbiIsImV4cCI6MTc5MDAwMDAwMH0.
Resultado
Cabecera {"alg":"none","typ":"JWT"} Payload {"sub":"admin","exp":1790000000} Firma: vacía; caduca 2026-09-21 14:13:20 UTC

Se decodifica sin problema. Si una API en producción acepta tokens así, cualquiera puede escribir sub: admin y entrar.

Cómo se usa

  1. Pega el token sin el prefijo 'Bearer '.
  2. Revisa alg y typ en la cabecera y las claims del payload.
  3. Comprueba exp, iat y nbf como fechas; las marcas de caducidad y nbf usan el reloj de tu equipo más el margen que indiques.

Preguntas frecuentes

¿Es seguro pegar aquí un token de producción?

La decodificación ocurre en tu navegador y el token no se envía a ninguna parte. Aun así, un token de acceso vigente es una credencial: evita pegarlo en chats o gestores de incidencias.

¿Puede decirme si la firma es válida?

No. La verificación necesita el secreto o la clave pública y corresponde a la biblioteca JWT del servidor, configurada con una lista explícita de algoritmos permitidos.

Aparece como caducado, pero la API lo acepta.

Probablemente el servidor admite unos minutos de margen, o el reloj de tu ordenador va adelantado. Escribe el margen del servidor en el campo de desfase de reloj para juzgarlo con el mismo criterio.

¿Por qué da error de número de segmentos?

Un JWT tiene exactamente dos puntos. Comprueba que no quede el prefijo 'Bearer ' o comillas, o que no sea un JWE, que tiene cuatro.

Fuentes

Revisado el:

Privacidad y tratamiento de datos