What are Middlewares?
Middlewares in Definable are components that process HTTP requests and responses at the global level. They wrap around the request handling process, allowing code to be executed:- Before the request is processed by the route handlers
- After the route handler generates a response
Middleware Implementation
Definable middlewares are implemented using StarletteβsBaseHTTPMiddleware class, which FastAPI inherits from. Each middleware follows a consistent pattern:
Middleware Registration
Middlewares are automatically discovered and registered in the FastAPI application by theManager class, which scans the middlewares directory for Python files:
Middleware Stack
Middlewares are executed in the reverse order they are added to the FastAPI application. The current middleware stack in Definable is:- CORS Middleware - Added directly in
app.pyfor handling Cross-Origin Resource Sharing - RateLimiting Middleware - Limits the number of requests per client IP
- Exceptions Middleware - Global exception handling and formatting
The middleware stack order is important as it determines both the pre-processing and post-processing execution sequence. CORS middleware is executed first for pre-processing but last for post-processing.
Core Middlewares
Exception Handling Middleware
Theexceptions.py middleware provides centralized error handling for the application:
- Catches all unhandled exceptions from route handlers
- Provides detailed error information in development mode
- Logs exceptions with full stack trace
- Returns simplified error messages in production
Rate Limiting Middleware
Theratelimit.py middleware implements a sliding window rate limiter to prevent API abuse:
- Implements a sliding window algorithm rather than a fixed time bucket
- Tracks requests per client IP address
- Configurable maximum requests and time window
- Returns HTTP 429 (Too Many Requests) when rate limit is exceeded
CORS Middleware
The Cross-Origin Resource Sharing middleware is added directly inapp.py:
- Controls which domains can access the API
- Configures allowed HTTP methods and headers
- Manages preflight requests automatically
- Essential for browser-based clients accessing the API
Middleware vs. Dependencies
Definable uses both middlewares and FastAPI dependencies to handle cross-cutting concerns, but they serve different purposes:Middlewares
- Global scope: Applied to all requests
- Pre/post processing: Can modify both requests and responses
- Application-level concerns: Logging, error handling, rate limiting
- No access to route-specific details: Limited context about the specific endpoint
Dependencies (like RBAC and JWTBearer)
- Route-specific: Applied only to routes that declare them
- Integrated with OpenAPI: Included in API documentation
- Request-specific validation: Can validate and extract route-specific data
- Type safety: Provide type hints for route handlers
Creating New Middlewares
To add a new middleware to the Definable backend:- Create a new file in the
src/middlewares/directory - Implement a class named
Middlewarethat inherits fromBaseHTTPMiddleware - Implement the
__init__anddispatchmethods - The middleware will be automatically discovered and registered
Middleware Best Practices
When working with middlewares in Definable, follow these best practices:- Keep middlewares focused: Each middleware should have a single responsibility
- Minimize middleware overhead: Optimize performance-critical code
- Handle exceptions: Catch and handle exceptions within the middleware
- Use dependency injection: Leverage the
Acquireclass for dependencies - Consider order: Be aware of middleware execution order
- Prefer dependencies for route-specific concerns: Use FastAPI dependencies instead of parsing route data in middlewares
Performance Considerations
Middlewares run for every request, so they can impact API performance:- Memory usage: Avoid storing large amounts of data in middleware instances
- Computation overhead: Minimize complex calculations in the request path
- Database access: Avoid database queries in middlewares when possible
- Caching: Consider caching results for expensive operations
Security Middlewares
While authentication in Definable is primarily handled by dependencies (JWTBearer and RBAC), security-related middlewares could be added for:
- IP filtering: Blocking requests from suspicious IPs
- Request validation: Scanning for malicious patterns
- Response headers: Adding security headers like CSP, HSTS
- Request throttling: More advanced rate limiting strategies