1.6.1分析

同一段接口逻辑,根据参数不同返回不同的数据

1.6.2介绍

参数就是客户端发送请求时附带的额外信息和指令

参数的作用是让同一个接口能根据不同的输入,返回不同的输出,实现动态交互

1.6.3参数分类

1.6.3.1路径参数(Path Parameter)
  • 位置:URL 路径的一部分,格式为 /资源/{参数名}(如 /book/{id})。
  • 作用:指向唯一的、特定的资源(如获取某本具体书籍的信息)。
  • 常用方法:GET(用于获取资源)。
@app.get("/book/{id}") # 定义请求的的路径,请求方式为get
async def get_book(id: int): # 定义这个接口,接收一个参数id,数据类型为int
    # 返回响应结果
    return {"id": id, "title": f"这是第{id}本书"}

--->运行后查看旁边的运行结果

接口文档中进行测试

注意:这里进行参数调试的时候,必须填一个值,否则直接excute会报错

1.6.3.1.1类型注解Path

FastAPI 允许为参数声明额外的信息和校验

@app.get("/book/{id}") 
async def get_book(id: int): 
    return {"id": id, "title": f"这是第{id}本书"}
1.6.3.1.2导入 FastAPI 的 Path 函数
@app.get("/book/{id}")
async def get_book(id: int = Path()):
    return {"id": id, "title": f"这是第{id}本书"}
# 定义请求的的路径,请求方式为get
@app.get("/book/{id}")
# 定义这个接口,接收一个参数id,数据类型为int
async def get_book(id: int=Path(...,gt=0,lt=101)):
    # 返回响应结果
    return {"id": id, "title": f"这是第{id}本书"}

重启,然后找到接口填写111

1.6.3.1.3会发现报错了,id要求不能大于101,
# 定义请求的的路径,请求方式为get
@app.get("/book/{id}")
# 定义这个接口,接收一个参数id,数据类型为int
async def get_book(id: int=Path(...,gt=0,lt=101,description="书籍id,取值范围为1-100")):
    # 返回响应结果
    return {"id": id, "title": f"这是第{id}本书"}
# 需求:查找书籍的作者,路径参数 name,长度范围 2-10
@app.get("/book/{name}")
async def get_name(name: str = Path(..., min_length=2, max_length=10, description="书籍名称,长度范围为2-10")):
    return {"msg": f'这是{name}的信息'}
1.6.3.1.4小结
  • 路径参数出现在什么位置?

URL 路径的一部分

  • 如何为路径参数添加类型注解?

Python 原生注解 和 Path 注解

1.6.3.1.5练习

需求:定义两个接口,携带路径参数,并使用 Path 来实现类型注解

具体如下:

  • 接口1:以 新闻分类 id 为参数设计 URL,id 范围为 1 ~ 100
  • 接口2:以 新闻分类名称为参数设计 URL,分类名称长度为 2 ~ 10
from fastapi import FastAPI, Path

app = FastAPI()

# ---------------------------------------------------------
# 接口1:新闻分类 ID
# 需求:id 范围为 1 ~ 100
# URL 示例: /news/category/50
# ---------------------------------------------------------
@app.get("/news/category/{category_id}")
async def get_news_by_id(
    category_id: int = Path(
        ..., 
        title="新闻分类ID", 
        description="新闻分类的唯一标识符", 
        ge=1,   # 大于等于 1
        le=100  # 小于等于 100
    )
):
    return {"category_id": category_id, "message": "成功获取该分类下的新闻"}


# ---------------------------------------------------------
# 接口2:新闻分类名称
# 需求:分类名称长度为 2 ~ 10
# URL 示例: /news/search/科技
# ---------------------------------------------------------
@app.get("/news/search/{category_name}")
async def get_news_by_name(
    category_name: str = Path(
        ..., 
        title="新闻分类名称", 
        description="新闻分类的名称关键字", 
        min_length=2,  # 最小长度 2
        max_length=10  # 最大长度 10
    )
):
    return {"category_name": category_name, "message": "成功搜索该分类相关的新闻"}
1.6.3.2查询参数(Query Parameter)
  • 位置:URL 中 ? 之后,格式为 key1=value1&key2=value2(如 ?page=1&sort=desc)。
  • 作用:对资源集合进行过滤、排序、分页等操作(如查询“第1页、按时间降序”的书籍列表)。
  • 常用方法:GET(用于获取资源集合的筛选结果)。

声明的参数不是路径参数时,路径操作函数会把该参数自动解释为查询参数

在news_list后面拼接参数,如右图:

# 需求:查询新闻页->分页,skip:跳过的记录数,limit:返回的记录数 10
@app.get("/news/news_list")
async def get_news_list(skip: int, limit: int = 10):
    return {"skip": skip, "limit": limit}
1.6.3.2.1类型注解 Query

导入 FastAPI 的 Query 函数

# 需求:查询新闻页->分页,skip:跳过的记录数,limit:返回的记录数 10
@app.get("/news/news_list")
async def get_news_list(
    skip: int = Query(0, description="跳过的记录数",lt=100),
    limit: int = Query(10, description="返回的记录数",lt=100)
):
    return {"skip": skip, "limit": limit}
1.6.3.2.2小结
  • 查询参数出现在什么位置?

URL? 之后, k1=v1&k2=v2

  • 如何为查询参数添加类型注解?

Python 原生注解 和 Query 注解

1.6.3.2.3练习

需求:设计接口查询图书,要求携带两个查询参数:图书分类和价格

参数具体要求:

  • 图书分类:默认值为 Python开发,长度限制5 ~ 255
  • 价格:限制大小范围 50 ~ 100
from fastapi import FastAPI, Query

app = FastAPI()

@app.get("/books/")
async def read_books(
    # 需求:图书分类,默认值为 "Python开发",长度限制 5 ~ 255
    category: str = Query(
        "Python开发", 
        min_length=5, 
        max_length=255,
        description="图书的分类名称"
    ),
    # 需求:价格,限制大小范围 50 ~ 100
    price: float = Query(
        ..., 
        ge=50, 
        le=100,
        description="图书的价格范围"
    )
):
    return {
        "category": category, 
        "price": price,
        "message": "查询成功"
    }
1.6.3.3请求体(Request Body)
  • 位置:HTTP 请求的消息体(body)中,常以 JSON 等格式携带数据。
  • 作用:用于创建、更新资源,或携带大量数据(如提交书籍的详细信息、更新用户资料)。
  • 常用方法:POST(创建资源)、PUT(更新资源)等。

在HTTP协议中,一个完整的请求由三部分组成:

① 请求行:包含方法、URL、协议版本

② 请求头:元数据信息(Content-Type、Authorization等)

③ 请求体:实际要发送的数据内容

1.6.3.3.1定义类型
from pydantic import BaseModel
class User(BaseModel):
    username: str
    password: str
  • 类型注解
@app.post("/register")
async def register(user: User):
    return user

响应结果如下:

1.6.3.3.2练习

需求:设计接口新增图书,图书信息包含:书名、作者、出版社、售价

from fastapi import FastAPI
from pydantic import BaseModel
from typing import Optional

app = FastAPI()

# 1. 定义数据模型 (Pydantic Model)
class BookItem(BaseModel):
    title: str          # 书名
    author: str         # 作者
    publisher: str      # 出版社
    price: float        # 售价

# 2. 定义新增图书接口
@app.post("/books/", summary="新增图书")
async def create_book(book: BookItem):
    """
    接收 JSON 格式的图书信息并返回
    """
    # 这里通常会写数据库插入逻辑
    return {
        "message": "图书新增成功",
        "book_info": book
    }
1.6.3.3.3类型注解 Field

导入 pydantic 的Field函数

from pydantic import BaseModel, Field
class User(BaseModel):
    username: str = Field(...)
    password: str = Field(...)
# 注册:用户名和密码->str
class User(BaseModel):
    username: str = Field(default="张三", min_length=2, max_length=10, description="用户名,长度范围为2-10")
    password: str = Field(min_length=6, max_length=20, description="密码,长度范围为6-20")

@app.post("/register")
async def register(user: User):
    return user
1.6.3.3.4小结
  • 请求体参数的作用是什么?

创建、更新资源

  • 如何定义、使用请求体参数?
# 注册:用户名和密码->str
class User(BaseModel):
    username: str = Field(default="张三", min_length=2, max_length=10, description="用户名,长度范围为2-10")
    password: str = Field(min_length=6, max_length=20, description="密码,长度范围为6-20")

@app.post("/register")
async def register(user: User):
    return user
  • 如何为请求体参数添加类型注解?

Python 原生注解 和 Field 注解

1.6.3.3.5练习

需求:设计接口新增图书,图书信息包含:书名、作者、出版社、售价

具体要求如下:

 书名:不能为空;长度 2 ~ 20

 作者:长度 2 ~ 10

 出版社:默认值“黑马出版社”

 售价:不能为空;价格大于0元

from fastapi import FastAPI
from pydantic import BaseModel, Field
from typing import Optional

app = FastAPI()

# 1. 定义数据模型
class Book(BaseModel):
    # 书名:不能为空;长度 2 ~ 20
    book_name: str = Field(
        ..., 
        min_length=2, 
        max_length=20, 
        description="书名,必填,2-20字"
    )
    # 作者:长度 2 ~ 10
    author: str = Field(
        ..., 
        min_length=2, 
        max_length=10, 
        description="作者,必填,2-10字"
    )
    # 出版社:默认值“黑马出版社”
    publisher: str = Field(
        default="黑马出版社", 
        description="出版社,默认黑马出版社"
    )
    # 售价:不能为空;价格大于0元
    price: float = Field(
        ..., 
        gt=0, 
        description="价格,必填,大于0"
    )

# 2. 定义新增图书接口
@app.post("/books", summary="新增图书")
async def create_book(book: Book):
    """
    接收图书信息,校验通过后返回
    """
    # 这里可以添加保存到数据库的逻辑
    return {"message": "图书新增成功", "book_data": book}
1.6.3.3.4核心区别总结

完整代码

from fastapi import FastAPI, Path, Query
from pydantic import BaseModel,Field

# 创建FastAPI实例
app = FastAPI()


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


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


# 访问/hello响应结果 msg:你好 FastAPI
@app.get("/hello")
async def get_hello():
    return {"msg": "你好 FastAPI"}


@app.get(" /user/hello")
async def get_user_hello():
    return {"msg": "我正在学习 FastAPI ......"}


# 定义请求的的路径,请求方式为get
@app.get("/book/{id}")
# 定义这个接口,接收一个参数id,数据类型为int
async def get_book(id: int = Path(..., gt=0, lt=101, description="书籍id,取值范围为1-100")):
    # 返回响应结果
    return {"id": id, "title": f"这是第{id}本书"}


# 需求:查找书籍的作者,路径参数 name,长度范围 2-10
@app.get("/book/{name}")
async def get_name(name: str = Path(..., min_length=2, max_length=10, description="书籍名称,长度范围为2-10")):
    return {"msg": f'这是{name}的信息'}


# 需求:查询新闻页->分页,skip:跳过的记录数,limit:返回的记录数 10
@app.get("/news/news_list")
async def get_news_list(
    skip: int = Query(0, description="跳过的记录数",lt=100),
    limit: int = Query(10, description="返回的记录数",lt=100)
):
    return {"skip": skip, "limit": limit}

# 注册:用户名和密码->str
class User(BaseModel):
    username: str = Field(default="张三", min_length=2, max_length=10, description="用户名,长度范围为2-10")
    password: str = Field(min_length=6, max_length=20, description="密码,长度范围为6-20")

@app.post("/register")
async def register(user: User):
    return user
Logo

AtomGit 是由开放原子开源基金会联合 CSDN 等生态伙伴共同推出的新一代开源与人工智能协作平台。平台坚持“开放、中立、公益”的理念,把代码托管、模型共享、数据集托管、智能体开发体验和算力服务整合在一起,为开发者提供从开发、训练到部署的一站式体验。

更多推荐