# Правила для агента ## Главный источник задачи Перед началом любой работы по проекту агент обязан прочитать файл: ```text Agent/TASK.md ``` Именно этот файл считается основным описанием задачи, требований и ограничений. ## Папка с задачами Детальный план работ хранится в папке: ```text Agent/Task/ ``` Задачи должны называться строго по формату: ```text TASK-0001.md TASK-0002.md TASK-0003.md ``` Новые задачи создаются только со следующим свободным номером. Нельзя пропускать номера без причины и нельзя переиспользовать номер удаленной или завершенной задачи. Правила шаблона задач описаны в файле: ```text Agent/Task/TASK_TEMPLATE.md ``` Каждая новая задача обязана соблюдать этот шаблон. ## Порядок работы 1. Сначала прочитать `Agent/TASK.md` полностью. 2. Прочитать `Agent/Task/TASK_TEMPLATE.md`. 3. Прочитать актуальные задачи `Agent/Task/TASK-*.md`. 4. После чтения сверять все решения с требованиями из задачи и конкретных task-файлов. 5. Не реализовывать вариант B или любую функциональность, которой нет в `Agent/TASK.md` или `Agent/Task/TASK-*.md`. 6. Не добавлять лишние архитектурные слои, если они не нужны для выполнения задачи. 7. Приоритет: минимальная корректная реализация, чистый жизненный цикл, понятный код. ## Работа со статусами задач - Перед реализацией брать только задачи со статусом `Ready`. - При начале реализации переводить задачу в статус `In Progress`. - После выполнения, проверки и фиксации результата переводить задачу в статус `Done`. - Если задача заблокирована, переводить ее в статус `Blocked` и описывать причину в разделе `Заметки`. - Не начинать следующую задачу, если текущая задача в статусе `In Progress` не завершена и не заблокирована. - Если для выполнения текущей задачи появилась новая работа, создать новую задачу по шаблону, а не смешивать разные цели в одном файле. ## Правила заведения задач - Новые задачи создавать только в `Agent/Task/`. - Имя файла должно быть `TASK-XXXX.md`, где `XXXX` — номер из четырех цифр. - Заголовок задачи должен начинаться с того же номера, что и имя файла. - Структура задачи должна соответствовать `Agent/Task/TASK_TEMPLATE.md`. - В задаче должны быть разделы `Статус`, `Цель`, `Что сделать`, `Технические требования`, `Критерии готовности`, `Заметки`. - Статус задачи должен быть одним из значений: `Planned`, `Ready`, `In Progress`, `Done`, `Blocked`. - Задача должна быть достаточно крупной, чтобы не дробить работу на слишком много файлов. - Задача должна быть достаточно конкретной, чтобы по критериям готовности можно было проверить результат. - Нельзя заводить задачи по варианту B. ## Ограничения - Использовать VContainer для DI. - Использовать UniTask для async-операций. - Использовать UniRx для реактивных значений и подписок. - Не использовать `FindObjectOfType`. - Не использовать `Singleton.Instance`. - Не хранить состояние в `static`. - Не использовать `async void`, кроме Unity-колбэков. - Все async-операции выполнять через UniTask и `CancellationToken`. - Все подписки должны корректно освобождаться. ## Архитектурные правила - Orchestration-логика должна жить в plain C# классах. - `MonoBehaviour` использовать только как View-компоненты и Unity binding layer. - State не должен сам переключать state machine изнутри своего `EnterAsync(...)`. - Переходами между state управляет внешний flow coordinator. - Generic state machine должна отвечать только за порядок `ExitAsync` текущего state и `EnterAsync` нового state. - ViewModel должна быть обычным C#-классом. - ViewModel передавать во View явно через bind/setup-метод, а не через DI-поля MonoBehaviour. - View не должна содержать бизнес-логику boot flow и не должна напрямую управлять state machine. ## Правила DI - Scene View регистрировать через `RegisterComponent(...)`. - Settings/config assets регистрировать через `[SerializeField]` и `RegisterInstance(...)`. - Сервисы, controller-объекты и state-объекты не регистрировать через `RegisterInstance(...)`. - Сервисы регистрировать как интерфейсы через `builder.Register(Lifetime.Singleton).As()`. - Runtime-данные не прокидывать в MonoBehaviour через DI-поля. - Не создавать зависимости вручную внутри MonoBehaviour, если они должны управляться контейнером. ## Правила async и отмены - Каждый `await` должен получать `CancellationToken`, пришедший сверху, если операция поддерживает отмену. - `UniTask.Delay`, `UniTask.Yield` и похожие операции должны использовать `CancellationToken`. - `CancellationToken` не должен быть декоративным: отмена должна реально останавливать ожидания и фоновые операции. - `OperationCanceledException` при штатной остановке flow, сцены или scope не считать ошибкой. - Если операция должна завершаться по нескольким причинам, использовать `CancellationTokenSource.CreateLinkedTokenSource(...)`. - Linked `CancellationTokenSource` обязательно освобождать через `Dispose()`. - Фоновые циклы запускать в `InitializeAsync` и останавливать через `CancellationTokenSource.Cancel()` в `ReleaseAsync`. ## Правила UI и подписок - Для UniRx-подписок использовать `CompositeDisposable`. - Подписки создавать при `Initialize()` или после явного bind/setup ViewModel. - Все подписки очищать в `Release()`. - `Release()` должен быть идемпотентным и безопасным при повторном вызове. - Сначала останавливать входящие сигналы и подписки, затем очищать ссылки на ViewModel и runtime-данные. - Для `Button.onClick` использовать симметричные `AddListener(...)` и `RemoveListener(...)`. - Снимать нужно тот же listener, который был добавлен. - Не использовать `RemoveAllListeners()` как основной способ очистки. - Не использовать анонимные listeners, если их потом нельзя симметрично снять. - Не обновлять реактивный UI через `Update()`. - Повторный вход во View не должен создавать дублирующиеся подписки или callbacks. ## Цель Сделать только задачу `Boot Flow` из `Agent/TASK.md` и подготовить проект так, чтобы его можно было проверить по описанным требованиям.