Принципы A-01…A-15 и контракты между процессами¶
Расширение к README.md: первоисточник принципов — docs/task5/50-stack/05-service-architecture.md. Здесь — привязка к файлам и перечень gRPC/REST для ревью кода.
gRPC-сервисы¶
| Файл | Сервис | Методы | Назначение |
|---|---|---|---|
src/backend/proto/geoscan/planner.proto |
PlannerService |
Plan (server stream), ExportPlan |
Расчёт и выгрузка KML/GeoJSON/plan/waypoints |
src/backend/proto/geoscan/validator.proto |
ValidatorService |
Validate |
Независимый отчёт admitted, violations, metrics |
src/backend/proto/geoscan/common.proto |
— | общие типы | Violation, Unassigned, ExportFormat, SolverStatus |
Клиенты gateway: src/backend/gateway/src/common/grpc/planner.client.ts, validator.client.ts. Дедлайн расчёта: time_limit_s из задания + 30 с запас (plan-dispatcher.service.ts:93-94).
REST gateway (публичный контур)¶
| Префикс | Контроллер | Примечание |
|---|---|---|
POST/GET /api/plans |
plans.controller.ts |
202 на создание, SSE GET :id/events |
GET /api/plans/:id/export/:fmt |
там же | fmt ∈ geojson, kml, plan, waypoints |
POST /api/validate |
validate.controller.ts |
Прокси в validator gRPC |
GET/POST /api/scenarios |
scenarios.controller.ts |
Реестр и upsert сценариев |
GET /api/fleet, /api/payloads |
fleet.controller.ts |
Каталог из docs/task5/10-hardware |
GET /healthz, /readyz, /status, /metrics |
ops.controller.ts |
A-02 на gateway — полный HTTP для ops |
OpenAPI: /api/docs, JSON: /api/openapi.json (SwaggerModule.setup('api/docs', …) — main.ts:90-91). В логе при старте указано docs: /docs (main.ts:98) — это не рабочий URL, только текст сообщения.
Барьерные тесты (A-13)¶
| Область | Путь |
|---|---|
| Валидатор не импортирует planner | src/backend/validator/tests/test_independence.py |
| Опции proto-loader | src/backend/tests/integration/test_loader_options.py |
| Контракт planner/validator gRPC | test_planner_grpc_server.py, test_validator_grpc_server.py |
| Деплой: metrics validator | test_deploy_contract_b6.py (ожидает geoscan_validator_violations_total) |
A-01…A-15 — развёрнутые формулировки¶
Краткая таблица статуса — в README. Ниже — что означает каждый ID для разработчика, меняющего код.
- A-01 — не добавлять второй публичный HTTP с бизнес-ручками; фронт не зовёт planner:5001 напрямую.
- A-02 — в Python не заводить FastAPI/Flask для домена; только
ops.pyна ThreadingHTTPServer. - A-03 — меняя
.proto, прогонять генерацию и pin-тест; поля в JSON остаютсяsnake_case. - A-04 — при добавлении RPC всегда передавать
buildMetadataс ключом изSERVICE_API_KEY. - A-05 — логировать
requestIdиз контекста; не терять при async dispatch плана. - A-06 — доменные ошибки в planner/validator → gRPC status; HTTP-код выбирает только gateway.
- A-07 — не блокировать
POST /api/plansдо конца OR-Tools; прогресс только через stream + SSE. - A-08 — не вводить брокер без второго подписчика на событие.
- A-09 — повтор
POST /api/plansс тем же ключом и телом → тот жеplanId, заголовокIdempotency-Replayed. - A-10 — не писать SQL из gateway в «чужую» схему; новый домен = новая схема + миграции.
- A-11 — новые секреты в creds-store, в манифестах — только
secretKeyRef. - A-12 — при новой метрике домена добавить в Prometheus и дашборд (
k3s/monitoring/). - A-13 — инвариант, который можно нарушить молча, закрывается тестом в
tests/barriersили domain-specific (independence). - A-14 — копировать каркас
main.ts/serve.py/ grpc module при новом процессе. - A-15 — не выделять микросервис без обоснования;
exportостаётся в planner, пока нет внешних планов.
PostGIS¶
Образ БД — PostGIS; расширение готово для будущего сервиса airspace (A-10, таблица в 05-service-architecture.md:223). Текущий gateway хранит геометрию в JSONB и не вызывает ST_* — поиск ST_ в src/backend (кроме venv) пустой для прикладного кода.