Files
autotest/AGENT_BRIEFING.md

181 lines
11 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# AGENT BRIEFING — app-autotest (2026-07-31, v1.2.23)
> **Контекст для нового агента.** Прочитай этот файл полностью — он заменит тебе чтение 4166 строк истории чата. Здесь всё что нужно знать чтобы продолжить работу.
---
## 1. Что такое app-autotest
Flask 3.1 + vanilla JS + PostgreSQL (psycopg2). Веб-приложение для автоматического тестирования сервисов облачной платформы Nubes через REST API.
**Ручной режим:** выбрать сервис → выбрать операцию (create/modify/delete/suspend/resume/redeploy) → заполнить параметры → запустить → поллинг статуса.
**Сценарный режим:** последовательность операций с передачей контекста между шагами. Сценарии редактируются через модальный UI, хранятся в БД.
**Деплой:** Nubes pythonk8s managed service, gunicorn --workers 2.
**URL:** `https://atest.pythonk8s.dev.nubes.ru`
**Репозиторий:** `https://gitea.services.ngcloud.ru/forcloud/app-autotest.git` (ветка `master`)
### Файлы которые надо прочитать (обязательно)
- [DOCS/ARCHITECTURE.md](DOCS/ARCHITECTURE.md) — архитектура, эндпоинты, безопасность
- [DOCS/polygon-plan.md](DOCS/polygon-plan.md) — полный план мок-полигона
- [HISTORY/2026-07-31-session.md](HISTORY/2026-07-31-session.md) — хронология всего что сделано сегодня
- [TASKS/mock-architecture-prompt.md](TASKS/mock-architecture-prompt.md) — исходный промпт для Опуса
- [TASKS/universal-mock-generator-prompt.md](TASKS/universal-mock-generator-prompt.md) — промпт про STANDS YAML
### Структура кода
```
app-autotest/site/
├── app.py # точка входа (VERSION = "1.2.23")
├── api/
│ ├── auth.py # токен/clientId/stand из JWT cookie
│ ├── http_client.py # HttpClient (requests.Session) + автостенд
│ └── utils.py # find_uid(), uid_from_location()
├── operations/
│ ├── executor.py # ЕДИНЫЙ запуск (create→instanceOperations→params→run)
│ ├── poll.py # poll_until_done() — поллинг до dtFinish
│ ├── scenario.py # run_scenario() — шаги с резолвингом instance_ref
│ ├── terraform.py # send_params_terraform() — нормализация + refSvc + validate-cfs
│ ├── tracker.py # JSON-файловый кеш /tmp/instances-*.json (flock)
│ ├── get_instances.py # GET /instances с пагинацией
│ ├── get_params.py # параметры с ТЕКУЩИМИ значениями из state.params
│ ├── get_services.py # GET /services
│ └── service_list.py # services_{stand}.txt фильтр
├── db/
│ ├── pool.py # ThreadedConnectionPool(1,5)
│ ├── init_db.py # CREATE TABLE + миграции + idx_one_running + seed
│ ├── save_run.py # INSERT в runs + instance_meta JSONB
│ └── scenario_defs.py # CRUD scenario_definitions + lock_check (трёхсостояночный)
├── routes/
│ ├── main.py # GET/POST / — главная страница
│ ├── api_test.py # /api/test, /api/params, /api/log (основная логика)
│ ├── api_scenario_run.py # /api/scenario/run, /api/scenario/status
│ ├── api_scenario_defs.py # CRUD /api/scenario/definitions
│ ├── api_scenario.py # ДУБЛИКАТ? (241 строка)
│ └── api.py # LEGACY /api/run
├── static/
│ ├── app.js, style.css
│ └── js/ (12 файлов: utils, icons, snackbar, views, instances, operations,
│ params-render, history, scenario-list, scenario-form,
│ scenario-create, scenario-edit, scenario-delete)
└── templates/
└── index.html
```
---
## 2. Что было сделано сегодня (2026-07-31)
### Версии
- v1.2.16 → v1.2.23 (8 версий)
- 23 коммита в app-autotest, 9 в root autotest
### Комментарии ко ВСЕМУ коду
29 файлов, ~6000 строк. Подробные комментарии к каждой функции, каждому if-ветвлению, каждому архитектурному решению. Python + JS.
### Аудит безопасности (GPT-5.3-Codex, 3 раунда)
**Раунд 1 (11 находок):**
- v1.2.19: XSS params, JS injection onclick, polling timeout, has_target, tracker atomic update
- v1.2.20: _op_results lock (threading.Lock), advisory lock (pg_try_advisory_lock), _ensure_schema logging, stale async generation token, validate-cfs JSONDecodeError
**Раунд 2 (Codex нашёл 2 критических ошибки в моих фиксах):**
- ❌ Advisory lock сломан: брал lock на conn1, unlock на conn2 (другая сессия из пула)
- ❌ escName без `"` escape: HTML-атрибут onclick="..." разрывается
- v1.2.21: advisory lock → partial unique index `idx_one_running`, escName + `"`
**Раунд 3 (3 находки):**
- v1.2.22: UniqueViolation→409, escName + `&`, lock_check fallback
- v1.2.23: трёхсостояночный lock_check (True/False/None→503) после дискуссии
**Тесты:** `app-autotest/tests/` — 5 файлов от Codex (conftest, test_api_scenario_run, test_db_scenario_defs, test_static_regressions, README). Покрывают критические фиксы. НЕ запускались.
### Архитектура мок-полигона (Опус)
**Концепция:** отдельный managed-сервис `https://nubes_polygon.pythonk8s.dev.nubes.ru`, притворяющийся Nubes API для всех 37 сервисов.
**10 архитектурных решений** (см. [DOCS/polygon-plan.md](DOCS/polygon-plan.md)):
- Отдельный процесс :5001 (не blueprint)
- Data-driven: сервисы из STANDS YAML, не хардкод
- Ленивый dtFinish (без потоков)
- Единая стейт-машина (create→running→suspended→deleted)
- Реальный мерж params при modify
- `/_mock/reset` для тестов
**Универсальный конвертер STANDS YAML** — Опус подтвердил: `polygon/from_stands.py` читает 37 YAML из `STANDS/test/resources_yaml/` и генерит конфиги для всех сервисов. Маппинг почти 1:1 (см. HISTORY).
**Subresource-операции**`create_user`/`create_database` через обычный `apply_effect` с флагом `subresource`. Универсально, без сервис-специфичного кода.
---
## 3. Что надо делать дальше
### 🔴 Срочно (сегодня)
**Реализовать мок-полигон** по плану в [DOCS/polygon-plan.md](DOCS/polygon-plan.md):
Фаза 1 — MVP:
1. `polygon/defaults.py``default_for(dataType)`
2. `polygon/from_stands.py` — конвертер STANDS YAML → polygon config
3. `polygon/state.py``MockState` (instances, operations, ленивый dtFinish, apply_effect, reset)
4. `polygon/server.py` — Flask на порту 5001, префикс `/api/v1/svc`, Location-заголовки
5. `polygon/services/` — НЕ создавать вручную! Генерится из STANDS
6. Интеграция в `auth.py` — short-circuit localhost (см. §3.3 в polygon-plan.md)
Фаза 2 — полный CRUD:
7. GET /instances, GET /instances/{uid}, GET /services, GET /services/{id}
8. GET /instanceOperations/default/{id} (cfsParams шаблон)
9. apply_effect для всех операций + subresource
10. `/_mock/reset`
Фаза 3 — тесты:
11. `tests/conftest.py` — фикстура поднятия мока
12. `tests/test_mock_integration.py` — 5 сценариев через app_client
### 🟡 В планах
- Прогнать конвертер на ВСЕХ 37 YAML, найти аномалии
- Исправить `instances.js:78` — instanceUid в onclick (низкий риск)
- Вынести `_op_results` в Redis/БД (архитектурное ограничение)
- Context snapshot всех инстансов пользователя (идея из HISTORY)
---
## 4. Ключевые файлы документации
| Файл | Содержание |
|------|-----------|
| [DOCS/ARCHITECTURE.md](DOCS/ARCHITECTURE.md) | Полная архитектура, эндпоинты Nubes API, безопасность (§8) |
| [DOCS/polygon-plan.md](DOCS/polygon-plan.md) | План мок-полигона: 3 фазы, 12 шагов, YAML-спецификация |
| [DOCS/architecture-final.md](DOCS/architecture-final.md) | Финальная архитектура |
| [HISTORY/2026-07-31-session.md](HISTORY/2026-07-31-session.md) | Хронология: все версии, аудит, ошибки, дискуссии |
| [TASKS/mock-architecture-prompt.md](TASKS/mock-architecture-prompt.md) | Исходный промпт для Опуса |
| [TASKS/universal-mock-generator-prompt.md](TASKS/universal-mock-generator-prompt.md) | Промпт про STANDS YAML + ответы |
| [STANDS/test/resources_yaml/](STANDS/test/resources_yaml/) | 37 YAML — источник для конвертера |
---
## 5. Что НЕ надо делать
- ❌ Не деплоить app-autotest без повышения версии
- ❌ Не править код без явного «делай»
- ❌ Не использовать sed для правки файлов
- ❌ Не удалять файлы/БД/контейнеры без разрешения
---
## 6. Как запускать
```bash
# app-autotest (основное)
cd app-autotest/site && python app.py # порт 5000
# Мок-полигон (когда будет готов)
cd app-autotest && STANDS_DIR=../STANDS/test/resources_yaml python polygon/server.py # порт 5001
# Тесты (когда будут готовы)
NUBES_API_ENDPOINT=http://localhost:5001/api/v1/svc pytest tests/ -v
```