"""CORS, structured request logging, and rate-limit middleware.""" from __future__ import annotations import logging import time import uuid from fastapi import FastAPI, Request, Response from fastapi.middleware.cors import CORSMiddleware from slowapi import Limiter, _rate_limit_exceeded_handler from slowapi.errors import RateLimitExceeded from slowapi.util import get_remote_address logger = logging.getLogger(__name__) limiter = Limiter(key_func=get_remote_address, default_limits=["60/minute"]) def register_middleware(app: FastAPI) -> None: """Attach all middleware to the FastAPI app.""" # CORS — allow WhatsApp webhook domain and local development app.add_middleware( CORSMiddleware, allow_origins=["*"], # Tighten in production with specific domains allow_credentials=True, allow_methods=["GET", "POST"], allow_headers=["*"], ) # Rate limiting app.state.limiter = limiter app.add_exception_handler(RateLimitExceeded, _rate_limit_exceeded_handler) @app.middleware("http") async def logging_middleware(request: Request, call_next) -> Response: request_id = str(uuid.uuid4())[:8] t0 = time.perf_counter() response = await call_next(request) elapsed_ms = int((time.perf_counter() - t0) * 1000) logger.info( "req_id=%s method=%s path=%s status=%d latency_ms=%d", request_id, request.method, request.url.path, response.status_code, elapsed_ms, ) response.headers["X-Request-ID"] = request_id return response