Перейти к содержанию
🌐 Перевод выполнен с помощью ИИ и людей

Этот перевод был сделан ИИ под руководством людей. 🤝

В нем могут быть ошибки из-за неправильного понимания оригинального смысла или неестественности и т. д. 🤖

Вы можете улучшить этот перевод, помогая нам лучше направлять ИИ LLM.

Английская версия

Шаблоны

Вы можете использовать любой шаблонизатор вместе с FastAPI.

Часто выбирают Jinja2 — тот же, что используется во Flask и других инструментах.

Есть утилиты для простой настройки, которые вы можете использовать прямо в своем приложении FastAPI (предоставляются Starlette).

Установка зависимостей

Добавьте jinja2 в ваш проект:

$ uv add jinja2

---> 100%

Использование Jinja2Templates

  • Импортируйте Jinja2Templates.
  • Создайте объект templates, который сможете переиспользовать позже.
  • Объявите параметр Request в операции пути, которая будет возвращать шаблон.
  • Используйте созданный templates, чтобы отрендерить и вернуть TemplateResponse; передайте имя шаблона, объект HTTP-запроса и словарь «context» с парами ключ-значение для использования внутри шаблона Jinja2.
from fastapi import FastAPI, Request
from fastapi.responses import HTMLResponse
from fastapi.staticfiles import StaticFiles
from fastapi.templating import Jinja2Templates

app = FastAPI()

app.mount("/static", StaticFiles(directory="static"), name="static")


templates = Jinja2Templates(directory="templates")


@app.get("/items/{id}", response_class=HTMLResponse)
async def read_item(request: Request, id: str):
    return templates.TemplateResponse(
        request=request, name="item.html", context={"id": id}
    )

Примечание

До FastAPI 0.108.0, Starlette 0.29.0, name был первым параметром.

Также раньше, в предыдущих версиях, объект request передавался как часть пар ключ-значение в контексте для Jinja2.

Совет

Если указать response_class=HTMLResponse, интерфейс документации сможет определить, что HTTP-ответ будет в формате HTML.

Технические детали

Можно также использовать from starlette.templating import Jinja2Templates.

FastAPI предоставляет тот же starlette.templating как fastapi.templating просто для удобства разработчика. Но большинство доступных HTTP-ответов приходят напрямую из Starlette. Так же и с Request и StaticFiles.

Написание шаблонов

Затем вы можете создать шаблон в templates/item.html, например:

<html>
<head>
    <title>Item Details</title>
    <link href="{{ url_for('static', path='/styles.css') }}" rel="stylesheet">
</head>
<body>
    <h1><a href="{{ url_for('read_item', id=id) }}">Item ID: {{ id }}</a></h1>
</body>
</html>

Значения контекста шаблона

В HTML, который содержит:

Item ID: {{ id }}

...будет отображён id, взятый из переданного вами «context» dict:

{"id": id}

Например, для ID 42 это отрендерится как:

Item ID: 42

Аргументы url_for в шаблоне

Вы также можете использовать url_for() внутри шаблона — он принимает те же аргументы, что использовались бы вашей функцией-обработчиком пути.

Таким образом, фрагмент:

<a href="{{ url_for('read_item', id=id) }}">

...сгенерирует ссылку на тот же URL, который обрабатывается функцией-обработчиком пути read_item(id=id).

url_for() возвращает абсолютный URL, включая схему и хост, на основе текущего HTTP-запроса.

Например, если ваше приложение доступно по адресу https://example.com, для ID 42 это отрендерится как:

<a href="https://example.com/items/42">

Пути URL в шаблонах

Для ссылок на тот же сайт можно использовать атрибут .path, чтобы получить только путь URL, например, в templates/item_path.html:

<html>
<head>
    <title>Item Details</title>
    <link href="{{ url_for('static', path='/styles.css').path }}" rel="stylesheet">
</head>
<body>
    <h1><a href="{{ url_for('read_item', id=id).path }}">Item ID: {{ id }}</a></h1>
</body>
</html>

Передайте имя шаблона в TemplateResponse:

# Code above omitted 👆

@app.get("/items/{id}", response_class=HTMLResponse)
async def read_item(request: Request, id: str):
    return templates.TemplateResponse(
        request=request, name="item_path.html", context={"id": id}
    )
👀 Full file preview
from fastapi import FastAPI, Request
from fastapi.responses import HTMLResponse
from fastapi.staticfiles import StaticFiles
from fastapi.templating import Jinja2Templates

app = FastAPI()

app.mount("/static", StaticFiles(directory="static"), name="static")


templates = Jinja2Templates(directory="templates")


@app.get("/items/{id}", response_class=HTMLResponse)
async def read_item(request: Request, id: str):
    return templates.TemplateResponse(
        request=request, name="item_path.html", context={"id": id}
    )

В том же примере ссылка на элемент отрендерится как:

<a href="/items/42">

Начальный / делает этот путь относительным к корню текущего сайта.

Атрибут .path не включает схему, хост, параметры запроса и фрагмент. Для ссылок на другой хост используйте полный URL.

Совет

Если ваше приложение находится за прокси-сервером, настройте HTTP-заголовки переадресации и root_path, как описано в разделе За прокси-сервером.

Шаблоны и статические файлы

Вы также можете использовать url_for() внутри шаблона, например, с StaticFiles, которые вы монтировали с name="static".

<html>
<head>
    <title>Item Details</title>
    <link href="{{ url_for('static', path='/styles.css') }}" rel="stylesheet">
</head>
<body>
    <h1><a href="{{ url_for('read_item', id=id) }}">Item ID: {{ id }}</a></h1>
</body>
</html>

В этом примере будет создана ссылка на CSS-файл static/styles.css с помощью:

h1 {
    color: green;
}

И, так как вы используете StaticFiles, этот CSS-файл будет автоматически «отдаваться» вашим приложением FastAPI по URL /static/styles.css.

Подробнее

Больше подробностей, включая то, как тестировать шаблоны, смотрите в документации Starlette по шаблонам.