[enhancement] Выделить боевое ядро и адаптеры: убрать UI/рендер из зависимостей симуляции #87

Open
opened 2026-10-30 10:29:47 +00:00 by chexit · 2 comments
Owner

🤖 Filed by Codex, AI-агент Владимира (chexit).

Архитектурный проход по 76f680eba64b64eb28435e71ce9f22a84b0e5da1.

Диагноз по текущему коду

Разделение уже начато и headless runner полезен; переписывать всё на ECS не требуется. Но sim/mod.rs (~2.7k строк) одновременно содержит сущности/спецификации, боевой цикл, модели, частицы, звуки и FX. Out смешивает scene primitives, сообщения и строковые команды миру. sim/why.rs обращается к crate::panel::distance из слоя HUD, а тест планировщика использует crate::wave::WaveConfig из меню. Единственный crate зависит от локального Horizon SDK, поэтому даже native тестам ядра требуется подготовленный форк.

lib.rs (~1.9k строк) объединяет команды, UI, persistence, world lifecycle, звуки, отправку рендера, replay и export. Размер сам по себе не баг; проблема — направления зависимостей и необходимость менять несколько трактов одной механики.

Целевые границы, небольшими шагами

  1. Доменные Order, RaidConfig, причины отказа и единицы времени вынести из меню/форматирования. Ядро выдаёт структурированные факты, UI превращает их в русский текст.
  2. Разделить обновление боя и построение сцены. CombatState + WorldAnswers + Orders → State + DomainEvents + WorldRequests; presentation читает состояние/события без изменения боя.
  3. Оставить Horizon/WIT, storage, модели, GUI и команды в адаптерах. AirDef сделать координатором, выделяя по ответственности, а не по тысяче строк.
  4. Отдельный airdef-core crate либо эквивалентный реально независимый package — если это упрощает сборку, без дробления на десятки crate. glam допустим, SDK/host imports ядру не нужны.

Приёмка и ограничения

Из чистого checkout можно запустить тесты/runner ядра без сборки Horizon. В domain-модулях нет импортов panel/wave/SDK. Первые extraction-коммиты сохраняют поведение и проходят существующие сценарии; механики не менять одновременно с переносом. Существующие headless тесты сохранить. Общая сцена/события и lifecycle сессии — отдельные задачи, а не обязательная одномоментная миграция.

Общий порядок и зависимости: архитектурная дорожная карта.

🤖 Filed by Codex, AI-агент Владимира (chexit). Архитектурный проход по `76f680eba64b64eb28435e71ce9f22a84b0e5da1`. ### Диагноз по текущему коду Разделение уже начато и headless runner полезен; переписывать всё на ECS не требуется. Но `sim/mod.rs` (~2.7k строк) одновременно содержит сущности/спецификации, боевой цикл, модели, частицы, звуки и FX. `Out` смешивает scene primitives, сообщения и строковые команды миру. `sim/why.rs` обращается к `crate::panel::distance` из слоя HUD, а тест планировщика использует `crate::wave::WaveConfig` из меню. Единственный crate зависит от локального Horizon SDK, поэтому даже native тестам ядра требуется подготовленный форк. `lib.rs` (~1.9k строк) объединяет команды, UI, persistence, world lifecycle, звуки, отправку рендера, replay и export. Размер сам по себе не баг; проблема — направления зависимостей и необходимость менять несколько трактов одной механики. ### Целевые границы, небольшими шагами 1. Доменные `Order`, `RaidConfig`, причины отказа и единицы времени вынести из меню/форматирования. Ядро выдаёт структурированные факты, UI превращает их в русский текст. 2. Разделить обновление боя и построение сцены. `CombatState + WorldAnswers + Orders → State + DomainEvents + WorldRequests`; presentation читает состояние/события без изменения боя. 3. Оставить Horizon/WIT, storage, модели, GUI и команды в адаптерах. `AirDef` сделать координатором, выделяя по ответственности, а не по тысяче строк. 4. Отдельный `airdef-core` crate либо эквивалентный реально независимый package — если это упрощает сборку, без дробления на десятки crate. `glam` допустим, SDK/host imports ядру не нужны. ### Приёмка и ограничения Из чистого checkout можно запустить тесты/runner ядра без сборки Horizon. В domain-модулях нет импортов panel/wave/SDK. Первые extraction-коммиты сохраняют поведение и проходят существующие сценарии; механики не менять одновременно с переносом. Существующие headless тесты сохранить. Общая сцена/события и lifecycle сессии — отдельные задачи, а не обязательная одномоментная миграция. Общий порядок и зависимости: [архитектурная дорожная карта](https://gitea.maoniao.team/chexit/airdef/issues/103).
Author
Owner

🤖 Agent: Codex — работа Владимира (chexit).

Первый архитектурный этап: production adapter использует канонический airdef-core, зависимость ядра — только glam. Тот же sim source собирается без Horizon SDK; доменные параметры raid и audio declarations больше не зависят от adapter. Детерминированный trace 600 ticks при извлечении сохранён (FNV 4af71fb5aeb02568).

Текущая проверка: 151 core unit, 4 scenario, 39 adapter unit и core-boundary прошли. Остаток: ядро ещё создаёт декларации визуальных/звуковых эффектов и часть текста; полный перенос presentation в адаптеры не объявляется законченным.

Issue оставлен открытым согласно просьбе автора.

🤖 Agent: Codex — работа Владимира (chexit). [Первый архитектурный этап](https://gitea.maoniao.team/chexit/airdef/commit/5f07027): production adapter использует канонический `airdef-core`, зависимость ядра — только glam. Тот же sim source собирается без Horizon SDK; доменные параметры raid и audio declarations больше не зависят от adapter. Детерминированный trace 600 ticks при извлечении сохранён (FNV `4af71fb5aeb02568`). Текущая проверка: 151 core unit, 4 scenario, 39 adapter unit и core-boundary прошли. Остаток: ядро ещё создаёт декларации визуальных/звуковых эффектов и часть текста; полный перенос presentation в адаптеры не объявляется законченным. Issue оставлен открытым согласно просьбе автора.
Author
Owner

🤖 Agent: Codex, with GPT-6.1 Terra.

Published 375fdf2/cb73cb7/0c870c1. BatteryStatus is now a typed snapshot; battery/map text, world-cache reporting, and damage/component diagnostic reasons are formatted by battery_view/world_view/why_view adapters. The command and monitor use the same presentation adapter; existing text/order preserved. Combined core release: 193 tests + 8 scenarios passed, 7 ignored; adapter: 64 + 1 boundary + 5 scenarios passed. Most legacy CheckReason::Text, Out messages, other status/doctrine and visual declarations still need gradual extraction. Current handoff. Issue state unchanged.

🤖 Agent: Codex, with GPT-6.1 Terra. Published 375fdf2/cb73cb7/0c870c1. BatteryStatus is now a typed snapshot; battery/map text, world-cache reporting, and damage/component diagnostic reasons are formatted by battery_view/world_view/why_view adapters. The command and monitor use the same presentation adapter; existing text/order preserved. Combined core release: 193 tests + 8 scenarios passed, 7 ignored; adapter: 64 + 1 boundary + 5 scenarios passed. Most legacy CheckReason::Text, Out messages, other status/doctrine and visual declarations still need gradual extraction. [Current handoff](https://gitea.maoniao.team/chexit/airdef/src/branch/kimi-work/docs/CONTINUATION-2026-11-04.md). Issue state unchanged.
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: chexit/airdef#87