ToolActToolAct

Herramienta de Análisis JWT

Decodifica y verifica JSON Web Token, ver Header, Payload y Signature

JWT Token

JWT de Ejemplo

¿Qué es JWT?

JWT (JSON Web Token) es un estándar abierto (RFC 7519) para transmitir información de manera segura entre partes. JWT consta de tres partes separadas por puntos: Encabezado (Header) que contiene el tipo de token y algoritmo de firma, Carga (Payload) que contiene los datos de declaraciones, y Firma (Signature) que verifica la integridad del token. JWT se usa comúnmente para autenticación e intercambio de información. Al trabajar con JWT es importante distinguir decodificar de verificar. El header y el payload solo están codificados en Base64URL, por lo que pueden leerse aunque la firma sea inválida. La confianza aparece con la validación del servidor: firma, algoritmo, expiración, emisor y audiencia. Datos sensibles no deberían colocarse en un payload sin cifrar, porque cualquiera que posea el token puede leerlos. Depurar un token es útil, pero no equivale a aceptarlo.

Cómo usar

Cómo usar

  1. Pega un JWT en el campo de entrada; la herramienta analizará y mostrará automáticamente el contenido del header y el payload
  2. Haz clic en las etiquetas de colores para copiar la parte codificada en Base64 correspondiente
  3. Introduce el secreto en el área de verificación de firma para comprobar si la firma es correcta (soporta algoritmos HS256/HS384/HS512)
  4. El área de información clave muestra valores decodificados para claims comunes; el estado de expiración se indica por colores

Consejos de seguridad

  • Esta herramienta se ejecuta localmente en tu navegador; el Token nunca se envía a ningún servidor
  • JWT solo codifica y firma los datos, no está cifrado, cualquiera puede decodificar y ver el contenido
  • No almacenes información sensible en JWT (como contraseñas o números de tarjetas de crédito)
  • Usa siempre HTTPS para transmitir JWT en entornos de producción

Casos de uso

Inspeccionar el contenido de un token durante la depuración de autenticaciónPega un JWT de tres partes (Header.Payload.Signature) para inspeccionar por separado el header y el payload decodificados en Base64URL, independientemente de la firma. Los claims estándar como iss, aud, sub, iat, nbf y exp se muestran con marcas de tiempo en segundos Unix y fechas legibles, facilitando el diagnóstico de problemas de inicio de sesión y sesiones. El token nunca sale de la pestaña del navegador.
Verificar firmas HMAC localmentePara tokens HS256, HS384 y HS512, introduce el secreto compartido para recalcular HMAC-SHA256/384/512 sobre header_b64 + '.' + payload_b64 y compararlo con el segmento de firma. Resulta útil al comparar entornos, diagnosticar un secreto rotado o confirmar que un token no fue alterado en tránsito. El secreto que pegas se usa solo para el HMAC local y nunca se envía a un servidor.
Revisar expiración y detalles de claims antes de compartir logsLa herramienta resalta los tokens expirados (exp < ahora) y muestra los límites de nbf / iat, por lo que un token 'firmado correctamente' pero aún no válido también se marca. Copia las partes en bruto o el JSON formateado. Dado que la decodificación y la verificación HMAC ocurren en el navegador, los tokens bearer sensibles pueden inspeccionarse sin enviarlos a un servicio de decodificación externo.
Inspeccionar tokens con clave pública sin verificarlos localmentePega un token firmado con RS256, PS256 o ES256 para leer el header y el payload decodificados. Como esta página solo verifica firmas HMAC (HS256/HS384/HS512) localmente, la verificación real de RSA / RSA-PSS / ECDSA debe hacerse en un servidor que tenga la clave pública correspondiente (cargada normalmente desde el endpoint JWKS del emisor). Resulta útil al diagnosticar un callback de OAuth cuando la pestaña local solo se usa para leer lo que afirma el token.
Detectar confusión de algoritmos y claims exp ausentesLa vista decodificada muestra header.alg junto con los claims estándar, haciendo evidente cuándo un token dice HS256 pero el servidor espera RS256 (el clásico ataque de sustitución de algoritmo), cuando alg es 'none' o cuando exp, nbf o iat están ausentes. Detecta estas discrepancias en el navegador antes de que lleguen a una librería de autenticación que podría degradar silenciosamente la validación.

Principio técnico

JWT (JSON Web Token, RFC 7519) se compone de tres partes — Header.Payload.Signature — unidas por el punto inglés '.'. Header: describe el tipo de token y el algoritmo de firma, p. ej. {"alg":"HS256","typ":"JWT"}. alg determina cómo se calcula la Signature; los más comunes son HS256 (HMAC-SHA256), RS256 (RSA-SHA256), ES256 (ECDSA-SHA256) y none (sin firma, prohibido en producción). Payload: también llamado claims, un conjunto de campos JSON. RFC 7519 define 7 claims registrados estándar: iss (emisor), sub (sujeto, normalmente un ID de usuario), aud (audiencia), exp (expiración), nbf (no antes de), iat (emitido en) y jti (ID único). Los desarrolladores pueden añadir cualquier campo privado encima, como userId, role, tenant. Signature: codificar en Base64URL el Header y el Payload, unirlos con un punto y luego firmar con el algoritmo especificado por alg usando una clave. HS256 usa HMAC-SHA256(secret, header_b64 + '.' + payload_b64); RS256 usa una clave privada RSA. El receptor recalcula la firma de la misma manera y comprueba si ambas coinciden. Base64URL frente a Base64 estándar: '+' se convierte en '-', '/' se convierte en '_', y el relleno final '=' se omite, por lo que el resultado puede colocarse en rutas URL y cadenas de consulta sin activar la codificación porcentual. Ten en cuenta que Base64URL es solo una codificación: no proporciona cifrado ni seguridad, y cualquiera puede decodificar y leer el payload. Límite de seguridad: JWT solo garantiza 'no ha sido manipulado', no 'el contenido es sensible'. Un error común es incluir números de teléfono, números de identificación o hashes de contraseñas en el payload, donde todo el mundo puede verlos.

  • Estructura de tres partes: Header.Payload.Signature, cada una codificada en Base64URL; la firma es HMAC(secret, header_b64 + '.' + payload_b64) o RSA(privateKey, misma entrada).
  • Base64URL intercambia '+' -> '-', '/' -> '_', y omite el relleno final '=', por lo que el resultado codificado puede colocarse directamente en una URL (sin activar codificación porcentual).
  • Esta herramienta solo verifica firmas de la familia HMAC (HS256/HS384/HS512) localmente. Algoritmos asimétricos como RS256 o ES256 requieren una clave pública del endpoint JWKS del emisor, así que la verificación de firma debe hacerse en un servidor que tenga la clave pública — la página puede decodificar el header y el payload, pero no puede verificarlos.
  • Claims estándar: iss (emisor), sub (sujeto), aud (audiencia), exp (expiración, marca de tiempo Unix en segundos), nbf (no antes de), iat (emitido en), jti (JWT ID, previene reutilización).
  • Ataque alg=none: el campo alg debe validarse estrictamente y el algoritmo none debe rechazarse, de lo contrario un atacante puede falsificar cualquier token; también deben prevenirse los ataques de sustitución de algoritmo (verificar un token HS256 usando la clave pública como secreto).
  • JWT no está cifrado: el payload es texto plano codificado en Base64URL, no cifrado; para contenido confidencial usar JWE (JSON Web Encryption), pero en la práctica el patrón común es mantener los datos sensibles en el backend y referenciarlos mediante el campo sub.

Ejemplos

Token estándar HS256

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkphbmUgRG9lIiwiaWF0IjoxNzA1MzEyODAwLCJleHAiOjE3MDUzMTY0MDB9.znHapMygT8K8YZN4K8zM1sV3bKlQ5pY3xE2gR4wN1vM

Header:  {"alg":"HS256","typ":"JWT"}
Payload: {"sub":"1234567890","name":"Jane Doe","iat":1705312800,"exp":1705316400}
RFC: RFC 7519 sección 3 define los Registered Claim Names (sub, iat, exp)

Token expirado

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiJ1c2VyLTEyMyIsImV4cCI6MTYwMDAwMDAwMH0.OxQ0fUKW0z4mK0xJ4vF0uF7eZB9wK3yF8pL2nQ6tX1k

Header:  {"alg":"HS256","typ":"JWT"}
Payload: {"sub":"user-123","exp":1600000000}
Estado:  expirado (exp < ahora)
Nota: el claim exp usa NumericDate (segundos desde la época Unix según RFC 7519 sección 2)

Token de información de usuario con claims personalizados

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiJ1c2VyLTQ1NiIsIm5hbWUiOiJBbGljZSIsInJvbGUiOiJhZG1pbiIsInRlbmFudCI6ImFjbWUiLCJpYXQiOjE3MDUzMTI4MDAsImV4cCI6MTcwNTMxNjQwMCwiYXVkIjoiYXBpLmV4YW1wbGUuY29tIn0.7Hk2L9oP3qR1mN4vK8xJ2wE5yT6sB0fA9cZ1dG3hI4U

Header:  {"alg":"HS256","typ":"JWT"}
Payload: {"sub":"user-456","name":"Alice","role":"admin","tenant":"acme","iat":1705312800,"exp":1705316400,"aud":"api.example.com"}
Nota: role y tenant son claims privados; no están definidos en RFC 7519

Lista de comprobación de seguridad para implementar JWT

1. Nunca almacenes secretos en el payload: JWT está codificado, no cifrado
2. Usa secretos fuertes para HS256 (>= 256 bits / 32 caracteres aleatorios)
3. Prefiere RS256/ES256 para verificación con clave pública en sistemas multi-servicio
4. Valida el header alg: rechaza 'none' o algoritmos inesperados
5. Verifica las marcas de tiempo exp, nbf, iat antes de confiar en el token
6. Comprueba que aud coincide con tu servicio para evitar la reutilización del token entre aplicaciones
7. Almacena en cookies HttpOnly, no en localStorage (protección XSS)

RFC: RFC 8725 (JWT Best Practices) cubre estas consideraciones de seguridad

Preguntas frecuentes

¿Cuáles son las tres partes de un JWT?

Cabecera, payload y firma, separadas por puntos. La cabecera declara el algoritmo de firma y el tipo de token. El payload lleva reclamos como sub, iss, aud, iat, exp y cualquier dato personalizado. La firma permite al verificador confirmar que el token no ha sido manipulado. La cabecera y el payload son JSON codificado en Base64URL: están firmados, no cifrados.

¿Está cifrado un JWT?

No: un JWT en formato JWS normal está firmado pero no cifrado. Cualquiera que lo intercepte puede decodificar la cabecera y el payload con Base64URL y leer todos los reclamos, incluidos IDs de usuario, correos y roles. Trata el contenido de un JWT como información pública; nunca pongas contraseñas ni secretos en el payload. JWE (JWT cifrado) existe pero es mucho menos común.

¿Qué significa cada reclamo estándar?

iss = emisor; sub = sujeto (a menudo el ID de usuario); aud = audiencia (destinatario previsto); exp = expiración (segundos Unix); nbf = no antes de; iat = emitido en; jti = ID único del token para revocación. Están definidos por el RFC 7519. Los reclamos personalizados pueden añadirse libremente: ponle prefijo a los específicos de cada proveedor para evitar colisiones.

¿Cómo verifico un JWT?

Lee la cabecera alg, usa la clave correspondiente (HS256 = secreto compartido, RS256/ES256 = clave pública del endpoint JWKS del emisor), recalcula la firma sobre el header.payload codificado y compara. Después comprueba exp, nbf, iss y aud. Rechaza el token si alg es 'none' o difiere de lo que tu servidor espera. Esta herramienta solo verifica firmas HS256/HS384/HS512 (secreto compartido) localmente; la verificación de RS256/ES256 debe hacerse en un servidor que tenga la clave pública.

¿La verificación se hace en mi navegador?

Sí. La página analiza el JWT localmente y verifica las firmas HS256/HS384/HS512 con HMAC ejecutado en JavaScript dentro de tu navegador. El token no llega a nuestro servidor, pero recuerda que un JWT está diseñado para viajar en URLs y cabeceras — supón que cualquier JWT que copies puede aparecer en logs.

¿Por qué es peligroso alg=none?

El RFC 7519 permite alg=none para tokens sin firma. Un verificador vulnerable puede aceptar un token así aunque no tenga firma, lo que deja a un atacante falsificar cualquier payload. Las bibliotecas modernas rechazan alg=none por defecto; si escribes tu propio verificador, codifica fijo el algoritmo esperado en lugar de fiarte de la cabecera.

¿Cómo de grande puede ser un JWT?

No hay límite del protocolo, pero los JWT suelen acabar en cabeceras HTTP (Authorization: Bearer ...) y muchos servidores limitan las cabeceras a unos 8 KB. Meter reclamos en un JWT engorda cada petición. Si necesitas mucho estado de sesión, usa una sesión del lado del servidor y mete un pequeño token de referencia en el JWT en su lugar.