144 lines
2.4 KiB
Markdown
144 lines
2.4 KiB
Markdown
# Identity Auth API
|
|
|
|
## Endpoints disponibles
|
|
|
|
```http
|
|
POST /identity/auth/login
|
|
POST /identity/auth/refresh
|
|
POST /identity/auth/logout
|
|
GET /identity/auth/session
|
|
```
|
|
|
|
## POST `/identity/auth/login`
|
|
|
|
### Request
|
|
|
|
```ts
|
|
export type LoginWithPasswordRequestDTO = {
|
|
email: string;
|
|
password: string;
|
|
};
|
|
```
|
|
|
|
### Response
|
|
|
|
```ts
|
|
export type LoginWithPasswordResponseDTO = {
|
|
access_token: string;
|
|
refresh_token: string;
|
|
account: AuthenticatedAccountDTO;
|
|
};
|
|
```
|
|
|
|
```ts
|
|
export type AuthenticatedAccountDTO = {
|
|
id: string;
|
|
email: string;
|
|
name: string;
|
|
avatar_url: string | null;
|
|
language_code: string;
|
|
};
|
|
```
|
|
|
|
### Notas
|
|
|
|
- No requiere `Authorization`.
|
|
- No requiere `X-Company-Id`.
|
|
- No devuelve empresas accesibles todavía.
|
|
- No devuelve roles ni permisos.
|
|
- El access token no contiene `companyId`.
|
|
|
|
## POST `/identity/auth/refresh`
|
|
|
|
### Request
|
|
|
|
```ts
|
|
export type RefreshSessionRequestDTO = {
|
|
refresh_token: string;
|
|
};
|
|
```
|
|
|
|
### Response
|
|
|
|
```ts
|
|
export type RefreshSessionResponseDTO = {
|
|
access_token: string;
|
|
refresh_token: string;
|
|
};
|
|
```
|
|
|
|
### Notas
|
|
|
|
- El refresh token se rota.
|
|
- El cliente debe reemplazar ambos tokens por los nuevos.
|
|
- El refresh token anterior no debe reutilizarse tras una renovación correcta.
|
|
|
|
## POST `/identity/auth/logout`
|
|
|
|
### Headers
|
|
|
|
```http
|
|
Authorization: Bearer <access_token>
|
|
```
|
|
|
|
### Request
|
|
|
|
```ts
|
|
export type LogoutRequestDTO = {
|
|
refresh_token?: string;
|
|
all_sessions?: boolean;
|
|
};
|
|
```
|
|
|
|
### Response
|
|
|
|
```ts
|
|
export type LogoutResponseDTO = {
|
|
success: true;
|
|
};
|
|
```
|
|
|
|
### Reglas
|
|
|
|
- Para logout normal, enviar el `refresh_token` actual.
|
|
- Para cerrar todas las sesiones, enviar `all_sessions: true`.
|
|
- Si logout falla por expiración de token, el frontend debe limpiar sesión igualmente.
|
|
|
|
## GET `/identity/auth/session`
|
|
|
|
### Headers
|
|
|
|
```http
|
|
Authorization: Bearer <access_token>
|
|
```
|
|
|
|
### Response
|
|
|
|
```ts
|
|
export type CurrentSessionResponseDTO = {
|
|
account: AuthenticatedAccountDTO;
|
|
};
|
|
```
|
|
|
|
## Errores esperados
|
|
|
|
```txt
|
|
400 -> request inválida o header mal formado
|
|
401 -> access token ausente/inválido/expirado o credenciales inválidas
|
|
403 -> contexto de empresa requerido en rutas tenant-scoped
|
|
500 -> error inesperado
|
|
```
|
|
|
|
## Rutas tenant-scoped
|
|
|
|
Las rutas de negocio tenant-scoped deben enviar:
|
|
|
|
```http
|
|
Authorization: Bearer <access_token>
|
|
X-Company-Id: <uuid-company>
|
|
```
|
|
|
|
Actualmente `X-Company-Id` se valida sintácticamente como UUID y se publica como `req.user.companyId`.
|
|
|
|
La validación real de membership queda pendiente.
|