О проекте
Команда: Astra the best
Кейс HackAlem.ai: Спецтрек — Astana Innovations
Стадия: Доведённый продукт
Задача кейса: «Аким на 5 часов»: городской симулятор, распределяющий бюджет по 5 направлениям и 5 районам
Суть
Симулятор городского бюджета на 3D-карте Астаны (MapLibre): редактор плана из 14 мер, серверный расчёт Score, поиск лучшего плана полным перебором, AI-анализ с проверкой фактов, сравнение сценариев и экспорт отчёта.
Как устроено
Next.js API (scenario/simulate/optimize/analyze) сам проверяет правила и пересчитывает стоимость и Score по каноническим данным: лаг (8−L)/8, синергии, критические показатели ниже 40. Цены и Score от клиента не принимаются. Оптимизатор перебирает все 694 395 допустимых сочетаний мер и районов, отдельно ищет улучшение заменой одной меры или района. Для AI-анализа сервер готовит факты рассчитанного сценария, модель объясняет сильные стороны и риски, а числа в ответе сверяются с процитированными фактами, при несовпадении ответ исправляется. 1 у.е. бюджета показана как 100 млн ₸.
Ключевые решения
- полный перебор
- локальное улучшение заменой
- валидация чисел в ответе LLM
- Zod-схемы
- 3D-карта MapLibre
- экспорт HTML/JSON
Особенности
Параллельную работу нескольких Codex-агентов координировали через файлы claims (P01–P53) и журнал handoff в репозитории. AI-отчёт отклоняется, если числа в нём не совпадают с фактами расчёта. Отдельно проверена производительность 3D-карты и раскладка меток.
Стек
TypeScript · Next.js · React · MapLibre GL · OpenFreeMap · Zod · Vitest · Playwright · Python/Shapely
Модели
OpenAI gpt-6-sol · GPT-6 Luna
Проект создан за 5 часов на финале хакатона HackAlem.ai (23 сентября 2026, Астана). Код — BAITC-Hacks/hack-5db21a28-astra-the-best.
README
README.md🏙️ Аким на 5 часов
Учебный симулятор управления Астаной: пять решений, ограниченный бюджет и измеримые последствия для города.
Распределите 10 млрд ₸, соберите городской план и оцените, как он изменит жизнь пяти районов. 3D-карта, воспроизводимый расчёт, поиск лучшего плана и объяснение от GPT-6 Sol.
📦 Репозиторий · 🚀 Запуск · 🧪 Сценарий для жюри
Интерфейс и карта
Сервер и AI
Проверки
Содержание
- Название проекта
- О проекте: проблема и аудитория
- Что реализовано
- Как работает решение
- Технологии
- Архитектура проекта
- Установка и запуск
- Как проверить решение
- Данные и интеграции
- Ограничения
- Развёрнутая версия
02 · О проекте: проблема и аудитория
Городской бюджет ограничен: строительство школы, улучшение транспорта и модернизация коммунальных сетей конкурируют за одни ресурсы. При выборе важно учитывать не только пользу отдельной меры, но и сроки, побочные эффекты и различия между районами.
«Аким на 5 часов» помогает студентам, участникам образовательных программ и жителям, интересующимся городским управлением, исследовать эти компромиссы. Пользователь выступает в роли акима: распределяет 10 млрд ₸ условного бюджета, выбирает ровно пять мероприятий и получает карту изменений, индекс качества жизни Astana Quality of Life Score и AI-объяснение результата.
Данные и эффекты синтетические. Это учебная модель, а не прогноз реальной городской политики. Горизонт расчёта — восемь условных кварталов (два года). «5 часов» — название кейса и время работы над ним на хакатоне; игрового таймера нет.
03 · Что реализовано
- Карта всей Астаны: объёмные здания, пять игровых зон, выбор района, слои десяти показателей, метки мероприятий и режим «До / После».
- Редактор городского плана: 14 мероприятий по пяти направлениям — транспорт, экология, социальная инфраструктура, безопасность и городские сервисы. Видны цена, район действия, задержка эффекта, положительные и отрицательные изменения.
- Контроль правил в интерфейсе и на сервере: пять уникальных мер, бюджет до 100 единиц, максимум две меры одного направления, проверка районов и несовместимостей. Меры можно удалять и заменять.
- Воспроизводимый расчёт и отчёт: Score до и после, все 50 районных показателей, слабейший район, критические значения и синергии — дополнительные эффекты сочетаний мер.
- AI-анализ: сильные стороны, риски, последствия и рекомендация на основе серверного расчёта. Для этой функции нужен API-ключ; ошибка AI не удаляет числовой результат.
- Поиск лучшего плана: полный перебор допустимых сочетаний мер и районов на сервере, затем AI-объяснение найденного варианта. Применение плана — отдельное действие пользователя.
- Сравнение вариантов: сохранение до шести сценариев в текущем браузере и отдельный поиск улучшения заменой одной меры или её района.
- Экспорт: автономный HTML-отчёт для просмотра и печати в PDF, а также JSON с точными числами.
- Обучение при первом входе: подсказки по реальным действиям, возможность пропустить или повторить обучение. Режимы «Город / Отчёт» сохраняют текущий сценарий при переключении.
04 · Как работает решение
- Входные данные. Приложение загружает одинаковый для всех набор: показатели пяти районов, каталог мер, бюджет и правила. Загружать собственный файл не требуется.
- Выбор. Пользователь изучает карту и собирает пять решений. Для районной меры выбирает район; общегородская действует во всех пяти зонах и оплачивается один раз.
- Расчёт. После нажатия «Рассчитать сценарий» сервер проверяет выбор, берёт цены и эффекты из канонического набора и рассчитывает результат с учётом задержек, синергий и критических показателей.
- Результат. Открывается отчёт с изменением Score и районных показателей. Можно вернуться на карту, сравнить «До / После» и отредактировать план.
- Объяснение и сравнение. По кнопке «Получить AI-анализ» модель объясняет уже рассчитанные факты. Сценарий можно сохранить, сравнить с другим или выгрузить в отчёт.
Эффект меры с задержкой L кварталов учитывается с долей (8 − L) / 8. После сложения эффектов и синергий каждый показатель ограничивается диапазоном 0–100. Чем выше показатель, тем лучше; значение строго ниже 40 считается критическим.
Score = 0,7 × средний балл районов с учётом долей населения
+ 0,3 × балл слабейшего района
− количество критических показателей
Балл района — взвешенная сумма его десяти показателей. AI не вычисляет и не меняет Score: одинаковые решения всегда дают одинаковые числа. В расчётах используются исходные 100 единиц бюджета, в интерфейсе 1 единица = 100 млн ₸. Это условные ассигнования, не реальные сметы; подробнее — шкала бюджета.
05 · Технологии
| Компонент | Технологии и назначение |
|---|---|
| Язык и среда | TypeScript 6, Node.js 22, npm 10 |
| Приложение и сервер | Next.js 16.3.6, React 19.3.0, App Router и серверные Route Handlers |
| Интерфейс | CSS Modules, адаптивная вёрстка |
| Карта | MapLibre GL JS 6.11.0, WebGL, GeoJSON, подложка OpenFreeMap |
| Проверка данных | Zod 4: схемы запросов и ответов AI |
| AI | OpenAI Chat Completions API; модель по умолчанию gpt-6-sol, reasoning_effort: none, до 2500 токенов ответа |
| Тесты | Vitest 5, Testing Library, Playwright 1.63 с Google Chrome |
| Контроль качества | TypeScript, ESLint 9 |
| Подготовка географии | Python + Shapely для границ, Node.js для геоориентиров; при обычном запуске не нужны |
Точные версии зависимостей зафиксированы в package.json и package-lock.json. База данных, регистрация и отдельный backend-сервис для локального запуска не требуются.
06 · Архитектура проекта
Одно приложение Next.js содержит браузерный интерфейс и серверный API. Карта и отчёт используют общее состояние выбранного плана.
flowchart LR
UI["Браузер: карта, редактор, отчёт"] --> API["Next.js API"]
DATA["Канонические данные и правила"] --> API
API --> DOMAIN["Валидация, расчёт и поиск"]
DOMAIN --> API
API --> UI
API --> FACTS["Факты рассчитанного сценария"]
FACTS --> AI["AI API"]
AI --> CHECK["Проверка ответа и ссылок на факты"]
CHECK --> UI
MAP["OpenFreeMap и локальный GeoJSON"] --> UI
UI <--> STORE["localStorage: сохранённые сценарии"]
| Каталог | Ответственность |
|---|---|
src/data/, src/contracts/ | Исходные данные, версия/hash набора, общие типы и контракты |
src/domain/ | Проверка правил, чистый расчёт, поиск оптимума и локальных улучшений |
src/app/api/ | HTTP-маршруты сценария, расчёта, оптимизации и анализа |
src/server/ai/ | Подготовка фактов, вызов модели, проверка структуры и чисел ответа |
src/features/, src/app/AppShell.tsx | Карта, редактор, отчёт, обучение, сравнение и экспорт; общее состояние интерфейса |
public/geo/ | Подготовленная геометрия пяти игровых зон |
tests/ | Проверки данных, формул, API, интерфейса и браузерных сценариев |
API предоставляет GET /api/scenario, POST /api/simulate, POST /api/optimize и POST /api/analyze. Сервер сам рассчитывает стоимость и результат; переданные клиентом цены или готовый Score не принимаются. Перед AI-запросом сценарий пересчитывается заново. Ключ провайдера хранится только на сервере. Подробности: контракт API, устройство поиска оптимума.
Особенность подхода — проверяемая цепочка: 694 395 допустимых сценариев → максимум канонического Score → факты расчёта для AI → объяснение и сравнение пользователем. Полный поиск выполняет алгоритм, а модель объясняет последствия; независимая проверка контрольного примера и тесты поиска позволяют воспроизвести числовой результат. Это сочетание показывает и лучший общий балл, и районные компромиссы, которые он скрывает.
07 · Установка и запуск
Нужны Git, Node.js >=22.14.0 <23, npm >=10 <11 и браузер с WebGL. Интернет нужен для установки пакетов, подложки карты и AI. Основная проверенная среда — Windows / PowerShell.
1. Получить проект и зависимости
git clone https://github.com/BAITC-Hacks/hack-5db21a28-astra-the-best.git
cd hack-5db21a28-astra-the-best
node --version
npm.cmd --version
npm.cmd ci
Если репозиторий уже открыт локально, выполняйте команды из его корня, начиная с проверки версий.
2. Подготовить окружение
При первом запуске скопируйте шаблон; существующий файл с ключом перезаписывать не нужно:
Copy-Item .env.example .env.local
| Переменная | Значение по умолчанию / назначение |
|---|---|
AI_API_KEY | Пустая; для AI укажите действующий ключ провайдера с доступом к выбранной модели |
AI_BASE_URL | https://api.openai.com/v1 — адрес API |
AI_MODEL | gpt-6-sol — модель анализа |
AI_TIMEOUT_MS | 30000 — время ожидания AI в миллисекундах |
AI_MAX_REQUESTS_PER_MINUTE | 10 — серверное ограничение частоты запросов анализа на клиента |
Файл .env.local исключён из Git. После изменения переменных перезапустите сервер. Пример альтернативной настройки NVIDIA находится в .env.example; ключ, адрес и модель должны соответствовать одному провайдеру.
Без ключа доступны редактор, расчёт, поиск лучшего плана, сравнение и экспорт. При запросе AI появится сообщение об отсутствии настройки; шаблонный текст не подставляется вместо анализа.
3. Запустить приложение
npm.cmd run dev
Откройте http://127.0.0.1:3000/. Сервер работает, пока открыта команда; остановка — Ctrl+C.
В macOS/Linux используйте npm вместо npm.cmd, а для копирования шаблона — cp .env.example .env.local.
4. Сборка для production и проверки
Для запуска production-сборки остановите dev-сервер, затем выполните:
npm.cmd run build
npm.cmd run start
Адрес останется http://127.0.0.1:3000/. Проверки кода и расчётов запускаются отдельно:
npm.cmd run typecheck
npm.cmd run lint
npm.cmd test
Для браузерных проверок установите Google Chrome и выполните:
npm.cmd run test:e2e -- --reporter=line --workers=2
Тесты явно используют channel: 'chrome': одного bundled Chromium недостаточно. Playwright поднимает dev-сервер автоматически, если порт 3000 свободен; уже работающий локальный сервер переиспользуется.
08 · Как проверить решение: сценарий для жюри
После запуска можно повторить этот пример без API-ключа.
- На первом экране нажмите «Освоюсь самостоятельно» или пройдите обучение.
- В режиме «Город» откройте «План · 0/5». Оставьте фильтр направлений на всех направлениях.
- Выберите Нуру и добавьте M7, M8, M10. Добавьте общегородскую M12 — район для неё не нужен. Затем выберите Сарыарку и добавьте M5.
| Мера в каталоге | Район | Цена в модели | Цена в интерфейсе |
|---|---|---|---|
| M7 — Школа + детсад (модульное строительство) | Нура | 24 | 2,4 млрд ₸ |
| M8 — Центр семейного здоровья / поликлиника | Нура | 20 | 2 млрд ₸ |
| M10 — Освещение и камеры (расширение Safe City) | Нура | 12 | 1,2 млрд ₸ |
| M12 — Единая цифровая платформа обращений | Весь город | 14 | 1,4 млрд ₸ |
| M5 — Перевод частного сектора на чистое топливо | Сарыарка | 25 | 2,5 млрд ₸ |
Нажмите «Рассчитать сценарий». Откроется отчёт со следующими результатами:
| Проверка | Ожидаемый результат |
|---|---|
| Расходы / остаток | 9,5 млрд ₸ / 500 млн ₸ — 95 / 5 единиц модели |
| Исходный Score | 52,55768; в интерфейсе 52,56 |
| Итоговый Score | 56,54307; в интерфейсе 56,54 |
| Изменение | +3,98539; в интерфейсе +3,99 |
| Критические показатели после расчёта | 0 |
| Синергия | M10 + M12: +2 к безопасности улиц (B1) в Нуре |
Далее проверьте дополнительные возможности:
- AI: при настроенном ключе нажмите «Получить AI-анализ». Появятся сильные стороны, риски, последствия и совет. Без ключа отобразится ошибка настройки, а расчёт останется доступен.
- Сравнение: в блоке «Сравните свои решения» назовите и сохраните текущий сценарий. Измените меру или район, пересчитайте и сравните варианты. «Найти проверяемое улучшение» ищет замену одного решения.
- Экспорт: скачайте «Скачать отчёт · HTML / PDF» или «Скачать данные · JSON». Для PDF откройте HTML и выберите печать → «Сохранить как PDF».
- Контроль правил: вернитесь к плану и удалите одну меру. С четырьмя решениями итоговый расчёт недоступен; добавление пятой допустимой меры восстанавливает возможность расчёта.
- Полный поиск: в редакторе нажмите «Найти лучший план с ИИ». Для текущего набора
astana-s2-v1поиск проверяет 694 395 допустимых сценариев и находит Score 57,236735 (на экране 57,24) при цене 9,8 млрд ₸. Кандидат доступен даже при ошибке AI и заменяет черновик только после «Применить лучший план». Состав и проверка — в описании оптимизатора.
Точные числа контрольного примера проверяются существующими тестами:
npm.cmd test -- tests/domain/simulation.test.ts tests/api/simulation.test.ts
Короткий маршрут первого запуска — docs/DEMO.md. Для защиты используйте демонстрацию пользы за 2–3 минуты: сравнение двух планов, цена улучшения и районные компромиссы. Выполненные проверки и незавершённые шаги сдачи отделены в проверке выпуска.
09 · Данные и интеграции
| Источник / сервис | Что используется и когда |
|---|---|
| Задание хакатона S1–S3 | Синтетические показатели пяти районов, доли населения, цены, эффекты 14 мер и формула Score. Снимки и оригинальные ссылки: источники требований |
Локальный набор src/data/ | Одинаковые исходные данные для всех сессий, версия и SHA-256 hash; внешняя статистика во время расчёта не загружается |
| OpenStreetMap / Nominatim | Географическая основа и ориентиры. Снимки подготовлены заранее; приложение не вызывает геокодер при каждом запуске |
| OpenFreeMap | Подложка, тайлы и ресурсы карты загружаются через интернет, ключ карты не нужен |
| OpenAI API | По запросу получает факты рассчитанного сценария и выбранные меры; возвращает объяснение. Провайдер настраивается серверными переменными окружения |
Браузерный localStorage | Явно сохранённые сценарии и состояние обучения; внешнее хранилище не используется |
Геометрия приведена к пяти зонам модели: Есиль, Алматы, Сарыарка, Байконур, Нура. В подготовленном снимке нынешние Алматы и Сарайшык объединены для соответствия заданию. Это игровое сопоставление, а не официальная карта административного деления. Источники, преобразования и атрибуция OpenMapTiles / OpenStreetMap перечислены в docs/MAP_SOURCES.md; геоданные распространяются на условиях ODbL.
10 · Ограничения текущей версии
- Фиксированная учебная модель: пять районов, 14 мер, горизонт восемь кварталов. Нет живой городской статистики, реальных смет, случайных событий или полноценной симуляции транспорта. Метки на карте иллюстрируют решения и не обозначают утверждённые строительные площадки.
- Принята трактовка подробных правил S2: максимум две меры одного направления, поэтому допустимы пять решений из трёх и более направлений. Обязательного выбора по одной мере каждого направления нет. Расхождение с краткой формулировкой S1 зафиксировано в docs/DECISIONS.md.
- AI зависит от внешнего API: нужны ключ, доступ к модели и сеть. Проверка структуры, ссылок на факты и чисел снижает риск ошибок, но не гарантирует правильность всех качественных выводов. Отклонённый ответ можно запросить повторно.
- Сохранения локальные: до шести сценариев в одном браузере. Несохранённый черновик и текущий отчёт теряются при перезагрузке. Нет аккаунтов, облачной синхронизации и совместного редактирования.
- Карта зависит от WebGL и сети: при недоступной подложке или WebGL доступен расчёт и отчёт, но полноценная 3D-карта недоступна. Полный офлайн-режим не реализован.
- Оптимум относится только к этой модели и Score. Он не означает лучшего результата по каждому показателю. Отдельный поиск замены одного решения не гарантирует глобальный максимум.
- Ограничение частоты AI-запросов и кеш оптимизатора хранятся в памяти процесса. Общее хранилище для нескольких серверных экземпляров не реализовано.
- PDF получается печатью HTML: отдельного серверного генератора PDF нет.
Следующие шаги развития — пока не реализованы:
- Провести учебный пилот: сравнить, насколько участники понимают бюджет, лаги и районные компромиссы до и после работы с симулятором.
- Добавить импорт версионированных наборов для других городов и откалибровать эффекты с профильными специалистами; проверять источники и неопределённость данных перед практическим использованием.
- В отдельном режиме исследования сравнивать цели «максимум Score / меньшие расходы / равномерность улучшений», сохраняя исходную формулу и правила хакатона в основном режиме.
11 · Развёрнутая версия
По состоянию на 23 сентября 2026 года публичный deployment в проекте не зафиксирован. Для проверки используйте локальный запуск: http://127.0.0.1:3000/; этот адрес доступен только на компьютере с запущенным приложением.
Настройки Next.js, переменные окружения и проверка после публикации описаны в инструкции для Vercel. Успешный запуск на публичном адресе требует отдельной проверки.
Авторы коммитов
История коммитов
- 2026-09-23 17:58Fix planner footer overlap on narrow panelsMagurin
- 2026-09-23 17:51Record verified hackathon release pushMagurin
- 2026-09-23 17:50Complete hackathon simulator, grounded AI analysis and release documentationMagurin
- 2026-09-23 17:19Keep measure pins geographically stable and highlight their scopeMagurin
- 2026-09-23 16:49Prevent marker overlap and integrate accessible city controls and guideMagurin
- 2026-09-23 16:43Verify dense map marker spacing across camera and viewport changesMagurin
- 2026-09-23 16:34Verify tenge report downloads and refresh delivery materialsMagurin
- 2026-09-23 16:31Improve readable metrics and tenge budgets across planner and reportsMagurin
Все коммиты (39)
- 2026-09-23 16:19Enter city explicitly in layout and map performance checksMagurin
- 2026-09-23 16:09Remove obsolete decoration toggle from demo and regression checksMagurin
- 2026-09-23 16:08Explain tenge budget mapping in project READMEMagurin
- 2026-09-23 16:07Record app shell ownership handoff for learning modeMagurin
- 2026-09-23 16:07Validate AI quantities against cited facts and repair invalid reportsMagurin
- 2026-09-23 16:05Add tenge budget scale to validation onboarding and exportsMagurin
- 2026-09-23 15:58Record completed map card cleanup acceptanceMagurin
- 2026-09-23 15:52Record verified delivery snapshot and pending platform submissionMagurin
- 2026-09-23 15:52Integrate remaining plan features and verify complete user journeysMagurin
- 2026-09-23 15:47Normalize onboarding source formattingMagurin
- 2026-09-23 15:46Add interactive mayor onboarding with guided spotlight and arrowsMagurin
- 2026-09-23 15:46Document onboarding comparisons export and city decorationMagurin
- 2026-09-23 15:46Use GPT-6 Luna for verified AI reportsMagurin
- 2026-09-23 15:44Add verified portable HTML and JSON report exportMagurin
- 2026-09-23 15:43Add saved scenario comparisons and validated local improvementsMagurin
- 2026-09-23 15:32Center city report switch in navigationMagurin
- 2026-09-23 15:24Apply graphite liquid-metal design and remove nav titleMagurin
- 2026-09-23 15:20Unify custom dropdowns and register visual refreshMagurin
- 2026-09-23 15:19Complete acceptance with measured 3D map performanceMagurin
- 2026-09-23 15:12Use compact structured AI responses and verify recommendationMagurin
- 2026-09-23 15:07Verify responsive layout and keyboard map controlsMagurin
- 2026-09-23 15:07Fix planner keyboard focus and mobile report overflowMagurin
- 2026-09-23 14:56Explain a verified cost and lag tradeoff in reportMagurin
- 2026-09-23 14:54Add browser acceptance and performance checksMagurin
- 2026-09-23 14:53Document reproducible setup and demo pathMagurin
- 2026-09-23 14:53Improve grounded AI guidance and update NVIDIA modelMagurin
- 2026-09-23 14:46Verify live OpenAI analysis and close integration tasksMagurin
- 2026-09-23 14:43Refine liquid UI and responsive readabilityMagurin
- 2026-09-23 14:37Integrate city scenario and visual measure effectsMagurin
- 2026-09-23 14:27Add server AI analysis with validated facts and API errorsMagurin
- 2026-09-23 14:24Build Astana map, scenario engine, planner, report, and simulation APIMagurin
Структура репозитория (192 файлов)
.env.example .gitignore .nvmrc AGENTS.md CLAUDE.md PLAN.md README.md coordination/claims/.gitkeep coordination/claims/O01.json coordination/claims/O02.json coordination/claims/O03.json coordination/claims/P01.json coordination/claims/P02.json coordination/claims/P03.json coordination/claims/P04.json coordination/claims/P05.json coordination/claims/P06.json coordination/claims/P07.json coordination/claims/P08.json coordination/claims/P09.json coordination/claims/P10.json coordination/claims/P11.json coordination/claims/P12.json coordination/claims/P13.json coordination/claims/P14.json coordination/claims/P15.json coordination/claims/P16.json coordination/claims/P17.json coordination/claims/P18.json coordination/claims/P19.json coordination/claims/P20.json coordination/claims/P21.json coordination/claims/P22.json coordination/claims/P23.json coordination/claims/P24.json coordination/claims/P25.json coordination/claims/P26.json coordination/claims/P27.json coordination/claims/P28.json coordination/claims/P29.json coordination/claims/P30.json coordination/claims/P31.json coordination/claims/P32.json coordination/claims/P33.json coordination/claims/P34.json coordination/claims/P35.json coordination/claims/P36.json coordination/claims/P37.json coordination/claims/P38.json coordination/claims/P39.json coordination/claims/P40.json coordination/claims/P41.json coordination/claims/P42.json coordination/claims/P43.json coordination/claims/P44.json coordination/claims/P45.json coordination/claims/P46.json coordination/claims/P47.json coordination/claims/P48.json coordination/claims/P49.json coordination/claims/P50.json coordination/claims/P51.json coordination/claims/P52.json coordination/claims/P53.json coordination/history/O02-codex-city-decoration-20260923-final-handoff.json coordination/history/P01-codexcli-20260923-9c34c28a.json coordination/history/P03-codexcli-spend-cap-20260923-141336.json coordination/history/P11-before-readme-20260923-01a0ce32.json coordination/history/P11-before-visual-style-20260923-01a0ce2f.json docs/ACCEPTANCE.md docs/AGENT_PROTOCOL.md docs/API.md docs/BUDGET.md docs/DECISIONS.md docs/DELIVERY.md docs/DEMO.md docs/JURY_DEMO.md docs/LEARNING.md docs/MAP_SOURCES.md docs/OPTIMIZER.md docs/RELEASE_CHECK.md docs/VERCEL.md docs/sources/01-task.txt docs/sources/02-rules.txt docs/sources/03-attachment.pdf docs/sources/03-attachment.txt docs/sources/README.md docs/sources/effect-landmarks-osm.json eslint.config.mjs next-env.d.ts next.config.ts package-lock.json package.json playwright.config.ts public/geo/astana-game-zones.geojson public/geo/astana-osm-source.json public/maplibre-gl-shared.mjs public/maplibre-gl-worker.mjs scripts/build-effect-landmarks.mjs scripts/build-geo.py scripts/claim-task.ps1 scripts/watch-status.ps1 src/app/AppShell.module.css src/app/AppShell.tsx src/app/api/analyze/route.ts src/app/api/optimize/route.ts src/app/api/scenario/route.ts src/app/api/simulate/route.ts src/app/globals.css src/app/icon.svg src/app/layout.tsx src/app/page.tsx src/components/SelectMenu.module.css src/components/SelectMenu.tsx src/contracts/index.ts src/contracts/scenario-request.schema.json src/data/README.md src/data/canonical.ts src/data/index.ts src/domain/search/improve.ts src/domain/search/optimize.ts src/domain/simulation.ts src/domain/validation.ts src/features/city-decoration/CityDecoration.test.tsx src/features/city-decoration/CityDecoration.tsx src/features/city-effects/CityEffects.module.css src/features/city-effects/CityEffects.tsx src/features/city-effects/impact.ts src/features/city-effects/landmarks.json src/features/city-effects/model.ts src/features/city-effects/positions.ts src/features/city-effects/sites.json src/features/city-map/CityMap.module.css src/features/city-map/CityMap.tsx src/features/city-map/score-colors.ts src/features/comparison/ComparisonPanel.module.css src/features/comparison/ComparisonPanel.tsx src/features/comparison/storage.ts src/features/export/ExportReport.module.css src/features/export/ExportReport.tsx src/features/export/report.test.ts src/features/export/report.ts src/features/onboarding/MayorGuide.module.css src/features/onboarding/MayorGuide.tsx src/features/onboarding/Spotlight.tsx src/features/onboarding/tour-progress.ts src/features/optimizer/OptimizerPanel.module.css src/features/optimizer/OptimizerPanel.tsx src/features/optimizer/responses.ts src/features/planner/Planner.module.css src/features/planner/Planner.tsx src/features/results/ReportView.module.css src/features/results/ReportView.tsx src/lib/budget.ts src/server/ai/facts.ts src/server/ai/provider.ts src/server/ai/validation.ts tests/ai/facts.test.ts tests/ai/provider.test.ts tests/ai/validation.test.ts tests/api/optimize.test.ts tests/api/simulation.test.ts tests/city-effects/impact.test.ts tests/city-effects/lifecycle.test.tsx tests/city-effects/model.test.ts tests/city-effects/placement.test.ts tests/data/data.test.ts tests/data/source-fixture.ts tests/domain/simulation.test.ts tests/e2e/layout.spec.ts tests/e2e/marker-spacing.spec.ts tests/e2e/onboarding.spec.ts tests/e2e/optimizer.spec.ts tests/e2e/optional-features.spec.ts tests/e2e/performance.spec.ts tests/e2e/scenario.spec.ts tests/fixtures/performance/chrome-30s-decoration.zip tests/fixtures/performance/chrome-30s-kiosk.zip tests/fixtures/performance/headed-decoration-run.json tests/fixtures/performance/headed-kiosk-run.json tests/search/comparison-ui.test.tsx tests/search/comparison.test.ts tests/search/optimize.test.ts tests/ui/city-guide.test.tsx tests/ui/onboarding-progress.test.tsx tests/ui/onboarding.test.tsx tests/ui/optimizer.test.tsx tests/ui/planner.test.tsx tests/ui/results.test.tsx tests/ui/select-menu.test.tsx tsconfig.json vitest.config.ts
Обсуждение 0 комментариев
Войдите, чтобы комментироватьПока нет комментариев — будьте первым.