diff --git a/app/core/middleware.py b/app/core/middleware.py index c6b3b74..37e7b82 100644 --- a/app/core/middleware.py +++ b/app/core/middleware.py @@ -74,6 +74,15 @@ class CSRFMiddleware(BaseHTTPMiddleware): if request.headers.get("upgrade", "").lower() == "websocket": return await call_next(request) + # Bearer-token requests are CSRF-immune by design: the Authorization + # header is never attached automatically by browsers, so cross-site + # requests cannot forge it. Exempts programmatic API clients + # (external agent API, MCP, integrations) from Origin+CSRF checks — + # they authenticate via get_current_user_bearer instead. + auth_header = request.headers.get("authorization", "") + if auth_header.startswith("Bearer "): + return await call_next(request) + if request.method in self.UNSAFE_METHODS: # 1. Origin header check origin = request.headers.get("origin")