zoukankan      html  css  js  c++  java
  • FastApi学习(一)

    前言

    学习不止

    正文

    介绍

    FastApi是PythonWeb框架的‘新晋干员’,虽然年轻但是很能打
    目前已有 12k start
    GitHub
    官网
    为什么说他能打呢?它内部使用了 Python 的 Async 异步,因此速度很快, 也要求必须是 Py3.6+
    Async 不同于之前自己实现的 gevent ,Async是官方写的, 听说Py4将会大量使用来提高效率
    FastApi官网展示了FastApi的特点

    快速:非常高的性能,看齐的NodeJS和Go(感谢Starlette和Pydantic)。现有最快的Python框架之一。
    快速编码:将功能开发速度提高约200%至300%。
    更少的错误:减少约40%的人为错误(开发人员)。
    直观:强大的编辑器支持。完成无处不在。调试时间更少。
    简易:旨在易于使用和学习。减少阅读文档的时间。
    短:最小化代码重复。每个参数声明中的多个功能。更少的错误。
    健壮:获取可用于生产的代码。具有自动交互式文档。
    基于标准:基于(并完全兼容)API的开放标准:OpenAPI(以前称为Swagger)和JSON Schema。

    才学了一点点的我已经有了类似的感受
    关于效率,官网提供了一个基准测试如下
    点我查看
    关于官方说的与GO和NodeJS看齐这个可以在学习的最后来与Go的Gin对比一下,日后再说

    安装

    我们使用 pip 来安装
    需要注意的是, 官方推荐了可以与 FastApi 搭配的几个模块, 基本上涵盖了几个大的使用场景

    由Pydantic使用:
    
    ujson-用于更快的JSON “解析”。
    email_validator -用于电子邮件验证。
    由Starlette使用:
    
    requests-如果要使用,则为必填TestClient。
    aiofiles-如果要使用FileResponse或,则为必填StaticFiles。
    jinja2 -如果要使用默认模板配置,则为必需。
    python-multipart-如果要使用来支持表单“解析”,则为必填request.form()。
    itsdangerous-需要SessionMiddleware支持。
    pyyaml-Starlette SchemaGenerator支持所必需的(FastAPI 可能不需要它)。
    graphene-需要GraphQLApp支持。
    ujson-如果要使用,则为必需UJSONResponse。
    由FastAPI / Starlette使用:
    
    uvicorn -用于加载和服务您的应用程序的服务器。
    orjson-如果要使用,则为必需ORJSONResponse。
    您可以使用安装所有这些pip install fastapi[all]。
    

    也就是说,你可以使用 pip install fastapi[all] 来安装以上推荐的所有模块
    如果执行时报错: zsh: no matches found: fastapi[all]
    请使用: pip install "fastapi[all]"
    如果你不想这样安装,请先安装 两个必须的模块,其他按需安装
    pip install fastapi
    pip install uvicorn
    uvicorn 类似于UWSGI的作用,官网说他与FastApi搭配是性能最佳

    HelloWorld

    在安装完依赖后,一切的一切就从 HelloWorld 开始
    新建一个 py 文件名叫 main.py
    内容如下

    from fastapi import FastAPI
    
    app = FastAPI()  # 初始化app
    
    @app.get("/")  # 监听GET请求
    async def read_root():
        return {"hello": "world"}  # 返回json
    

    以上就是最简单的一个 Fast 接口, 需要注意的是, FastApi内部处理网络io的时候使用的是Async, 但是进入函数的具体逻辑不受框架控制, 你可以写成同步,当然写成异步最佳,这里及本系列后面的都是能用异步则用异步,实在没有的再用同步

    启动这个项目,在命令行下输入

    uvicorn main:app --reload

    这行命令的意思是使用 uvicorn 启动 main.py 的 app

    reload 指检测到文件改动时自动重载(这在调试时非常有用)

    运行后会输出

    (.venv) ➜  fast uvicorn main:app --reload
    INFO:     Uvicorn running on http://127.0.0.1:8000 (Press CTRL+C to quit)
    INFO:     Started reloader process [70401]
    INFO:     Started server process [70404]
    INFO:     Waiting for application startup.
    INFO:     Application startup complete.
    

    代表启动成功,此时我们可以使用 postman 等调试工具测试接口

    以 get 的方式请求 http://127.0.0.1:8000/

    返回我们定义的数据为正常

    {
        "hello": "world"
    }
    

    自动生成接口文档

    FastApi 会自己给你生成接口文档, 真正的解放你的双手

    FastApi 默认提供了两种接口文档, 其实内容一样, 只是使用了两个开源的文档框架

    swagger

    这得益于 swagger 的帮助, swagger的更多使用这里不再赘述

    默认的文档位置在 http://127.0.0.1:8000/docs 使用浏览器打开即可

    在你更新代码时接口文档也会同步更新

    redoc

    得益于 redoc 的帮助, redoc的更多使用这里不再赘述

    默认的文档位置在 http://127.0.0.1:8000/redoc 使用浏览器打开即可

    在你更新代码时接口文档也会同步更新

    get传参

    在 get 请求时,传递参数通常使用 url 拼接参数和 query 的方式传参

    url传参

    比如 http://127.0.0.1:8000/phone/123456

    在 main.py 中增加函数

    @app.get("/phone/{phone}")
    async def get_phone(phone: int):
        return {"phone": phone}
    

    这里强调一下, phone: int 是声明参数 phone 是 int 类型,这是 python 3.5+ 有的语法, 目的是增加对开发人员的友好度与IDE的提示, 以后有时间会单独铺开讲

    因我们在启动时设置了 --reload 所以我们在保存时项目会自己更新, 同时 docs 也会更新

    我们访问url查看结果

    {
        "phone": 123456
    }
    

    query传参

    比如: http://127.0.0.1:8000/user?user_id=12

    在函数中是

    @app.get("/user")
    async def get_user(user_id: int):
        return {"user_id": user_id}
    

    复合传参

    如果一个请求中有两种方式

    http://127.0.0.1:8000/user/12?mod=login

    对应的是

    @app.get("/user/{user_id}")
    async def user_mod(user_id: int, mod: str = None):  # str = None 代表mod参数可以为空
        return {
            "user_id": user_id,
            "mod": mod
        }
    

    返回

    {
        "user_id": 12,
        "mod": "login"
    }
    

    body传参

    针对Body传参的情况, 其实也是以函数传参的形式, 但是考虑到传统的 form-data 传参方式字段很多, 我们可以采用 application/json 的方式, 并且定义一个参数类来管控参数

    from fastapi import FastAPI
    from pydantic import BaseModel
    
    app = FastAPI()
    
    
    class Item(BaseModel):  # 定义一个类用作参数
        name: str
        price: float
        is_offer: bool = None  # 该字段可为空
    
    
    @app.put("/{item_id}")
    async def update_item(item_id: int, item: Item):  # item需要与Item对象定义保持一致
        return {
            "item_name": item.name,
            "item_id": item_id
        }
    

    这里接受 URL 参数与 Body 的 json 格式的参数

    举个例子, 我们使用 postman 调试, Body里设置为 json 传递

    {
    	"name": "t1",
    	"price": 12.8
    }
    

    这里注意我们没有传递 is_offer 因为可以为空

    url为 http://127.0.0.1:8000/12 , 请求方式为 put, 结果为

    {
        "item_name": "t1",
        "item_id": 12
    }
    

    与类型声明结合

    如果你试过在以上几种接口中传递错误的参数或者少传递参数, 你会发现 FastApi 会自己返回错误给客户端,

    比如在参数中定义了 id 为 int 的时候传递了 str

    没错, FastApi 将其与 类型声明 结合在了一起, 这便是其另一个强大之处,附上官网的解释

    总而言之,您一次将参数,主体等的类型声明为函数参数。

    您可以使用标准的现代Python类型来做到这一点。

    您不必学习新的语法,特定库的方法或类等。

    只是标准的Python 3.6+

    例如,对于int

    item_id: int
    

    或更复杂的Item模型:

    item: Item
    

    ...并且使用该单个声明,您将获得:

    • 编辑器支持,包括:

      • 完成。
      • 类型检查。
    • 数据验证:

      • 数据无效时自动清除错误。

      • 甚至对深度嵌套的JSON对象也进行验证。

      • 输入数据的转换:从网络转换为Python数据和类型。读自:

      • JSON。

      • 路径参数。

      • 查询参数。

      • 饼干。

      • 标头。

      • 形式。

      • 文件。

    • 转换

      输出的数据:从Python数据和类型转换为网络数据(JSON):

      • 转换的Python类型(strintfloatboollist,等)。
      • datetime 对象。
      • UUID 对象。
      • 数据库模型。
      • ...还有很多。
    • 自动交互式API文档,包括2个备用用户界面:

      • 招摇UI。
      • ReDoc。

    回到前面的代码示例,FastAPI将:

    • 验证和请求item_id的路径中是否存在。PUT

    • 验证 item_id 的类型 intPUT 请求。

    • 如果不是,客户端将看到一个有用的明确错误。

    • 对于 PUT 请求 /items/{item_id} ,请以JSON格式读取正文:

    • 检查其是否具有必填属性name,该属性应为str

    • 检查其是否具有必填属性price,该属性必须为float

    • 检查它是否具有可选属性,如果存在is_offer,则应为bool

    • 所有这些对于深度嵌套的JSON对象也适用。

    • 自动从和转换为JSON。

    • 使用OpenAPI记录所有内容,可用于:

      • 交互式文档系统。
      • 自动客户端代码生成系统,适用于多种语言。
    • 直接提供2个交互式文档Web界面。

  • 相关阅读:
    guzzle 中间件原理
    K8S-K8S 环境搭建
    K8S-k8s 理念知识
    云计算的概念
    Linux-DHCP 交互的过程
    linux-怎么踢出系统当前已连接的用户
    linux-Centos 搭建http yum源
    linux-硬链接与软连接
    linux-centos网络配置bond
    linux-dd 一个测试文件
  • 原文地址:https://www.cnblogs.com/chnmig/p/12603895.html
Copyright © 2011-2022 走看看