|
| 1 | +from fastapi_django.conf.global_settings import MANAGEMENT |
| 2 | + |
1 | 3 | # Команды |
2 | 4 |
|
3 | 5 | Работа с командами реализована в модуле [management](../fastapi_django/management). Работают команды на [Typer](https://typer.tiangolo.com) |
4 | 6 |
|
5 | | -В модуле [management/commands](../fastapi_django/management/commands) реализованы дефолтные команды runserver и echo. |
| 7 | +## CLI |
| 8 | + |
| 9 | +Экземпляр Typer и команды созданы в модуле [management/cli.py](../fastapi_django/management/cli.py). Из-за особенностей работы с Typer необходимо, чтобы |
| 10 | +интерпретатор Python при импорте экземпляра Typer проходил также команды, обернутые декоратором `command()`. |
| 11 | + |
| 12 | +## Дефолтные команды |
| 13 | + |
| 14 | +Реализованы дефолтные команды `echo` и `runserver` (см. [management/cli.py](../fastapi_django/management/cli.py)). |
| 15 | + |
| 16 | +## Директория management/commands |
6 | 17 |
|
7 | | -По сути manage.py является прокси к приложению на Typer. |
| 18 | +Дефолтные команды `echo` и `runserver` простые и вполне помещаются в функцию. Однако, если логика громоздкая, то возникает |
| 19 | +потребность поместить ее в класс. В таком случае, предлагается размещать в каждый свой файл как это например показано |
| 20 | +по ссылке https://github.com/albertalexandrov/fastapi-django-example/blob/main/src/management/commands/calculator.py. |
| 21 | +Осталось эту логику запустить. Для этого в https://github.com/albertalexandrov/fastapi-django-example/blob/main/src/management/cli.py создается команда, |
| 22 | +которая запускает ее. |
8 | 23 |
|
9 | 24 | ## Кастомные команды |
10 | 25 |
|
11 | | -Команда - это callable объект, который может находится в любом месте проекта. Но чтобы команда разаработала, ее необходимо |
12 | | -зарегистрировать. Предлагается регистрировать ее в том же модуле, в котором вызывается приложение Typer, то есть в модуле manage.py |
13 | | -при помоши функции management.utils.register_command. |
| 26 | +Объект `typer` [management/cli.py](../fastapi_django/management/cli.py) является **корневым** CLI, в которому должны |
| 27 | +добавляться кастомные команды. |
14 | 28 |
|
15 | | -Пример кастомной команды https://github.com/albertalexandrov/fastapi-django-example/tree/main/src/commands. |
16 | | -Пример регистрации команды: https://github.com/albertalexandrov/fastapi-django-example/blob/main/src/manage.py#L10 |
| 29 | +Вне зависимости от того, идет ли речь про код приложения FastAPI или некоторой библиотеки предлагается следующий алгоритм |
| 30 | +создания кастомных команд. |
17 | 31 |
|
18 | | -## Команда runserver |
| 32 | +1. В проекте/библиотеке создается структура папок и файлов: |
19 | 33 |
|
20 | | -Данная команда запускает приложение FastAPI при помощи Uvicorn. Если взглянуть на ее реализацию, можно увидеть, |
21 | | -как она понимает, с какими параметрами необходимо запустить приложение: |
| 34 | +```python |
| 35 | +management |
| 36 | +├── commands (опционально) |
| 37 | + ├── __init__.py |
| 38 | +├── cli.py |
| 39 | +``` |
| 40 | + |
| 41 | +2. в `cli.py` определяется, настраивается объект `Typer`, реализуются кастомные команды: |
22 | 42 |
|
23 | 43 | ```python |
24 | | -def runserver() -> None: |
25 | | - params = {} |
26 | | - uvicorn_settings = [setting for setting in dir(settings) if setting.startswith("UVICORN_")] |
27 | | - for setting in uvicorn_settings: |
28 | | - _, param = setting.split("_", 1) |
29 | | - params[param.lower()] = getattr(settings, setting) |
30 | | - uvicorn.run(**params) |
| 44 | +# cli.py |
| 45 | + |
| 46 | +from typer import Typer |
| 47 | + |
| 48 | +typer = Typer(help="Команды проекта/библиотеки") |
| 49 | + |
| 50 | + |
| 51 | +@typer.command() |
| 52 | +def info(): |
| 53 | + print("Вот информация о проекте/библиотеке") |
| 54 | + |
31 | 55 | ``` |
32 | 56 |
|
33 | | -Параметры запуска Uvicorn задаются в settings. Названия параметров должны иметь префикс UVICORN_ |
34 | | -Далее идут названия параметров функции uvicorn.run в верхнем регистре. Таким образом, параметр, |
35 | | -соответствующий параметру workers будет иметь название UVICORN_WORKERS, для port - UVICORN_PORT и тд |
| 57 | +3. Подключение к корневому CLI |
36 | 58 |
|
37 | | -## Список команд |
| 59 | +Осталось подключить созданный объект typer, который содержит кастомные команды, к корневому CLI. |
| 60 | +Для этого необходимо в настройку MANAGEMENT прописать: |
38 | 61 |
|
39 | | -Здесь https://github.com/albertalexandrov/fastapi-django-example/blob/main/src/manage.py#L10 была зарегистрирована |
40 | | -кастомная команда. Убедится, команда была зарегистрирована можно введя в консоль список всех команд командой: |
| 62 | +```python |
| 63 | +# settings.py |
41 | 64 |
|
42 | | -```shell |
43 | | -python manage.py --help |
| 65 | +MANAGEMENT = [ |
| 66 | + { |
| 67 | + "typer": "management.cli:typer", |
| 68 | + } |
| 69 | +] |
44 | 70 | ``` |
45 | 71 |
|
46 | | - |
| 72 | +4. Проверка |
47 | 73 |
|
48 | | -## Примечание |
| 74 | +Чтобы просмотреть список команд, необходимо выполнить команду `python manage.py --help`: |
49 | 75 |
|
50 | | -Я рассчитывал, что объект [cli](../fastapi_django/management/__init__.py) будет импортироваться где нужно и |
51 | | -команды будут автоматически регистрироваться. Однако, недостаточно обернуть функцию в декоратор cli.command, |
52 | | -поэтому приходится делать так, что команда регистрируется аккурат перед тем, когда выполняется |
53 | | -cli() ([в файле manage.py](https://github.com/albertalexandrov/fastapi-django-example/blob/main/src/manage.py#L10)) |
| 76 | + |
54 | 77 |
|
55 | | -Поэтому сторонние библиотеки (не проект) не смогут просто оборачивать свои собственные команды - в проекте придется |
56 | | -импортировать команды сторонних библиотек и регистрировать. |
| 78 | +Можно видеть, что отобразились как дефолтные команды, так и кастомная команд. |
| 79 | + |
| 80 | +Если в настройке MANAGEMENT определить name, то команды будут объединены в субкоманды, доступ к которым будет через |
| 81 | +name: |
| 82 | + |
| 83 | +```python |
| 84 | +# settings.py |
| 85 | + |
| 86 | +MANAGEMENT = [ |
| 87 | + { |
| 88 | + "typer": "management.cli:typer", |
| 89 | + "name": "custom-commands", |
| 90 | + } |
| 91 | +] |
| 92 | +``` |
57 | 93 |
|
58 | | -**Возможно у кого нибудь возникнут идеи как реализовать автоматическую регистрацию команд. Автодисковеринг как в Celery |
59 | | -или типа того. Пишите.** |
| 94 | + |
0 commit comments