fastapi/docs/ru/docs/tutorial/security/get-current-user.md

6.9 KiB
Raw Blame History

Получить текущего пользователя

В предыдущей главе система безопасности (основанная на системе внедрения зависимостей) передавала функции-обработчику пути token типа str:

{* ../../docs_src/security/tutorial001_an_py39.py hl[12] *}

Но это всё ещё не слишком полезно.

Сделаем так, чтобы она возвращала текущего пользователя.

Создать модель пользователя

Сначала создадим Pydantic-модель пользователя.

Точно так же, как мы используем Pydantic для объявления тел запросов, мы можем использовать его где угодно:

{* ../../docs_src/security/tutorial002_an_py310.py hl[5,12:6] *}

Создать зависимость get_current_user

Давайте создадим зависимость get_current_user.

Помните, что у зависимостей могут быть подзависимости?

get_current_user будет иметь зависимость от того же oauth2_scheme, который мы создали ранее.

Аналогично тому, как мы делали ранее прямо в операции пути, новая зависимость get_current_user получит token типа str от подзависимости oauth2_scheme:

{* ../../docs_src/security/tutorial002_an_py310.py hl[25] *}

Получить пользователя

get_current_user будет использовать созданную нами (ненастоящую) служебную функцию, которая принимает токен типа str и возвращает нашу Pydantic-модель User:

{* ../../docs_src/security/tutorial002_an_py310.py hl[19:22,26:27] *}

Внедрить текущего пользователя

Теперь мы можем использовать тот же Depends с нашей get_current_user в операции пути:

{* ../../docs_src/security/tutorial002_an_py310.py hl[31] *}

Обратите внимание, что мы объявляем тип current_user как Pydantic-модель User.

Это поможет внутри функции с автозавершением и проверками типов.

/// tip | Подсказка

Возможно, вы помните, что тела запросов также объявляются с помощью Pydantic-моделей.

Здесь FastAPI не запутается, потому что вы используете Depends.

///

/// check | Заметка

То, как устроена эта система зависимостей, позволяет иметь разные зависимости, которые возвращают модель User.

Мы не ограничены наличием только одной зависимости, которая может возвращать такой тип данных.

///

Другие модели

Теперь вы можете получать текущего пользователя напрямую в функциях-обработчиках пути и работать с механизмами безопасности на уровне внедрения зависимостей, используя Depends.

И вы можете использовать любую модель или данные для требований безопасности (в данном случае Pydantic-модель User).

Но вы не ограничены использованием какой-то конкретной модели данных, класса или типа.

Хотите, чтобы в модели были id и email, но не было username? Пожалуйста. Можно использовать те же инструменты.

Хотите просто str? Или просто dict? Или напрямую экземпляр класса модели базы данных? Всё работает одинаково.

У вас вообще нет пользователей, которые входят в приложение, а есть роботы, боты или другие системы, у которых есть только токен доступа? Снова — всё работает так же.

Просто используйте любую модель, любой класс, любую базу данных, которые нужны вашему приложению. Система внедрения зависимостей FastAPI поможет вам в этом.

Размер кода

Этот пример может показаться многословным. Имейте в виду, что в одном файле мы смешиваем безопасность, модели данных, служебные функции и операции пути.

Но вот ключевой момент.

Всё, что касается безопасности и внедрения зависимостей, пишется один раз.

И вы можете сделать это настолько сложным, насколько захотите. И всё равно это будет написано только один раз, в одном месте. Со всей гибкостью.

При этом у вас могут быть тысячи эндпоинтов (операций пути), использующих одну и ту же систему безопасности.

И все они (или любая их часть по вашему желанию) могут воспользоваться преимуществами повторного использования этих зависимостей или любых других зависимостей, которые вы создадите.

И все эти тысячи операций пути могут состоять всего из 3 строк:

{* ../../docs_src/security/tutorial002_an_py310.py hl[30:32] *}

Резюме

Теперь вы можете получать текущего пользователя прямо в своей функции-обработчике пути.

Мы уже на полпути.

Нужно лишь добавить операцию пути, чтобы пользователь/клиент мог отправить username и password.

Это будет дальше.