FastAPI Azure Auth
FastAPI-Azure-Auth is a Python library that provides an easy and secure implementation of Azure Entra ID (formerly Azure Active Directory) authentication and authorization for FastAPI APIs. It supports B2C, single-tenant, and multi-tenant applications. The library is actively maintained, with frequent updates, and is currently at version 5.2.0.
Warnings
- breaking Azure Entra ID (formerly Active Directory) v1 token support has been dropped. All new and existing projects should migrate to v2 tokens.
- breaking Pydantic v1 support has been dropped. Your project must use Pydantic v2 or later.
- breaking The `InvalidAuth` exception class now requires both `detail` and `request` objects. For HTTP or WebSocket contexts, it's recommended to explicitly use `InvalidAuthHttp` or `InvalidAuthWebSocket` respectively.
- gotcha A common 'redirect URI mismatch' error can occur if the redirect URI configured in Azure Entra ID does not exactly match the one used by your application. This includes differences between 'localhost' and '127.0.0.1'.
- gotcha Integrating Azure Easy Auth (App Service Authentication/Authorization) directly with `fastapi-azure-auth` in a 2-tier application can lead to conflicts, as Easy Auth's flow might interfere with the library's custom token validation logic.
- gotcha When using the client_credentials flow, 'Invalid audience' errors can occur if application permissions (app roles) are not correctly configured and granted by an administrator or the API's owner. Delegated permissions are not sufficient for application-only authentication.
Install
-
pip install fastapi-azure-auth uvicorn
Imports
- FastAPI
from fastapi import FastAPI
- Security
from fastapi import Security
- Depends
from fastapi import Depends
- SingleTenantAzureAuthorizationCodeBearer
from fastapi_azure_auth.auth import SingleTenantAzureAuthorizationCodeBearer
- MultiTenantAzureAuthorizationCodeBearer
from fastapi_azure_auth.auth import MultiTenantAzureAuthorizationCodeBearer
- B2CMultiTenantAuthorizationCodeBearer
from fastapi_azure_auth.auth import B2CMultiTenantAuthorizationCodeBearer
- User
from fastapi_azure_auth.user import User
- BaseSettings
from pydantic_settings import BaseSettings
- SettingsConfigDict
from pydantic_settings import SettingsConfigDict
Quickstart
import os
from fastapi import FastAPI, Depends, HTTPException, status
from pydantic import AnyHttpUrl
from pydantic_settings import BaseSettings, SettingsConfigDict
from fastapi_azure_auth import SingleTenantAzureAuthorizationCodeBearer
from fastapi_azure_auth.user import User
class Settings(BaseSettings):
BACKEND_CORS_ORIGINS: list[str | AnyHttpUrl] = ['http://localhost:8000']
TENANT_ID: str = os.environ.get('TENANT_ID', '')
APP_CLIENT_ID: str = os.environ.get('APP_CLIENT_ID', '')
OPENAPI_CLIENT_ID: str = os.environ.get('OPENAPI_CLIENT_ID', '')
SCOPE_DESCRIPTION: str = os.environ.get('SCOPE_DESCRIPTION', 'user_impersonation')
model_config = SettingsConfigDict(
env_file='.env', env_file_encoding='utf-8', case_sensitive=True
)
@property
def SCOPE_NAME(self) -> str:
return f'api://{self.APP_CLIENT_ID}/{self.SCOPE_DESCRIPTION}'
@property
def SCOPES(self) -> dict:
return {self.SCOPE_NAME: self.SCOPE_DESCRIPTION}
settings = Settings()
# Configure Azure AD authentication scheme
azure_scheme = SingleTenantAzureAuthorizationCodeBearer(
app_client_id=settings.APP_CLIENT_ID,
tenant_id=settings.TENANT_ID,
scopes=settings.SCOPES,
)
app = FastAPI(
swagger_ui_oauth2_redirect_url='/oauth2-redirect',
swagger_ui_init_oauth={
'usePkceWithAuthorizationCodeGrant': True,
'clientId': settings.OPENAPI_CLIENT_ID,
'scopes': settings.SCOPE_NAME,
},
)
@app.get("/authenticated-hello")
async def authenticated_hello(user: User = Depends(azure_scheme)):
if not user:
raise HTTPException(status_code=status.HTTP_401_UNAUTHORIZED, detail="Not authenticated")
return {"message": f"Hello, {user.name}! Your roles: {user.roles}"}
# To run: uvicorn main:app --reload
# Make sure to set TENANT_ID, APP_CLIENT_ID, OPENAPI_CLIENT_ID in your .env file or environment variables.
# Also configure your Azure App Registration with the correct Redirect URIs (e.g., http://localhost:8000/oauth2-redirect).