JWT vs Sessão: que mecanismo de autenticação escolher?
Autenticar um utilizador é saber, a cada pedido, quem ele é. Confrontam-se duas grandes famílias: as sessões de servidor, em que o servidor guarda o registo do utilizador ligado, e os JSON Web Tokens (JWT), em que a identidade viaja num token assinado transportado pelo cliente. A escolha influencia a segurança, a capacidade de escalar e a facilidade de desligar um utilizador. Eis como decidir consoante o seu contexto.
As sessões de servidor (stateful)
Com uma sessão, o servidor cria um identificador de sessão na ligação, armazena os dados associados (identidade, perfis, carrinho) do lado do servidor (memória, Redis, base de dados) e devolve ao navegador um cookie que contém apenas esse identificador. A cada pedido, o servidor lê o cookie, recupera a sessão e sabe quem está a falar.
- Estado do lado do servidor: a fonte de verdade permanece no servidor, o cliente transporta apenas uma referência opaca.
- Revogação imediata: eliminar a sessão do lado do servidor desliga instantaneamente o utilizador.
- Cookie: transmitido automaticamente pelo navegador, idealmente em
HttpOnly,SecureeSameSite.
Os JSON Web Tokens (stateless)
Um JWT é um token autossuficiente composto por três partes codificadas em base64url e separadas por pontos: um header, um payload (as claims, por exemplo o identificador do utilizador e a expiração) e uma assinatura. O servidor assina o token na ligação; depois basta-lhe verificar a assinatura para confiar no conteúdo, sem armazenar nada.
- Sem estado: toda a informação necessária está no token, o servidor não precisa de memória partilhada.
- Verificável em qualquer lado: qualquer serviço que conheça a chave pode validar o token, prático para as arquiteturas distribuídas e o SSO.
- Ferramentas: pode inspecionar um token com o nosso descodificador JWT, controlar a sua assinatura com o verificador JWT ou forjar um com o gerador JWT.
Tabela comparativa
| Critério | Sessão de servidor | JWT |
|---|---|---|
| Estado | Stateful (armazenado no servidor) | Stateless (transportado pelo cliente) |
| Armazenamento no servidor | Necessário (Redis, base de dados) | Nenhum |
| Revogação | Imediata | Difícil antes da expiração |
| Escalabilidade horizontal | Necessário store partilhado | Nativa |
| Tamanho transmitido | Pequeno (um identificador) | Maior (claims assinadas) |
| Entre domínios / SSO | Restritivo | Adaptado |
| Superfície XSS | Reduzida se cookie HttpOnly | Elevada se armazenado em localStorage |
Segurança: XSS, CSRF e revogação
Ambas as abordagens são seguras se forem bem implementadas, mas os seus riscos diferem.
- XSS: um cookie de sessão
HttpOnlyé inacessível ao JavaScript, portanto protegido do roubo por injeção. Um JWT armazenado emlocalStorageé, pelo contrário, legível por qualquer script, o que o torna um alvo de eleição. Armazenar o JWT num cookieHttpOnlyanula esta vantagem do JWT mas reintroduz o risco CSRF. - CSRF: os cookies são enviados automaticamente, portanto vulneráveis ao CSRF sem proteção (atributo
SameSite, token anti-CSRF). Um JWT enviado manualmente no cabeçalhoAuthorizationnão é afetado. - Revogação: é o ponto fraco do JWT. Como é autossuficiente, não é possível invalidá-lo antes da sua expiração sem reintroduzir um estado de servidor (lista de revogação, blacklist). Uma sessão elimina-se instantaneamente.
Escalabilidade e arquitetura
Num único servidor, as sessões são triviais. Assim que reparte a carga por várias instâncias, cada instância tem de aceder às sessões: é preciso um store partilhado (Redis) ou sticky sessions. O JWT brilha aqui, porque qualquer instância valida o token sem chamada de rede nem armazenamento comum.
- Microsserviços: um JWT propaga a identidade de um serviço para outro sem base centralizada.
- APIs públicas e móveis: o JWT evita a gestão de cookies do lado do cliente nativo.
- Monólito clássico: a sessão continua mais simples e mais segura por omissão.
Quando escolher um ou outro
Escolher as sessões quando
- Desenvolve uma aplicação web clássica com renderização no servidor
- A revogação imediata é crítica (banca, saúde, back-office)
- Pretende a solução mais segura por omissão, com menos armadilhas
- A sua infraestrutura suporta um store de sessões partilhado sem dificuldade
Escolher o JWT quando
- Expõe uma API consumida por SPA, dispositivos móveis ou terceiros
- Tem uma arquitetura de microsserviços ou SSO entre domínios
- Precisa de escalar horizontalmente sem store partilhado
- Aceita gerir a expiração curta e a renovação dos tokens
Recomendação
Para a maioria das aplicações web, as sessões de servidor continuam a ser a escolha mais segura e mais simples: revogação imediata, cookie HttpOnly e zero gestão de token do lado do cliente. Reserve o JWT para os casos em que a sua ausência de estado traz valor real: API stateless, dispositivos móveis, microsserviços, SSO.
Se optar pelo JWT, mantenha um tempo de vida curto (alguns minutos) associado a um refresh token armazenado em cookie HttpOnly, e preveja uma lista de revogação para os casos sensíveis. Combina assim o melhor dos dois mundos.
Perguntas frequentes
Um JWT é cifrado?
Não, por omissão um JWT é apenas assinado, não cifrado. O seu payload é codificado em base64url e legível por quem o intercetar. Nunca coloque dados sensíveis em claro num JWT. Para cifrar o conteúdo, é preciso recorrer ao JWE (JSON Web Encryption).
Onde armazenar um JWT do lado do cliente?
O mais seguro é um cookie HttpOnly, Secure e SameSite, que protege do roubo por XSS. O localStorage é mais simples mas expõe o token a qualquer script malicioso. Evite-o para tokens com privilégios elevados.
Como desligar um utilizador com um JWT?
Como o token é autossuficiente, a desconexão real exige aguardar a sua expiração ou manter uma lista de revogação do lado do servidor. É por isso que se utilizam tempos de vida curtos e um refresh token que se pode, esse sim, revogar.
É possível combinar sessões e JWT?
Sim, é uma prática comum: um access token JWT de tempo de vida curto para as chamadas de API, e um refresh token gerido como uma sessão (armazenado e revogável do lado do servidor) para renovar o access token.