FastAPI 如何只允许特定 IP 的端点访问?

FastAPI how to allow endpoint access for specific IP only?

如何使用 FastAPI 将端点访问限制为仅特定 IP?

FastAPI 提供了一个TrustedHostMiddleware

Enforces that all incoming requests have a correctly set Host header, in order to guard against HTTP Host Header attacks.

from fastapi import FastAPI from fastapi.middleware.trustedhost import TrustedHostMiddleware

app = FastAPI()

app.add_middleware(
    TrustedHostMiddleware, allowed_hosts=["example.com","*.example.com"] 
)


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

The following arguments are supported:

  • allowed_hosts - A list of domain names that should be allowed as hostnames. Wildcard domains such as *.example.com are supported for matching subdomains to allow any hostname either use allowed_hosts=["*"] or omit the middleware.

If an incoming request does not validate correctly then a 400 response will be sent.

另一种解决方案是为您的部署介质(例如:k8)编写一个 IP 白名单。

接受的答案使用 TrustedHostMiddleware but that can be easily spoofed using a reverse proxy, i.e. using NGINX or using any other technique. In my opinion, validating IP address in a custom middleware 更安全:

from fastapi import FastAPI, Request, status
from fastapi.responses import JSONResponse


app = FastAPI()

# Whitelisted IPs
WHITELISTED_IPS = []

@app.middleware('http')
async def validate_ip(request: Request, call_next):
    # Get client IP
    ip = str(request.client.host)
    
    # Check if IP is allowed
    if ip not in WHITELISTED_IPS:
        data = {
            'message': f'IP {ip} is not allowed to access this resource.'
        }
        return JSONResponse(status_code=status.HTTP_400_BAD_REQUEST, content=data)

    # Proceed if IP is allowed
    return await call_next(request)

我会维护一个列入白名单的 IP 列表,然后将客户端 IP 与该列表进行比较,如果 IP 不在列入白名单的 IP 列表中,则会 return 出现 400 Bad Request 错误.