Architecture Overview
This document provides an overview of the architectural patterns and design decisions implemented in the SaaS Auth API.
Architectural Principles
The SaaS Auth API follows Clean Architecture (also known as Hexagonal or Ports and Adapters Architecture) principles to ensure:
- Separation of Concerns: Clear boundaries between different parts of the application
- Dependency Inversion: Dependencies point inward, with the domain at the center
- Testability: Components are easy to test in isolation
- Flexibility: Easy to swap out implementations (e.g., database, cache, etc.)
- Maintainability: Clear organization makes the codebase easier to maintain
High-Level Architecture
The application is divided into several layers:
┌─────────────────────────────────────────────────────────────────┐│ ││ ┌─────────────┐ ┌─────────────┐ ┌─────────────────┐ ││ │ │ │ │ │ │ ││ │ Interface │ ──> │ Application │ ──> │ Domain Models │ ││ │ Layer │ │ Layer │ │ & Interfaces │ ││ │ │ │ │ │ │ ││ └─────────────┘ └─────────────┘ └─────────────────┘ ││ │ │ Λ ││ │ │ │ ││ │ ▼ │ ││ │ ┌─────────────┐ │ ││ │ │ │ │ ││ └────────────>│ Domain │────────────┘ ││ │ Services │ ││ │ │ ││ └─────────────┘ ││ │ ││ ▼ ││ ┌─────────────────┐ ││ │ │ ││ │ Infrastructure │ ││ │ Layer │ ││ │ │ ││ └─────────────────┘ ││ │└─────────────────────────────────────────────────────────────────┘
Layers
-
Domain Layer
- Core business entities and logic
- Domain interfaces (repositories, services)
- No dependencies on other layers or external frameworks
-
Application Layer
- Use cases/services that implement business logic
- Coordinates domain entities
- Depends only on the domain layer
-
Infrastructure Layer
- Implements domain interfaces
- Contains adapters for external systems (database, cache, etc.)
- Depends on the domain layer (implements its interfaces)
-
Interface Layer
- HTTP handlers and routes
- Request/response formatting
- Input validation
- Depends on the application layer
Project Structure
The project follows a domain-driven directory structure:
saas-auth-api/├── cmd/ # Application entry points│ └── api/ # Main API application│ └── main.go # Application bootstrap├── config/ # Configuration│ └── config.yaml # Configuration file├── docs/ # Documentation│ └── swagger.yaml # API documentation├── internal/ # Application core│ ├── apiKey/ # API key domain│ │ ├── application/ # API key use cases│ │ ├── domain/ # API key domain models and interfaces│ │ ├── infrastructure/ # API key repository implementations│ │ └── interfaces/ # API key HTTP handlers and routes│ ├── auth/ # Authentication domain│ │ ├── application/ # Auth use cases│ │ ├── domain/ # Auth domain models and interfaces│ │ ├── infrastructure/ # Auth repository implementations│ │ └── interfaces/ # Auth HTTP handlers and routes│ ├── role/ # Role and permission domain│ │ ├── application/ # Role use cases│ │ ├── domain/ # Role domain models and interfaces│ │ ├── infrastructure/ # Role repository implementations│ │ └── interfaces/ # Role HTTP handlers and routes│ └── user/ # User domain│ ├── application/ # User use cases│ ├── domain/ # User domain models and interfaces│ ├── infrastructure/ # User repository implementations│ └── interfaces/ # User HTTP handlers and routes├── migrations/ # Database migrations├── pkg/ # Shared packages│ ├── config/ # Configuration loading│ ├── database/ # Database connection and repositories│ ├── logger/ # Logging utilities│ ├── middleware/ # HTTP middlewares│ └── validator/ # Input validation└── tests/ # Tests ├── e2e/ # End-to-end tests ├── integration/ # Integration tests └── unit/ # Unit tests
Key Components
Domain Models
Each domain area has its own models that represent core business entities:
- User: Represents an authenticated user
- Role: Represents a set of permissions
- Permission: Represents an action that can be performed
- APIKey: Represents an API key for authentication
Repositories
Repositories provide an abstraction layer for data access:
- UserRepository: User data access
- RoleRepository: Role data access
- PermissionRepository: Permission data access
- APIKeyRepository: API key data access
- AuthRepository: Authentication data (tokens, sessions) access
Services
Services implement business logic:
- AuthService: Authentication and authorization
- UserService: User management
- RoleService: Role and permission management
- APIKeyService: API key management
HTTP Handlers
HTTP handlers process requests and return responses:
- AuthHandler: Authentication endpoints
- UserHandler: User management endpoints
- RoleHandler: Role management endpoints
- APIKeyHandler: API key management endpoints
Middleware
Middleware functions process requests before they reach the handlers:
- JWT Middleware: JWT authentication
- API Key Middleware: API key authentication
- RBAC Middleware: Role-based access control
- Rate Limit Middleware: Request rate limiting
Data Flow
Authentication Flow
- Client sends credentials to
/auth/login
- AuthHandler receives the request
- AuthService validates credentials
- AuthService generates JWT tokens
- AuthRepository stores refresh token in Redis
- AuthHandler returns tokens to client
Authorization Flow
- Client sends authenticated request with JWT or API key
- JWTMiddleware or APIKeyMiddleware validates the authentication
- RBACMiddleware checks permissions
- Request is processed if authorized
- Unauthorized requests are rejected with 401 or 403 status
Database Schema
The application uses a PostgreSQL database with the following key tables:
- users: User information
- roles: Role definitions
- permissions: Permission definitions
- role_permissions: Role-permission relationships
- user_roles: User-role relationships
- api_keys: API key information
- api_key_permissions: API key-permission relationships
- audit_logs: Security and audit events
External Dependencies
The application depends on the following external systems:
- PostgreSQL: Primary data storage
- Redis: Cache and session storage
- Docker: Containerization
- Fiber: HTTP framework
- JWT: Authentication tokens
Scalability Considerations
The architecture supports horizontal scaling:
- Stateless Design: No session state is stored in the application
- Connection Pooling: Database and Redis connections are pooled
- Caching: Redis is used for caching frequently accessed data
- Rate Limiting: Distributed rate limiting using Redis
Security Architecture
Security is implemented at multiple levels:
- Authentication: JWT tokens and API keys
- Authorization: Role-based access control
- Input Validation: All input is validated
- Password Security: Bcrypt hashing with salt
- Token Management: Token expiration and rotation
- Rate Limiting: Protection against brute force attacks
Monitoring and Observability
The application provides:
- Logging: Structured logging with level control
- Health Checks: HTTP endpoint for health monitoring
- Error Tracking: Standardized error responses
- Database Stats: Connection pool statistics
- Redis Stats: Connection and operation metrics
Deployment Architecture
The application can be deployed in various configurations:
Simple Deployment
┌───────────┐ ┌───────────┐ ┌───────────┐│ │ │ │ │ ││ API │───>│ PostgreSQL│ │ Redis ││ Container │ │ │ │ ││ │ └───────────┘ └───────────┘└───────────┘ Λ Λ │ │ └───────────────┘
Scalable Deployment
┌───────────┐│ ││ Load ││ Balancer ││ │└───────────┘ │ ▼┌───────────┐ ┌───────────┐ ┌───────────┐│ │ │ │ │ ││ API │ │ API │ │ API ││ Instance 1│ │ Instance 2│ │ Instance N││ │ │ │ │ │└───────────┘ └───────────┘ └───────────┘ │ │ │ └────────────────┼────────────────┘ │ ▼ ┌───────────────┐ │ │ │ Database │ │ Cluster │ │ │ └───────────────┘ │ ▼ ┌───────────────┐ │ │ │ Redis │ │ Cluster │ │ │ └───────────────┘
Design Patterns
The application uses several design patterns:
- Repository Pattern: Data access abstraction
- Dependency Injection: Service and repository injection
- Factory Pattern: Creating domain objects
- Strategy Pattern: Authentication strategies (JWT, API key)
- Middleware Pattern: Request processing pipeline
- Builder Pattern: Creating complex objects
- Adapter Pattern: Adapting external systems to the domain