Skip to content

Autenticación

Autenticación

NeoPOS usa JWT (HS256) con refresh token rotacional para la autenticación. Esto significa que cada vez que refrescas tu token, el anterior queda invalidado.

Flujo completo

  1. LoginPOST /api/auth/login → obtienes access_token + refresh_token
  2. Si password_must_change=true → los endpoints protegidos retornan 403 con code: "PASSWORD_CHANGE_REQUIRED" → usa PATCH /api/auth/change-password
  3. Re-login con la nueva contraseña
  4. Llamadas autenticadas → incluir Authorization: Bearer <access_token>
  5. Refrescar (cuando expire) → POST /api/auth/refresh con refresh_token
  6. LogoutPOST /api/auth/logout invalida ambos tokens

Obtener tokens (Login)

Terminal window
curl -X POST https://api.neopos.app/api/auth/login \
-H "Content-Type: application/json" \
-d '{"correo": "soporte@neoapp.com", "password": "12345678"}'

Respuesta exitosa:

{
"access_token": "eyJhbGciOiJIUzI1NiIs...",
"refresh_token": "a1b2c3d4e5f6...",
"token_type": "bearer",
"expires_in": 3600,
"usuario": {
"id": 1, "nombre": "Soporte NeoApp", "correo": "soporte@neoapp.com",
"rol": 3, "tenant_id": "uuid-tenant", "password_must_change": false
},
"permisos": [],
"tenant": {},
"password_must_change": false
}

Errores: 401 (credenciales inválidas), 403 con code: "PASSWORD_CHANGE_REQUIRED" (debe cambiar contraseña)

Refrescar tokens

Cuando el access_token expira (por defecto en 1 hora), usa el refresh_token para obtener uno nuevo. La rotación invalida el refresh anterior.

Terminal window
curl -X POST https://api.neopos.app/api/auth/refresh \
-H "Content-Type: application/json" \
-d '{"refresh_token": "a1b2c3d4e5f6..."}'

Respuesta: misma estructura que login (nuevo access_token + nuevo refresh_token)

Cerrar sesión (Logout)

Invalida ambos tokens activos:

Terminal window
curl -X POST https://api.neopos.app/api/auth/logout \
-H "Content-Type: application/json" \
-H "Authorization: Bearer <access_token>" \
-d '{"refresh_token": "a1b2c3d4e5f6...", "access_token": "eyJ..."}'

Manejo de expiración

TokenDuraciónQué pasa al expirar
access_token1 horaLas llamadas devuelven 401 — haz refresh
refresh_token7 díasDebes hacer login nuevamente

Recomendación: Refresca el token cuando recibas un 401 o antes de que expire (ej. cada 30 minutos en segundo plano).

Rotación de refresh tokens

Cada vez que llamas a /api/auth/refresh, el refresh token anterior se invalida automáticamente. Esto previene ataques de reutilización. Si un atacante roba un refresh token, solo será válido hasta el próximo refresh legítimo.

Verificar token

Terminal window
curl https://api.neopos.app/api/auth/verify \
-H "Authorization: Bearer <access_token>"

Respuesta: información del payload JWT, tiempo restante, estado de expiración.

Cambio de contraseña obligatorio (password_must_change)

Cuando un usuario se registra o se crea mediante register-tenant, el flag password_must_change se establece en true. Esto fuerza al usuario a cambiar su contraseña en el primer inicio de sesión.

Flujo:

  1. POST /api/auth/login → respuesta incluye password_must_change: true
  2. Cualquier endpoint protegido retorna 403 con { "code": "PASSWORD_CHANGE_REQUIRED", "message": "..." }
  3. El usuario llama a PATCH /api/auth/change-password (funciona incluso con el flag activo):
    Terminal window
    curl -X PATCH https://api.neopos.app/api/auth/change-password \
    -H "Content-Type: application/json" \
    -H "Authorization: Bearer <access_token>" \
    -d '{"old_password": "Passw0rd!", "new_password": "NewPass1@"}'
  4. El flag se limpia y el usuario debe hacer login nuevamente

La nueva contraseña debe cumplir: mínimo 8 caracteres, al menos una mayúscula, un número y un carácter especial.

Referencia de endpoints

Para la lista completa de endpoints de autenticación, consulta la referencia de Auth.