Módulo Authentication — visão geral
O módulo de autenticação implementa o servidor de autorização OAuth2/OIDC do Portal 2.0: login
com e-mail e senha, segundo fator (TOTP e SafeID), recuperação e troca de senha, emissão e
renovação de tokens, sessões, login por QR-code e os endpoints padrão de descoberta OIDC. Ele
vive em quatro pacotes do backend (NestJS): identity/authentication, identity/oauth,
identity/session e identity/privileged-access.
Reescrita recente. Este módulo foi reescrito de forma abrangente. Se você conhece uma versão anterior desta documentação, atenção: não existe mais
:tenantno path das rotas, o login não emite maisauthorization_code, os códigos de erro mudaram de prefixo (AUTH_*→IDENTITY_*), o QR-code e o encerramento de sessão (antigo/logout) foram remodelados como operações sobre o recurso/sessions, e passou a existir um endpoint de introspecção de token que antes não existia. Cada página abaixo é a fonte confiável para o comportamento atual.
Prefixo de rotas e versionamento
A API usa o versionamento nativo do NestJS por URI (VersioningType.URI, versão padrão 1), então
toda rota deste módulo é servida sob /v1/... (ex.: /v1/authentication/login,
/v1/oauth/token). Não há segmento de tenant no caminho — a resolução de organização, quando
necessária (ex.: validar a origem do login), acontece por outros meios (ver IdentityOriginGuard
na página de login), não por um parâmetro de rota.
Em desenvolvimento local, o serviço sobe na porta 3000 (MAIN_API_PORT, default 3000) e expõe
o Swagger em http://localhost:3000/docs.
Arquitetura
Login não emite mais authorization_code
A mudança mais importante em relação a versões antigas: POST /authentication/login (e a
conclusão de MFA em /authentication/totp/verify ou /authentication/safe-id/verify) cria uma
sessão diretamente e devolve session_id + session_expires_at + user_id — não existe mais
um authorization_code intermediário nesse fluxo. O conceito de authorization_code com PKCE
continua existindo, mas pertence ao fluxo OAuth2 clássico (/oauth/authorize → /oauth/token),
usado para autorizar clients OAuth específicos, trocar de conta (/sessions/switch) e concluir o
login por QR-code (/sessions/qr-challenges/complete). Os três reaproveitam o mesmo
IssueIdentityAuthorizationCodeService.
A confirmar — responsável: time de Identity; data: 24/09/2026. Não foi possível confirmar neste levantamento como a experiência de login no navegador obtém o access token necessário para chamar
POST /oauth/authorizelogo após o login (essa rota exige um Bearer token válido). Existem dois caminhos no código:POST /oauth/authorize(com o access token do próprio usuário) ePOST /oauth/authorize/session(chamado por um serviço interno comX-Service-Token, informandoidentity_session_id/user_ide uma decisãoapprove/denysem precisar de um access token de usuário). Qual desses o front usa hoje não foi verificado neste levantamento — ver Autorizar aplicação (OAuth).
Sessão, tokens e assurance
- Sessão (
identity/session) é o objeto durável que liga usuário, dispositivo e o nível de confiança da autenticação (assurance:PASSWORDouMFA). Access e refresh tokens são emitidos contra uma sessão ativa. - Access token / ID token: JWT assinado com RS256, chave pública publicada em
/.well-known/jwks.json(conjunto global, não há chave por tenant). TTL fixo de 3600s, definido como constante no código (não é variável de ambiente). - Refresh token: opaco, de uso único (rotação); reutilizar um refresh token já usado revoga
toda a família de tokens daquela sessão. TTL configurável via
IDENTITY_REFRESH_TOKEN_LIFETIME_DAYS(default 30 dias). - Authorization code: opaco, de uso único, TTL configurável via
IDENTITY_OAUTH_AUTHORIZATION_CODE_LIFETIME_SECONDS(default 600s). - Elevação de sessão (step-up):
identity/privileged-accesspermite elevar oassurancede uma sessão já autenticada paraMFA(reconfirmando o TOTP) antes de liberar ações sensíveis (ex.: administração de segredos/IAM). É uma capacidade separada do login/logout — não tem página própria nesta documentação ainda; ver código empackage/identity/privileged-access(pendência de documentação).
Autenticação de origem e multi-tenant
Diferente de versões antigas baseadas em :tenant no path, a validação de origem hoje é feita
pelo IdentityOriginGuard (usado só em POST /authentication/login): a origem da requisição
precisa estar na lista IDENTITY_ALLOWED_ORIGINS ou ser um domínio próprio de uma organização,
confirmado por uma chamada ao serviço de Organization. As demais rotas do módulo (OAuth, sessão,
QR-code) não validam Origin nem dependem de tenant no path.
Rate limiting
Todas as rotas sensíveis usam ThrottlerGuard (via RateLimitGuard, guard global). Várias delas
somam um segundo "balde" por identidade (@RateLimitIdentity) — um hash do e-mail, do token ou do
state do corpo — além do balde padrão por IP, os dois com o mesmo limite/janela. Os limites
exatos estão documentados em cada página de rota.
Convenção de erros
Toda exceção de negócio estende BaseError e já carrega seu statusCode e errorCode fixos no
próprio construtor (ex.: IdentityAccountLockedError sempre lança 423). O filtro global
(AllExceptionsFilter) apenas repassa esses valores — não há uma tabela central de mapeamento
status↔erro. Os decorators @ApiResponse do Swagger documentam esse comportamento, mas em alguns
pontos ficaram desatualizados em relação ao código; cada página de rota abaixo sinaliza as
divergências confirmadas.
Páginas deste módulo
| Página | Cobre |
|---|---|
| Login | POST /authentication/login — autenticação por e-mail/senha, bloqueio progressivo de conta, disparo de desafio de MFA |
| MFA (TOTP e SafeID) | POST /authentication/totp/verify, /safe-id/verify, e o autoatendimento de TOTP (/totp/enrollment, /totp/enrollment/confirm, DELETE /totp) |
| Senha | POST /authentication/password/forgot, /password/reset e PATCH /authentication/password (trocar senha autenticado) |
| Autorizar aplicação (OAuth) | GET/POST /oauth/authorize e POST /oauth/authorize/session — emissão de authorization_code via PKCE |
| Token | POST /oauth/token (todos os grants) e POST /oauth/introspect |
| Login por QR-code | POST /sessions/qr-challenges, /qr-challenges/approve, /qr-challenges/complete |
| Encerrar sessão | DELETE /sessions/current e DELETE /sessions — o substituto do antigo /logout |
| Sessões e identidade | HEAD /sessions/current, GET /sessions/switchable-accounts, POST /sessions/switch, GET /userinfo |
| Descoberta OIDC | GET /.well-known/openid-configuration e GET /.well-known/jwks.json |
:::tip OpenAPI
A documentação interativa (schemas + "Try it out") está disponível em /docs no ambiente onde a
API está rodando (local: http://localhost:3000/docs).
:::