ADR-0005: Keycloak cho identity/auth thay vì tự xây auth service
- Status: Accepted
- Date: ~2026-06-27 (backfilled 2026-07-25)
- Supersedes: —
- Superseded by: —
Bối cảnh
Hệ thống có nhiều role (customer, owner, admin) và nhiều service cần verify JWT giống nhau (ADR-0001). Cần một nguồn định danh (identity provider) tập trung thay vì mỗi service tự quản lý user/password, để tránh trùng lặp logic đăng nhập, refresh token, RBAC.
Quyết định
Dùng Keycloak (self-hosted, port 8090/8080 tuỳ compose) làm identity provider tập trung, chuẩn OpenID Connect:
api-gatewayverify JWT quakeycloak-connect/jwks-rsa(apps/api-gateway/src/auth/keycloak-token-verifier.service.ts)- Client GraphQL/REST đều dùng chung
Authorization: Bearer <keycloak-jwt> - Role/permission (customer/owner/admin) quản lý trong Keycloak realm
football-booking, không tự build bảngroles/permissionsriêng
Lựa chọn khác đã cân nhắc
- Tự xây auth module trong
user-service(bcrypt + JWT tự ký): kiểm soát toàn bộ logic nhưng phải tự làm lại refresh token rotation, password reset, RBAC, social login... — loại vì tốn effort không cần thiết khi Keycloak đã cung cấp sẵn, đã kiểm chứng rộng rãi (battle-tested). - SaaS identity (Auth0, Clerk...): giảm effort vận hành nhưng chi phí theo MAU và phụ thuộc vendor ngoài — loại vì mục tiêu tự chủ hạ tầng K3s.
Hệ quả
- Được: RBAC/OIDC chuẩn, JWT verify nhất quán qua mọi service qua api-gateway; không phải tự maintain logic bảo mật nhạy cảm (password hashing, token rotation).
- Đánh đổi: thêm 1 hệ thống hạ tầng phải vận hành (Keycloak + DB riêng); mọi service phụ thuộc Keycloak khả dụng để verify JWT (single point of failure cần lưu ý khi thiết kế health-check/circuit breaker).