# internal/lkgateway — BFF слой ЛК + admin web UI

Реализует REST-контракт ESIA Finance V1
(`docs/lk-contract/v1/openapi.yaml`) на стороне Bridge-and-Join-s и
admin-веб для оператора.

## REST API

- `POST /api/v1/back_office/claims/` — приём заявки от ЛК.
  Валидирует, собирает `M2MTransferRequest` через
  `m2mcore.EnrichRequest`, создаёт `m2mcore.Deal`, отправляет в НРД
  через `m2mcore.NSDSender` (на M2 — mock).
- `GET /api/v1/back_office/claims/{id}` — карточка заявки.
- `GET /api/v1/back_office/claims` — список с фильтрами
  (status/investor_id/created_from/created_to/limit/offset).
- `PATCH /api/v1/back_office/claims/{id}` — placeholder для callback
  от внешней системы.
- `/healthz` — health.

## Admin web UI

- `/admin/` — дашборд: статус системы, счётчики (Total/Confirmed/
  InProgress/Failed), последние 10 заявок.
- `/admin/claims` — журнал всех заявок.
- `/admin/claims/{id}` — детальная карточка: история FSM, ответ НРД
  (`M2MTransferResponse`), решение принимающей стороны
  (`M2MTransferDecision`), последний callback.
- `/admin/status` — детальные проверки: postgres, crypto-service (UDS),
  nsd-adapter (REST), lk-emulator callback URL.

## Состав пакета

- `server.go` — `Server` обвязка: HTTP mux + сервис + фоновый
  consumeDecisions (читает из `mock.Sender.Decisions()` и обновляет
  сделки + шлёт callback в ЛК).
- `service.go` — бизнес-логика: DTO ↔ доменные сущности m2mcore,
  оркестрация FSM, отправка callback'ов.
- `api.go` — REST endpoints.
- `admin.go` — HTML endpoints с шаблонами в `web/templates/`.
- `checks.go` — проверки готовности подсистем (postgres, crypto-service,
  nsd-adapter, callback URL).
- `seedstore.go` — in-memory `m2mcore.FansyStore` с 5 тестовыми
  клиентами и счетами депо (соответствует
  `docs/fansy-contract/v1/examples/seed-data.sql`).
- `types.go` — DTO под OpenAPI.
- `http_util.go` — JSON-хелперы.

## Конфигурация (cmd/lk-gateway/main.go, ENV)

| Переменная | По умолчанию | Назначение |
|---|---|---|
| `BJ_HTTP_ADDR` | `:8080` | Адрес HTTP |
| `BJ_M2M_SENDER` | `MC0079200000` | DeponentCode отправителя в M2M Header |
| `BJ_M2M_RECEIVER` | `MC0010300000` | DeponentCode получателя |
| `BJ_DSN` | — | PostgreSQL DSN (M2-шаг-3, пока пусто = in-memory) |
| `BJ_CRYPTO_SOCKET` | `/run/bj/crypto.sock` | UDS для crypto-service |
| `BJ_NSD_ADAPTER_URL` | — | URL nsd-adapter HTTP (пусто = mock) |
| `BJ_LK_CALLBACK_URL` | — | URL ЛК для PATCH callback'ов (пусто = эмулятор регистрирует свой) |
| `BJ_NSD_PROFILE` | `demo (mock NSD)` | Имя профиля (отображается в admin) |
| `BJ_CRYPTO_PROVIDER` | `stub` | Провайдер криптографии в admin-статусе |

## Что подключается в следующих шагах

- **M2-шаг-3**: pgx-репозиторий → миграция
  `migrations/m2m-core/001__deals.sql` уже готова.
- **M3**: реальный `nsd-adapter` вместо mock — выставить
  `BJ_NSD_ADAPTER_URL` и реализовать в nsd-adapter поллер,
  отправляющий Decision не через канал mock, а через шину.
- **M4**: `admin-ui` v2 на React + раздел «Сертификаты КриптоПро»
  для обновления публичных сертификатов через UI.
