Перейти до змісту

FastAPI

FastAPI

Готовий до продакшину, високопродуктивний, простий у вивченні та швидкий для написання коду фреймворк

Test Coverage Package version Supported Python versions


Документація: https://fastapi.tiangolo.com

Програмний код: https://github.com/fastapi/fastapi


FastAPI - це сучасний, швидкий (високопродуктивний), вебфреймворк для створення API за допомогою Python,в основі якого лежить стандартна анотація типів Python.

Ключові особливості:

  • Швидкий: Дуже висока продуктивність, на рівні з NodeJS та Go (завдяки Starlette та Pydantic). Один із найшвидших фреймворків.

  • Швидке написання коду: Пришвидшує розробку функціоналу приблизно на 200%-300%. *

  • Менше помилок: Зменшить кількість помилок спричинених людиною (розробником) на 40%. *
  • Інтуїтивний: Чудова підтримка редакторами коду. Доповнення всюди. Зменште час на налагодження.
  • Простий: Спроектований, для легкого використання та навчання. Знадобиться менше часу на читання документації.
  • Короткий: Зведе до мінімуму дублювання коду. Кожен оголошений параметр може виконувати кілька функцій.
  • Надійний: Ви матимете стабільний код готовий до продакшину з автоматичною інтерактивною документацією.
  • Стандартизований: Оснований та повністю сумісний з відкритими стандартами для API: OpenAPI (попередньо відомий як Swagger) та JSON Schema.

* оцінка на основі тестів внутрішньої команди розробників, створення продуктових застосунків.

Спонсори

Other sponsors

Враження

"[...] I'm using FastAPI a ton these days. [...] I'm actually planning to use it for all of my team's ML services at Microsoft. Some of them are getting integrated into the core Windows product and some Office products."

Kabir Khan - Microsoft (ref)

"We adopted the FastAPI library to spawn a REST server that can be queried to obtain predictions. [for Ludwig]"

Piero Molino, Yaroslav Dudin, and Sai Sumanth Miryala - Uber (ref)

"Netflix is pleased to announce the open-source release of our crisis management orchestration framework: Dispatch! [built with FastAPI]"

Kevin Glisson, Marc Vilanova, Forest Monsen - Netflix (ref)

"I’m over the moon excited about FastAPI. It’s so fun!"

Brian Okken - Python Bytes podcast host (ref)

"Honestly, what you've built looks super solid and polished. In many ways, it's what I wanted Hug to be - it's really inspiring to see someone build that."

Timothy Crosley - Hug creator (ref)

"If you're looking to learn one modern framework for building REST APIs, check out FastAPI [...] It's fast, easy to use and easy to learn [...]"

"We've switched over to FastAPI for our APIs [...] I think you'll like it [...]"

Ines Montani - Matthew Honnibal - Explosion AI founders - spaCy creators (ref) - (ref)

Typer, FastAPI CLI

Створюючи CLI застосунок для використання в терміналі, замість веб-API зверніть увагу на Typer.

Typer є молодшим братом FastAPI. І це FastAPI для CLI. ⌨️ 🚀

Вимоги

FastAPI стоїть на плечах гігантів:

Вставновлення

$ pip install fastapi

---> 100%

Вам також знадобиться сервер ASGI для продакшину, наприклад Uvicorn або Hypercorn.

$ pip install uvicorn[standard]

---> 100%

Приклад

Створіть

  • Створіть файл main.py з:
from typing import Union

from fastapi import FastAPI

app = FastAPI()


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


@app.get("/items/{item_id}")
def read_item(item_id: int, q: Union[str, None] = None):
    return {"item_id": item_id, "q": q}
Або використайте async def...

Якщо ваш код використовує async / await, скористайтеся async def:

from typing import Union

from fastapi import FastAPI

app = FastAPI()


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


@app.get("/items/{item_id}")
async def read_item(item_id: int, q: Union[str, None] = None):
    return {"item_id": item_id, "q": q}

Примітка:

Стикнувшись з проблемами, не зайвим буде ознайомитися з розділом "In a hurry?" про async та await у документації.

Запустіть

Запустіть server з:

$ uvicorn main:app --reload

INFO:     Uvicorn running on http://127.0.0.1:8000 (Press CTRL+C to quit)
INFO:     Started reloader process [28720]
INFO:     Started server process [28722]
INFO:     Waiting for application startup.
INFO:     Application startup complete.
Про команди uvicorn main:app --reload...

Команда uvicorn main:app посилається на:

  • main: файл main.py ("Модуль" Python).
  • app: об’єкт створений усередині main.py рядком app = FastAPI().
  • --reload: перезапускає сервер після зміни коду. Використовуйте виключно для розробки.

Перевірте

Відкрийте браузер та введіть адресу http://127.0.0.1:8000/items/5?q=somequery.

Ви побачите у відповідь подібний JSON:

{"item_id": 5, "q": "somequery"}

Ви вже створили API, який:

  • Отримує HTTP запити за шляхами / та /items/{item_id}.
  • Обидва шляхи приймають GET операції (також відомі як HTTP методи).
  • Шлях /items/{item_id} містить параметр шляху item_id який має бути типу int.
  • Шлях /items/{item_id} містить необовʼязковий str параметр запиту q.

Інтерактивні документації API

Перейдемо сюди http://127.0.0.1:8000/docs.

Ви побачите автоматичну інтерактивну API документацію (створену завдяки Swagger UI):

Swagger UI

Альтернативні документації API

Тепер перейдемо сюди http://127.0.0.1:8000/redoc.

Ви побачите альтернативну автоматичну документацію (створену завдяки ReDoc):

ReDoc

Приклад оновлення

Тепер модифікуйте файл main.py, щоб отримати вміст запиту PUT.

Оголошуйте вміст запиту за допомогою стандартних типів Python завдяки Pydantic.

from typing import Union

from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI()


class Item(BaseModel):
    name: str
    price: float
    is_offer: Union[bool, None] = None


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


@app.get("/items/{item_id}")
def read_item(item_id: int, q: Union[str, None] = None):
    return {"item_id": item_id, "q": q}


@app.put("/items/{item_id}")
def update_item(item_id: int, item: Item):
    return {"item_name": item.name, "item_id": item_id}

Сервер повинен автоматично перезавантажуватися (тому що Ви додали --reload до uvicorn команди вище).

Оновлення інтерактивної API документації

Тепер перейдемо сюди http://127.0.0.1:8000/docs.

  • Інтерактивна документація API буде автоматично оновлена, включаючи новий вміст:

Swagger UI

  • Натисніть кнопку "Try it out", це дозволить вам заповнити параметри та безпосередньо взаємодіяти з API:

Swagger UI interaction

  • Потім натисніть кнопку "Execute", інтерфейс користувача зв'яжеться з вашим API, надішле параметри, у відповідь отримає результати та покаже їх на екрані:

Swagger UI interaction

Оновлення альтернативної API документації

Зараз перейдемо http://127.0.0.1:8000/redoc.

  • Альтернативна документація також показуватиме новий параметр і вміст запиту:

ReDoc

Підсумки

Таким чином, Ви один раз оголошуєте типи параметрів, тіла тощо, як параметри функції.

Ви робите це за допомогою стандартних сучасних типів Python.

Вам не потрібно вивчати новий синтаксис, методи чи класи конкретної бібліотеки тощо.

Використовуючи стандартний Python.

Наприклад, для int:

item_id: int

або для більш складної моделі Item:

item: Item

...і з цим єдиним оголошенням Ви отримуєте:

  • Підтримку редактора, включаючи:
    • Варіанти заповнення.
    • Перевірку типів.
  • Перевірку даних:
    • Автоматичні та зрозумілі помилки, у разі некоректних даних.
    • Перевірка навіть для JSON з високим рівнем вкладеності.
  • Перетворення вхідних даних: з мережі до даних і типів Python. Читання з:
    • JSON.
    • Параметрів шляху.
    • Параметрів запиту.
    • Cookies.
    • Headers.
    • Forms.
    • Файлів.
  • Перетворення вихідних даних: з типів і даних Python до мережевих даних (як JSON):
    • Конвертація Python типів (str, int, float, bool, list, тощо).
    • datetime об'єкти.
    • UUID об'єкти.
    • Моделі бази даних.
    • ...та багато іншого.
  • Автоматичну інтерактивну документацію API, включаючи 2 альтернативні інтерфейси користувача:
    • Swagger UI.
    • ReDoc.

Повертаючись до попереднього прикладу коду, FastAPI:

  • Підтвердить наявність item_id у шляху для запитів GET та PUT.
  • Підтвердить, що item_id має тип int для запитів GET and PUT.
    • Якщо це не так, клієнт побачить корисну, зрозумілу помилку.
  • Перевірить, чи є необов'язковий параметр запиту з назвою q (а саме http://127.0.0.1:8000/items/foo?q=somequery) для запитів GET.
    • Оскільки параметр q оголошено як = None, він необов'язковий.
    • За відсутності None він був би обов'язковим (як і вміст у випадку з PUT).
  • Для запитів PUT із /items/{item_id}, читає вміст як JSON:
    • Перевірить, чи має обов'язковий атрибут name тип str.
    • Перевірить, чи має обов'язковий атрибут price тип float.
    • Перевірить, чи існує необов'язковий атрибут is_offer та чи має він тип bool.
    • Усе це також працюватиме для глибоко вкладених об'єктів JSON.
  • Автоматично конвертує із та в JSON.
  • Документує все за допомогою OpenAPI, який може бути використано в:
    • Інтерактивних системах документації.
    • Системах автоматичної генерації клієнтського коду для багатьох мов.
  • Надає безпосередньо 2 вебінтерфейси інтерактивної документації.

Ми лише трішки доторкнулися до коду, але Ви вже маєте уявлення про те, як все працює.

Спробуйте змінити рядок:

    return {"item_name": item.name, "item_id": item_id}

...із:

        ... "item_name": item.name ...

...на:

        ... "item_price": item.price ...

...і побачите, як ваш редактор автоматично заповнюватиме атрибути та знатиме їхні типи:

editor support

Для більш повного ознайомлення з додатковими функціями, перегляньте Туторіал - Посібник Користувача.

Spoiler alert: туторіал - посібник користувача містить:

  • Оголошення параметрів з інших місць як: headers, cookies, form fields та files.
  • Як встановити перевірку обмежень як maximum_length або regex.
  • Дуже потужна і проста у використанні система Ін'єкція Залежностей.
  • Безпека та автентифікація, включаючи підтримку OAuth2 з JWT tokens та HTTP Basic автентифікацію.
  • Досконаліші (але однаково прості) техніки для оголошення глибоко вкладених моделей JSON (завдяки Pydantic).
  • Багато додаткових функцій (завдяки Starlette) як-от:
    • WebSockets
    • надзвичайно прості тести на основі HTTPX та pytest
    • CORS
    • Cookie Sessions
    • ...та більше.

Продуктивність

Незалежні тести TechEmpower показують що застосунки FastAPI, які працюють під керуванням Uvicorn є одними з найшвидших серед доступних фреймворків в Python, поступаючись лише Starlette та Uvicorn (які внутрішньо використовуються в FastAPI). (*)

Щоб дізнатися більше про це, перегляньте розділ Benchmarks.

Необов'язкові залежності

Pydantic використовує:

  • email-validator - для валідації електронної пошти.
  • pydantic-settings - для управління налаштуваннями.
  • pydantic-extra-types - для додаткових типів, що можуть бути використані з Pydantic.

Starlette використовує:

  • httpx - Необхідно, якщо Ви хочете використовувати TestClient.
  • jinja2 - Необхідно, якщо Ви хочете використовувати шаблони як конфігурацію за замовчуванням.
  • python-multipart - Необхідно, якщо Ви хочете підтримувати "розбір" форми за допомогою request.form().
  • itsdangerous - Необхідно для підтримки SessionMiddleware.
  • pyyaml - Необхідно для підтримки Starlette SchemaGenerator (ймовірно, вам це не потрібно з FastAPI).

FastAPI / Starlette використовують:

  • uvicorn - для сервера, який завантажує та обслуговує вашу програму.
  • orjson - Необхідно, якщо Ви хочете використовувати ORJSONResponse.
  • ujson - Необхідно, якщо Ви хочете використовувати UJSONResponse.

Ви можете встановити все це за допомогою pip install fastapi[all].

Ліцензія

Цей проєкт ліцензовано згідно з умовами ліцензії MIT.