JWT es una herramienta útil, pero no perdona configuraciones vagas. Muchos incidentes no ocurren porque el formato sea débil, sino porque la aplicación valida solo una parte: decodifica el payload, mira el usuario y olvida issuer, audience, expiración o algoritmo. Un token firmado debe tratarse como un documento con reglas estrictas. Si una regla falta, el atacante buscará justo esa grieta.
No aceptes algoritmos decididos por el atacante
El header del token declara un algoritmo, pero el servidor no debe confiar ciegamente en esa declaración. La aplicación debe configurar una lista cerrada de algoritmos permitidos para cada issuer y tipo de token. Aceptar none o cambiar entre HMAC y RSA sin cuidado ha producido vulnerabilidades conocidas.
La biblioteca debe usarse con opciones explícitas. Si el código dice simplemente “verificar token” sin especificar algoritmo esperado y clave adecuada, conviene revisarlo. La seguridad vive en esos detalles.
Firma válida no significa token aceptable
Un token puede estar correctamente firmado y aun así no pertenecer a esta API. Tal vez fue emitido para otro cliente, otro entorno o un propósito diferente. Validar iss y aud evita que un token legítimo en un contexto se reutilice en otro.
También hay que revisar exp, nbf e incluso iat si la política lo requiere. La firma protege contra modificación; los claims determinan si el token debe autorizar la acción actual.
No pongas secretos en el payload
El payload de un JWT firmado se puede leer con herramientas públicas. Base64URL no es cifrado. Incluir datos sensibles, credenciales, números privados o información excesiva viola minimización y puede filtrarse por logs, analytics, referrers o capturas.
Incluye solo claims necesarios para que el receptor tome decisiones. Si necesita datos frescos o sensibles, consulta un backend autorizado. Tokens pequeños también reducen límites de cabecera y exposición accidental.
Expiraciones largas aumentan daño
Un access token válido por días o semanas se parece a una contraseña portable. Si se roba, el atacante tiene mucho tiempo. Expiraciones cortas limitan impacto, especialmente combinadas con refresh tokens revocables y detección de abuso.
La duración debe adaptarse al riesgo. Un token para una API administrativa merece una vida más corta y controles más fuertes que uno para leer datos públicos. La comodidad no debe ocultar el coste de revocación.
La revocación necesita un diseño explícito
El atractivo stateless de JWT significa que el servidor puede aceptar tokens sin consultar almacenamiento central. Pero cuando un usuario cierra sesión, cambia contraseña o pierde un dispositivo, quizá se necesite invalidación. Eso exige listas de revocación, rotación de claves, session version o introspection.
No todos los sistemas necesitan revocar cada access token inmediatamente, pero todos deben saber qué ocurre después de un incidente. La respuesta “esperar a que expire” solo es aceptable si la expiración es corta y el riesgo está documentado.
Key rotation debe probarse antes de una emergencia
Las claves cambian por higiene, compromiso o migraciones. Con claves asimétricas, el header puede incluir kid para seleccionar public key. El verificador debe obtener keys de una fuente confiable, cachearlas con cuidado y manejar claves retiradas durante una ventana razonable.
Un kid no debe permitir path traversal, consultas arbitrarias o selección de claves controladas por el atacante. La key lookup también forma parte de la superficie de seguridad.
El lugar de almacenamiento importa
Guardar JWT en localStorage facilita llamadas API desde JavaScript, pero XSS puede robarlo. Guardarlo en cookie HttpOnly reduce ese riesgo, pero requiere política SameSite, CSRF tokens o diseño que no acepte acciones peligrosas solo por cookie. La decisión depende de arquitectura y amenazas.
Cualquier estrategia debe acompañarse de XSS prevention, HTTPS, cabeceras correctas y reducción de datos en el token. Un JWT no compensa una aplicación que permite script injection.
No mezcles autenticación y autorización sin límites
El token puede identificar al usuario y traer roles o scopes. Eso no significa que todas las decisiones deban congelarse dentro del token. Permisos que cambian rápidamente, suspensiones o límites por recurso quizá requieran consulta adicional al servidor.
Los scopes deben ser específicos y comprensibles. Un claim genérico como admin: true puede crecer hasta significar demasiadas cosas. Mejor separar capacidades y revisar cada endpoint contra ellas.
Observabilidad ayuda a encontrar fallos
Los logs deben registrar razón de rechazo sin almacenar tokens completos. Métricas por issuer, audience inválido, expiración y firma fallida revelan ataques e integraciones rotas. Redactar el token evita que una herramienta de monitoreo se convierta en almacén de credenciales.
Las alertas deben distinguir picos de tokens expirados, que suelen ser normales, de firmas inválidas o issuers desconocidos, que pueden indicar ataques o una rotación de claves mal coordinada. Esa separación evita ruido y permite reaccionar rápido cuando el fallo sí apunta a compromiso o integración rota.
JWT seguro no es solo elegir una biblioteca. Es configurar algoritmos, validar claims, proteger claves, limitar vida, decidir revocación, almacenar con cuidado y observar fallos. Cada parte reduce una categoría concreta de riesgo.