Python-FastAPI-完全教程笔记-全-

Python FastAPI 完全教程笔记(全)

001:第 1 部分

概述

在本课程中,我们将学习如何使用 FastAPI 框架构建 Web 应用程序。FastAPI 是一个流行的 Python Web 框架,因其高性能、简洁性以及对现代 Python 特性的支持而广受欢迎。在本系列视频中,我们将探讨该框架的不同方面,并学习如何利用它们在一个简单的 Web 应用程序中实现功能。

环境设置

上一节我们介绍了课程概述,本节中我们来看看如何设置开发环境。

要开始我们的项目,首先需要创建一个文件夹来安装项目依赖。

以下是创建和激活虚拟环境的步骤:

  1. 打开 VS Code 并创建一个新文件夹,例如 bookley
  2. 在 VS Code 中打开该文件夹。
  3. 打开终端,使用 Python 的 venv 模块创建虚拟环境:
    python3 -m venv venv
    
  4. 激活虚拟环境:
    • Linux/MacOS:
      source venv/bin/activate
      
    • Windows:
      venv\Scripts\activate
      
  5. 激活后,确认 Python 解释器指向虚拟环境:
    which python3
    

安装 FastAPI

现在我们已经激活了虚拟环境,接下来安装 FastAPI。

使用 pip 安装 FastAPI:

pip install fastapi

安装完成后,可以通过导入模块来验证安装:

import fastapi

或者,通过运行 FastAPI CLI 来验证:

fastapi

创建简单的 Web 服务器

上一节我们完成了环境设置和 FastAPI 安装,本节中我们来看看如何创建一个简单的 Web 服务器。

首先,创建一个名为 main.py 的文件。

main.py 中,导入 FastAPI 类并创建一个应用实例:

from fastapi import FastAPI

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/61b5aa4c68627fe37ce2e42649211167_68.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/61b5aa4c68627fe37ce2e42649211167_69.png)

app = FastAPI()

接下来,定义一个处理根路径 GET 请求的路由:

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

要运行这个服务器,可以使用 FastAPI 的开发服务器命令:

fastapi dev main.py

服务器将在 http://localhost:8000 启动。访问该地址,你将看到返回的 JSON 消息。

定义更多端点

上一节我们创建了一个简单的 Web 服务器,本节中我们来看看如何定义更多端点以返回不同的响应。

我们将创建一个用于问候用户的端点。

以下是创建带路径参数的问候端点的步骤:

  1. 定义一个 GET 端点,路径为 /greet/{name}
  2. 在路径处理函数中接收 name 参数。
  3. 返回包含问候消息的字典。

代码示例如下:

@app.get("/greet/{name}")
async def greet_name(name: str):
    return {"message": f"Hello {name}"}

访问 http://localhost:8000/greet/Jonathan,服务器将返回 {"message": "Hello Jonathan"}

使用 HTTP 客户端

到目前为止,我们一直使用浏览器作为 HTTP 客户端。但在实际开发中,使用专门的 HTTP 客户端工具(如 Postman、Insomnia 或 RESTfox)会更方便。

我们将使用 RESTfox 来测试我们的 API 端点。

以下是使用 RESTfox 的基本步骤:

  1. 打开 RESTfox 并创建一个新的工作空间。
  2. 在工作空间中创建一个新的 HTTP 请求。
  3. 设置请求方法(如 GET)和目标 URL(如 http://localhost:8000/)。
  4. 发送请求并查看响应。

查询参数

除了路径参数,FastAPI 还允许我们通过查询参数向服务器发送数据。

查询参数是通过 URL 中的键值对传递的,例如 ?name=Jonathan

以下是如何在 FastAPI 中定义和使用查询参数:

  1. 在路径处理函数中定义一个参数(例如 name),但不将其包含在 URL 路径中。
  2. FastAPI 会自动将其视为查询参数。
  3. 可以指定参数类型(如 str)和默认值。

代码示例如下:

@app.get("/greet")
async def greet_user(name: str = "User"):
    return {"message": f"Hello {name}"}

访问 http://localhost:8000/greet?name=Jonathan,服务器将返回 {"message": "Hello Jonathan"}

混合路径参数和查询参数

在某些情况下,我们可能需要在同一个端点中同时使用路径参数和查询参数。

以下是如何混合使用路径参数和查询参数:

  1. 在 URL 路径中定义路径参数(如 {name})。
  2. 在路径处理函数中定义额外的参数作为查询参数(如 age)。
  3. 发送请求时,在 URL 中提供路径参数,在查询字符串中提供查询参数。

代码示例如下:

@app.get("/greet/{name}")
async def greet_user_with_age(name: str, age: int = 0):
    return {"message": f"Hello {name}, you are {age} years old"}

访问 http://localhost:8000/greet/Jonathan?age=23,服务器将返回 {"message": "Hello Jonathan, you are 23 years old"}

可选查询参数

有时,我们希望查询参数是可选的,并在未提供时使用默认值。

以下是如何定义可选查询参数:

  1. typing 模块导入 Optional 类。
  2. 将参数类型定义为 Optional[str]Optional[int]
  3. 为参数提供默认值。

代码示例如下:

from typing import Optional

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/61b5aa4c68627fe37ce2e42649211167_98.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/61b5aa4c68627fe37ce2e42649211167_99.png)

@app.get("/greet")
async def greet_optional(name: Optional[str] = "User", age: Optional[int] = 0):
    return {"message": f"Hello {name}, you are {age} years old"}

如果访问 http://localhost:8000/greet,服务器将返回 {"message": "Hello User, you are 0 years old"}。如果提供 nameage 参数,则使用提供的值。

请求体

除了路径参数和查询参数,我们还可以通过请求体向服务器发送数据,通常用于创建或更新资源。

以下是如何使用请求体发送数据:

  1. 定义一个 Pydantic 模型来验证请求体数据。
  2. 在路径处理函数中将该模型作为参数注入。
  3. 使用模型验证数据并返回响应。

代码示例如下:

from pydantic import BaseModel

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/61b5aa4c68627fe37ce2e42649211167_108.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/61b5aa4c68627fe37ce2e42649211167_109.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/61b5aa4c68627fe37ce2e42649211167_111.png)

class BookCreate(BaseModel):
    title: str
    author: str

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/61b5aa4c68627fe37ce2e42649211167_113.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/61b5aa4c68627fe37ce2e42649211167_115.png)

@app.post("/createbook")
async def create_book(book: BookCreate):
    return {"title": book.title, "author": book.author}

使用 RESTfox 发送 POST 请求到 http://localhost:8000/createbook,并在请求体中提供 JSON 数据(如 {"title": "Learn FastAPI", "author": "John Doe"}),服务器将返回创建的书本信息。

请求头

FastAPI 允许我们访问请求头信息,例如 User-AgentHost 等。

以下是如何访问请求头:

  1. fastapi 导入 Header 函数。
  2. 在路径处理函数中定义参数,并使用 Header 作为默认值。
  3. 返回包含请求头信息的字典。

代码示例如下:

from fastapi import Header

@app.get("/headers")
async def get_headers(user_agent: Optional[str] = Header(None), host: Optional[str] = Header(None)):
    return {"User-Agent": user_agent, "Host": host}

访问 http://localhost:8000/headers,服务器将返回请求头信息。

状态码

我们可以自定义端点返回的 HTTP 状态码。

以下是如何指定状态码:

  1. fastapi 导入 status 模块。
  2. 在路由装饰器中指定 status_code 参数。

代码示例如下:

from fastapi import status

@app.post("/createbook", status_code=status.HTTP_201_CREATED)
async def create_book(book: BookCreate):
    return {"title": book.title, "author": book.author}

当创建资源成功时,服务器将返回状态码 201(Created)。

总结

本节课中我们一起学习了如何使用 FastAPI 构建简单的 Web 服务器。我们探讨了如何定义路由、使用路径参数和查询参数、处理请求体、访问请求头以及自定义状态码。通过这些基础知识,你已经能够创建功能丰富的 API 端点。在接下来的课程中,我们将深入探讨更高级的主题,如数据库集成、身份验证和授权等。

002:构建用户认证、授权、关系与部署

概述

在本节课中,我们将学习如何使用 FastAPI 构建一个完整的 API 端点,包括用户认证、授权、数据库关系、错误处理、中间件、电子邮件发送、后台任务、API 文档以及最终部署。我们将从获取当前登录用户开始,逐步实现角色管理、数据库关系、错误处理、中间件、电子邮件验证、密码重置、后台任务、API 文档和部署。


获取当前登录用户

上一节我们介绍了令牌验证,本节中我们来看看如何获取当前登录用户。

首先,我们需要创建一个依赖项来获取当前登录的用户。这个依赖项将使用我们之前创建的令牌验证依赖项。

from fastapi import Depends
from sqlalchemy.ext.asyncio import AsyncSession
from source.db.main import get_session
from source.auth.service import UserService
from source.auth.models import User

async def get_current_user(
    token: str = Depends(AccessTokenBearer()),
    session: AsyncSession = Depends(get_session)
) -> User:
    token_data = decode_access_token(token)
    user_email = token_data.get("user", {}).get("email")
    user_service = UserService()
    user = await user_service.get_user_by_email(session, user_email)
    return user

接下来,我们创建一个路由来获取当前登录用户。

from fastapi import APIRouter, Depends
from source.auth.dependencies import get_current_user

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_10.png)

router = APIRouter()

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_12.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_14.png)

@router.get("/me")
async def get_current_user_endpoint(user: User = Depends(get_current_user)):
    return user

现在,我们可以测试这个端点。首先,我们需要获取一个有效的访问令牌,然后在请求头中添加授权头。


角色管理

上一节我们介绍了如何获取当前登录用户,本节中我们来看看如何实现角色管理。

首先,我们在用户模型中添加一个角色字段。

from sqlmodel import Field
from typing import Optional

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_16.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_18.png)

class User(SQLModel, table=True):
    role: Optional[str] = Field(default="user", sa_column_kwargs={"server_default": "user"})

接下来,我们创建一个依赖项来检查用户角色。

from fastapi import HTTPException, status
from typing import List

class RoleChecker:
    def __init__(self, allowed_roles: List[str]):
        self.allowed_roles = allowed_roles

    async def __call__(self, current_user: User = Depends(get_current_user)):
        if current_user.role in self.allowed_roles:
            return True
        raise HTTPException(
            status_code=status.HTTP_403_FORBIDDEN,
            detail="You are not permitted to perform this action."
        )

现在,我们可以在路由中使用这个依赖项来限制访问。

from source.auth.dependencies import RoleChecker

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_20.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_21.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_22.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_23.png)

admin_role_checker = RoleChecker(allowed_roles=["admin"])

@router.get("/admin-only", dependencies=[Depends(admin_role_checker)])
async def admin_only_endpoint():
    return {"message": "This is an admin-only endpoint."}

数据库关系

上一节我们介绍了角色管理,本节中我们来看看如何建立数据库关系。

首先,我们在书籍模型中添加一个外键,关联到用户表。

from sqlmodel import Field, Relationship
from typing import Optional

class Book(SQLModel, table=True):
    user_uid: Optional[str] = Field(default=None, foreign_key="user.uid")
    user: Optional[User] = Relationship(back_populates="books")

接下来,我们在用户模型中添加反向关系。

class User(SQLModel, table=True):
    books: List[Book] = Relationship(back_populates="user")

现在,我们可以在创建书籍时关联当前登录用户。

@router.post("/books")
async def create_book(
    book_data: BookCreate,
    user: User = Depends(get_current_user),
    session: AsyncSession = Depends(get_session)
):
    book_service = BookService()
    book = await book_service.create_book(session, book_data, user.uid)
    return book

错误处理

上一节我们介绍了数据库关系,本节中我们来看看如何自定义错误处理。

首先,我们创建一个自定义异常类。

class BooklyException(Exception):
    """Base class for all custom exceptions in the app."""
    pass

class InvalidTokenError(BooklyException):
    """Raised when an invalid or expired token is provided."""
    pass

接下来,我们创建一个异常处理器。

from fastapi import Request
from fastapi.responses import JSONResponse

def create_exception_handler(status_code: int, detail: Any):
    async def exception_handler(request: Request, exc: Exception):
        return JSONResponse(
            content={"detail": detail},
            status_code=status_code
        )
    return exception_handler

然后,我们将自定义异常注册到 FastAPI 应用中。

from source.errors import InvalidTokenError

app.add_exception_handler(InvalidTokenError, create_exception_handler(401, "Invalid token provided."))

中间件

上一节我们介绍了错误处理,本节中我们来看看如何使用中间件。

首先,我们创建一个日志中间件。

import time
from fastapi import Request

@app.middleware("http")
async def custom_logging_middleware(request: Request, call_next):
    start_time = time.time()
    response = await call_next(request)
    process_time = time.time() - start_time
    print(f"{request.method} {request.url.path} completed in {process_time:.2f}s")
    return response

接下来,我们创建一个授权中间件。

from fastapi.responses import JSONResponse

@app.middleware("http")
async def authorization_middleware(request: Request, call_next):
    if "authorization" not in request.headers:
        return JSONResponse(
            content={"message": "Not authenticated", "resolution": "Please provide valid credentials."},
            status_code=401
        )
    response = await call_next(request)
    return response


电子邮件发送

上一节我们介绍了中间件,本节中我们来看看如何发送电子邮件。

首先,我们配置电子邮件设置。

from fastapi_mail import FastMail, ConnectionConfig

config = ConnectionConfig(
    MAIL_USERNAME="your-email@gmail.com",
    MAIL_PASSWORD="your-app-password",
    MAIL_FROM="your-email@gmail.com",
    MAIL_PORT=587,
    MAIL_SERVER="smtp.gmail.com",
    MAIL_STARTTLS=True,
    MAIL_SSL_TLS=False
)

fm = FastMail(config)

接下来,我们创建一个发送电子邮件的函数。

from fastapi_mail import MessageSchema

async def send_email(recipients: List[str], subject: str, body: str):
    message = MessageSchema(
        recipients=recipients,
        subject=subject,
        body=body,
        subtype="html"
    )
    await fm.send_message(message)

现在,我们可以在用户注册时发送验证电子邮件。

@router.post("/signup")
async def signup(user_data: UserCreate, session: AsyncSession = Depends(get_session)):
    user_service = UserService()
    user = await user_service.create_user(session, user_data)
    verification_token = create_url_safe_token({"email": user.email})
    verification_link = f"{config.DOMAIN}/auth/verify/{verification_token}"
    html_message = f"<h1>Verify your email</h1><p>Click <a href='{verification_link}'>here</a> to verify your email.</p>"
    await send_email([user.email], "Verify your email", html_message)
    return {"message": "Account created. Please check your email to verify your account."}

密码重置

上一节我们介绍了电子邮件发送,本节中我们来看看如何实现密码重置。

首先,我们创建一个密码重置请求端点。

@router.post("/password-reset-request")
async def password_reset_request(email_data: EmailSchema):
    user_service = UserService()
    user = await user_service.get_user_by_email(session, email_data.email)
    if not user:
        raise HTTPException(status_code=404, detail="User not found.")
    reset_token = create_url_safe_token({"email": user.email})
    reset_link = f"{config.DOMAIN}/auth/password-reset-confirm/{reset_token}"
    html_message = f"<h1>Reset your password</h1><p>Click <a href='{reset_link}'>here</a> to reset your password.</p>"
    await send_email([user.email], "Reset your password", html_message)
    return {"message": "Password reset link sent. Please check your email."}

接下来,我们创建一个密码重置确认端点。

@router.post("/password-reset-confirm/{token}")
async def password_reset_confirm(token: str, passwords: PasswordResetConfirm, session: AsyncSession = Depends(get_session)):
    token_data = decode_url_safe_token(token)
    user_email = token_data.get("email")
    user_service = UserService()
    user = await user_service.get_user_by_email(session, user_email)
    if not user:
        raise HTTPException(status_code=404, detail="User not found.")
    if passwords.new_password != passwords.confirm_new_password:
        raise HTTPException(status_code=400, detail="Passwords do not match.")
    hashed_password = generate_password_hash(passwords.new_password)
    await user_service.update_user(session, user, {"password_hash": hashed_password})
    return {"message": "Password reset successfully."}

后台任务

上一节我们介绍了密码重置,本节中我们来看看如何使用后台任务。

首先,我们使用 FastAPI 的内置后台任务功能。

from fastapi import BackgroundTasks

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_107.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_108.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_109.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_111.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_113.png)

@router.post("/send-email")
async def send_email_endpoint(
    email_data: EmailSchema,
    background_tasks: BackgroundTasks
):
    html_message = "<h1>Welcome to the app</h1>"
    background_tasks.add_task(send_email, email_data.addresses, "Welcome", html_message)
    return {"message": "Email sent successfully."}

接下来,我们使用 Celery 处理后台任务。

from celery import Celery

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_141.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_143.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_145.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_147.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_149.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_151.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_152.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_154.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_156.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_158.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_160.png)

celery_app = Celery("tasks", broker=config.REDIS_URL, backend=config.REDIS_URL)

@celery_app.task
def send_email_task(recipients: List[str], subject: str, body: str):
    # 发送电子邮件的逻辑
    pass

现在,我们可以在路由中调用 Celery 任务。

@router.post("/send-email-celery")
async def send_email_celery_endpoint(email_data: EmailSchema):
    html_message = "<h1>Welcome to the app</h1>"
    send_email_task.delay(email_data.addresses, "Welcome", html_message)
    return {"message": "Email sent successfully."}

API 文档

上一节我们介绍了后台任务,本节中我们来看看如何生成 API 文档。

FastAPI 自动生成 OpenAPI 文档,我们可以通过访问 /docs/redoc 来查看。

我们还可以自定义文档的元数据。

from fastapi import FastAPI

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_178.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_180.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_181.png)

![](https://github.com/OpenDocCN/cs-notes-pt1-zh/raw/master/docs/py-fapi-cmpl-tut/img/7d5adcabc5e6be579c6937eaaf16dbca_183.png)

app = FastAPI(
    title="Bookly API",
    description="A simple book review API.",
    version="1.0.0",
    contact={
        "name": "Your Name",
        "email": "your-email@example.com"
    },
    docs_url="/api/docs",
    redoc_url="/api/redoc"
)


部署

上一节我们介绍了 API 文档,本节中我们来看看如何部署应用。

我们将使用 Render 平台部署 FastAPI 应用、PostgreSQL 数据库、Redis 和 Celery 工作器。

部署步骤:

  1. 创建 Web 服务,指向 FastAPI 应用。
  2. 创建 PostgreSQL 数据库,并更新环境变量。
  3. 创建 Redis 实例,用于任务队列。
  4. 创建 Celery 工作器,处理后台任务。
  5. 更新环境变量,确保所有服务正确连接。

环境变量示例:

DATABASE_URL=postgresql+asyncpg://user:password@host:port/dbname
REDIS_URL=redis://host:port
MAIL_USERNAME=your-email@gmail.com
MAIL_PASSWORD=your-app-password
DOMAIN=https://your-app.onrender.com

启动命令:

  • Web 服务:fastapi run source
  • Celery 工作器:celery -A source.celery_tasks.celery_app worker --loglevel=info


总结

在本节课中,我们一起学习了如何使用 FastAPI 构建一个完整的 API 应用。我们从获取当前登录用户开始,逐步实现了角色管理、数据库关系、错误处理、中间件、电子邮件发送、密码重置、后台任务、API 文档和部署。通过这些内容,你应该能够构建一个功能齐全的 FastAPI 应用,并将其部署到生产环境中。

posted @ 2026-03-29 09:24  布客飞龙II  阅读(52)  评论(0)    收藏  举报