跳转到内容
搜索文档

使用 FastAPI 验证 Access 令牌

最后更新 查看 MarkdownAgent 设置

本教程介绍如何验证针对 FastAPI 应用程序的请求中包含 Access JWT

完成所需时间: 15 分钟

前提条件

1. 创建验证函数

  1. 在您的 FastAPI 项目中,创建一个包含以下代码的名为 cloudflare.py 的新文件:
from fastapi import Request, HTTPException

# The Application Audience (AUD) tag for your application
POLICY_AUD = "XXXXX"

# Your CF Access team domain
TEAM_DOMAIN = "https://<your-team-name>.cloudflareaccess.com"
CERTS_URL = "{}/cdn-cgi/access/certs".format(TEAM_DOMAIN)

async def validate_cloudflare(request: Request):
    """
    Validate that the request is authenticated by Cloudflare Access.
    """
    if verify_token(request) != True:
        raise HTTPException(status_code=400, detail="Not authenticated properly!")


def _get_public_keys():
    """
    Returns:
        List of RSA public keys usable by PyJWT.
    """
    r = requests.get(CERTS_URL)
    public_keys = []
    jwk_set = r.json()
    for key_dict in jwk_set["keys"]:
        public_key = jwt.algorithms.RSAAlgorithm.from_jwk(json.dumps(key_dict))
        public_keys.append(public_key)
    return public_keys


def verify_token(request):
    """
    Verify the token in the request.
    """
    token = ""

    if "CF_Authorization" in request.cookies:
        token = request.cookies["CF_Authorization"]
    else:
        raise HTTPException(status_code=400, detail="missing required cf authorization token")

    keys = _get_public_keys()

    # Loop through the keys since we can't pass the key set to the decoder
    valid_token = False
    for key in keys:
        try:
            # decode returns the claims that has the email when needed
            jwt.decode(token, key=key, audience=POLICY_AUD, algorithms=["RS256"])
            valid_token = True
            break
        except:
            raise HTTPException(status_code=400, detail="Error decoding token")
    if not valid_token:
        raise HTTPException(status_code=400, detail="Invalid token")

    return True

2. 在您的应用程序中使用验证函数

您现在可以将验证函数添加为 FastAPI 应用程序中的依赖项。执行此操作的一种方法是创建一个 APIRouter 实例。以下示例针对每个向以 /admin 开头的路径发起的请求执行该验证函数:

from fastapi import APIRouter, Depends, HTTPException
from cloudflare import validate_cloudflare

router = APIRouter(
    prefix="/admin",
    tags=["admin"],
    dependencies=[Depends(validate_cloudflare)]
    responses={404: {"description": "Not found"}},
)

@router.get("/")
async def root():
    return {"message": "Hello World"}

这篇文档对您有帮助吗?