# Ответ Claude Sonnet (v2 — после жёстких ограничений) **Дата:** 2026-08-13 **Источник:** Claude Sonnet, промпт v2 (жёсткий список из 16 файлов, без поиска, без терраформа) --- ## 1. Код-ревью (блокеры деплоя) | Файл | Находка | Блокер? | |---|---|---| | `Dockerfile` | `EXPOSE 4100`, не 80 — порт нестандартный, но конфигурируемый | зависит от платформы (→ открытый вопрос №1) | | `persistence/redis.go` | `redis.Options` без `TLSConfig` — plain TCP на `*.svc.cluster.local:6379` | зависит от платформы (→ открытый вопрос №3) | | `router/router.go` | TLS терминируется снаружи (в k8s — Ingress); сам код HTTP | нет — аналогично работает за любым proxy | | `admin/admin.go` | `NUBES_ENDPOINT` default = тестовый `deck-api-test.ngcloud.ru` | нет — переопределяется env | | `goaws.go` | `SHARED_SQS_ADMIN_TOKEN` — обязательный env, fatal без него | нет — задаётся в контейнере | | `Makefile` | образ в Docker Hub (`naeel/shared-sqs`), не в приватном registry | зависит от платформы (→ открытый вопрос №2) | **Код менять не нужно.** Все потенциальные проблемы — на стороне платформы, не кода. --- ## 2. Целевая архитектура ```mermaid graph TD Client["AWS SDK / CLI\n(endpoint_url = новый домен)"] Proxy["Nubes Platform Proxy\nTLS termination"] App["Простой HTTP контейнер\nnaeel/shared-sqs:v0.1.22\nport 4100"] Redis["Managed Redis\nredisk8s.4ff5678b-b683-4aef-91da-22d89dec8a25\n.svc.cluster.local:6379\nrealm iot-naeel"] PG["Managed PostgreSQL\n(опционально, billing)"] NubesAPI["NUBES_ENDPOINT\nJWT-валидация UI"] Client -->|HTTPS :443| Proxy Proxy -->|HTTP :4100\ninternal| App App -->|"TCP :6379\nno TLS, internal DNS"| Redis App -. "BILLING_PG_HOST задан" .->|TCP :5432| PG App -->|HTTPS| NubesAPI ``` **Env vars контейнера:** ``` SHARED_SQS_ADMIN_TOKEN=<секрет> REDIS_ADDR=redisk8s.4ff5678b-b683-4aef-91da-22d89dec8a25.svc.cluster.local:6379 REDIS_USER=default REDIS_PASSWORD=ZJOke5b2bIr6YPOKrnJG NUBES_ENDPOINT=https:///api/v1 ← уточнить (вопрос №6) SHARED_SQS_SEED_DEMO=false # Только если нужен billing: BILLING_PG_HOST=... BILLING_PG_PORT=5432 BILLING_PG_DATABASE=... BILLING_PG_USER=... BILLING_PG_PASSWORD=... BILLING_PG_SSLMODE=require ``` --- ## 3. План миграции (через deck-UI) ### Шаг 0 — Ответы на платформу (блокирует остальное) Получить ответы на 7 открытых вопросов из раздела 4. *Критерий: все вопросы закрыты, особенно №1 (порт), №3 (TLS Redis), №4 (DNS).* --- ### Шаг 1 — Проверить Managed Redis доступность Запустить временный контейнер (любой с `redis-cli`) в realm iot-naeel, выполнить: ``` redis-cli -h redisk8s.4ff5678b-b683-4aef-91da-22d89dec8a25.svc.cluster.local \ -p 6379 -a ZJOke5b2bIr6YPOKrnJG ping ``` *Критерий: ответ `PONG`.* *Откат: не нужен — k8s работает.* --- ### Шаг 2 — Создать "Простой HTTP контейнер" в deck-UI В deck выбрать realm `iot-naeel`, создать контейнер: - Образ: `naeel/shared-sqs:v0.1.22` (или полный путь — уточнить вопрос №2) - Порт: 4100 (или как требует платформа — вопрос №1) - Ресурсы: min 64Mi/50m CPU, max 256Mi/500m CPU - Env vars: полный список из раздела 2 выше - Health check: `/health` (уже задан в Dockerfile через `wget`) *Критерий: контейнер поднялся, статус healthy, `curl /health` → 200 OK.* *Откат: удалить контейнер в deck-UI, трафик остаётся в k8s.* --- ### Шаг 3 — Smoke test (до переключения трафика) ```bash # 1. Health curl -m 5 https:///health # 2. Создать тенанта curl -m 5 -X POST https:///admin/tenants \ -H "Authorization: Bearer " \ -d '{"name":"smoke","maxQueues":5}' # 3. Создать очередь и прогнать сообщение aws sqs create-queue --queue-name test-q \ --endpoint-url https:// --region us-east-1 aws sqs send-message --queue-url ... --message-body hello aws sqs receive-message --queue-url ... ``` *Критерий: все 3 операции успешны; `/metrics` содержит `sqs_*` метрики.* *Откат: исправить env vars в deck-UI → рестарт контейнера.* --- ### Шаг 4 — Переключить клиентов Обновить `endpoint_url` на всех клиентах с `qu.kube5s.ru` → новый домен Nubes. *(Домен `qu.kube5s.ru` не использовать.)* *Критерий: метрики `sqs_messages_received_total` растут на новом инстансе; ошибок в логах нет.* *Откат: вернуть `endpoint_url` на k8s адрес (он ещё жив).* --- ### Шаг 5 — Вывод k8s (только после N дней стабильной работы) В k8s удалить (в таком порядке): 1. Ingress `shared-sqs-ingress` 2. Deployment `shared-sqs` 3. Deployment `shared-sqs-redis` + PVC `shared-sqs-redis-pvc` ← **необратимо, только когда уверены в данных** 4. Secrets `shared-sqs-admin`, `shared-sqs-redis` 5. Namespace `shared-sqs` (если больше не нужен) *Критерий: namespace пуст, сервис работает только через Nubes.* --- ## 4. Открытые вопросы (ответы только от платформы Nubes) | # | Приоритет | Вопрос | |---|---|---| | 1 | **КРИТИЧНО** | Какой порт ожидает "Простой HTTP контейнер" — читает `EXPOSE 4100`, требует явного поля `port`, или нужен env `PORT`? | | 2 | **КРИТИЧНО** | Как задаётся образ в deck-UI — Docker Hub `naeel/shared-sqs:v0.1.22` напрямую, или нужен предварительный push в Nubes-registry? Если registry — какой адрес и как аутентифицироваться? | | 3 | **КРИТИЧНО** | Требует ли Managed Redis TLS на внутреннем адресе `*.svc.cluster.local:6379`? Код подключается без TLS. | | 4 | **КРИТИЧНО** | Видит ли контейнер `nubes_http` внутренний DNS `*.svc.cluster.local` в realm iot-naeel? | | 5 | **ВЫСОКИЙ** | Какой URL/домен получает контейнер после деплоя — авто-выдаётся или задаётся вручную? | | 6 | **ВЫСОКИЙ** | Какой production URL для `NUBES_ENDPOINT` (вместо тестового `deck-api-test.ngcloud.ru`)? | | 7 | **ВЫСОКИЙ** | Поддерживает ли платформа idle HTTP-соединения до 20–30 секунд (SQS long-polling, `WaitTimeSeconds` до 20с)? Если таймаут < 20с — клиенты с long-polling будут получать ошибки. |