17 KiB
CHAT RESUME: IaC-развёртывание Штурвала — состояние на 2026-09-24
Кому: новый чат / новый участник. Читать целиком, это хендовер. Что это: сводка длинной сессии (2026-09-23/24) по вопросу «как дать клиенту IaC для цепочки Штурвал». Статус: решение НЕ принято, код НЕ написан. Есть анализ, проверенные факты и развилка.
0. TL;DR (одним абзацем)
Клиенту нужен настоящий IaC: один конфиг + terraform apply = вся инфраструктура. Цепочка Штурвала
(vcOrg → vcVdc → vcNsxt → [modify оргов/эдж] → k8sShturval) упирается в две операции modify, которые
провайдер сейчас выразить не может: в схеме tf-ресурса их параметров нет (схема строится только из create).
Ручной ЛК и скрипт отклонены — это не IaC. Единственный каноничный путь — отдельные tf-ресурсы под
модификации (как сделано в провайдере VMware Cloud Director, прецедент в папке !/),
плюс желательно, чтобы платформа отдавала через API выводимые значения (ipSpaceName), которые юзер знать не может.
Часть прежних «блокеров» оказалась ложной — см. §7, это критично.
1. Задача
Развернуть Штурвал (k8s) целиком через Terraform, с корректным apply/plan/destroy:
vcOrg -> create (в нашем случае орг уже создана вручную и НЕ в state)
vcVdc -> create
vcNsxt -> create (Edge)
------------------------------
vcOrg -> modify (аллокация внешних IP: vIPConfigure)
vcNsxt -> modify (включить SNAT, указать внешний IP из vcOrg: ipSpaceName)
------------------------------
k8sShturval -> create
Операции строго последовательны. Проблема: между nsxt.create и shturval.create стоят два modify,
которые в один tf-ресурс не укладываются.
2. Позиции участников (Telegram 2026-09-23)
| Кто | Позиция |
|---|---|
| Владимир (наш) | Пытается сделать всё терраформом. create — ок, modify — «просто так не получится, надо создавать дополнительные ресурсы-модификаторы». Сомневался: может, руками в ЛК или скриптом. |
| Георгий | Основной запрос клиента — IaC. Ручной ЛК/скрипт «совсем не подойдёт». Правильно указал порядок: сначала nsxt, потом квота на оргу. |
| Дмитрий | Хочет «terraform apply одного ямлика со всей инфрой — и всё». Спрашивал, как это реализовано в провайдере Cloud Director из провайдерской УЗ. |
| Виталий | Дал 3 tf-файла (vmware_org.tf, vdc.tf, network.tf.tmpl) — официальный провайдер Cloud Director. Ключевое: ipSpace → providerGateway → providerVdc (цепочка, которую юзер не знает), «квоту делаем через API на оргу, т.к. эджей много, а орга одна», «при создании параметры подкладываются», «в организации один T0». |
3. Подтверждённые факты (с источниками)
- Схема tf-ресурса строится ТОЛЬКО из
create(генераторTOOLS/resource-generator). → modify-only параметры в схему не попадают. vIPConfigure(vc_org, modify id 207, param id 662,array-map-fixed, sub:name=39,count=40) есть только в modify. Вcreate(id 136) — толькоresourceRealm(418),organizationType(556),orgSuffix(1125). Файл:generated/dev/resources_yaml/19_vc_org.yaml.ipSpaceName(vc_nsxt, modify id 111, param id 372, string, required false) есть только в modify. Вcreate(id 10) —vdcUid,needEnableAVI(340),virtualServicesCount(341),qosProfile(825),routedNetConfiguration(1110). Файл:generated/dev/resources_yaml/22_vc_nsxt.yaml.vIPConfigure— replace-семантика, НЕ накопительная. Повторный modify с тем же count не задваивает (1→1), работает вверх/вниз/до 0,count=0принимается (несмотря наminvalue:1), live читается изstate.params. Источник:docs/ORG_IP_MODIFIER_TEST_2026-09-22.md(проверено на стенде DEV_STAND/FullPipe, провайдер 2.0.9).ipSpaceName— выводимое значение: цепочкаproviderVdc → providerGateway → ipSpace, юзер его не знает. Платформа сейчас «подкладывает» недостающие параметры при создании пустой орги. Список доступных ipSpace в статической выгрузке (/instanceOperations/default/{id}) — пустой, виден только в ЛК/живом инстансе. (Виталий + форензика)- Допущение платформы: в организации один T0/провайдер-шлюз. Рост T0 отложен, но при нём схема сломается.
- Доступ к значению modify-параметра: live берётся из
GET /instances/{uid}→state.params, а НЕ изcfsParams.paramValue(это сохранённый дефолт формы от прошлых прогонов, см.dtCreatedв HAR). - Flow modify (HAR
org_enough_.har):POST /instanceOperations {instanceUid, operation:"modify"}→POST /instanceOperationCfsParams {paramValue, instanceOperationUid, svcOperationCfsParamId}→POST /instanceOperations/{opUid}/validate-cfs→POST /instanceOperations/{opUid}/run. - Прецедент (VCD, папка
!/): та же цепочка делается отдельными ресурсами сdepends_on:vcd_nsxt_alb_settings(count = var.alb_enable ? 1 : 0),vcd_nsxt_alb_edgegateway_service_engine_group(reserved_virtual_services),vcd_network_routed_v2,vcd_ip_space_custom_quota(на оргу). Приём «включено/выключено» = существование ресурса; inverse = удаление ресурса. - Nubes — надстройка над Cloud Director. Наши
vcOrg/vcVdc/vcNsxtсоздают объекты в VCD. Провайдер Nubes — обёртка над API Nubes, отдельный от официальногоterraform-provider-vcd.
4. Почему «просто добавить поле» / «насильно в state» / «скрипт» — не работает
- Добавить поле в .tf → падает на
plan: атрибута нет в схеме (см. §3.1). - Terraform не может внутри одного ресурса сделать «create → через N шагов modify».
Декларативный Update требует желаемого состояния;
ipSpaceName— это включение SNAT, а не значение поля. - Вписать в tfstate нельзя: state валидируется по схеме провайдера, а «записанное» состояние ≠ реальность
(получишь чистый
planпри сломанной инфраструктуре).null_resource/terraform_data+local-execдаёт только факт выполнения, не состояние. - Ручной ЛК / скрипт вне tf — отклонено: это не IaC (нет версионирования, воспроизводимости, дрейфа, отката).
- Правка провайдера «по-старому» (метки
kind: modifierв YAML + реестр вyaml-generator) — отменённый заход, см. §7.
5. Каноничное решение (что делать)
Два независимых требования — нужны оба:
- Отдельные tf-ресурсы под
modify(наша сторона): e.g.nubes_org_ip_allocation(vIPConfigure),nubes_nsxt_network(needEnableAVI/virtualServicesCount/ipSpaceName/routedNetConfiguration), привязка черезdepends_onк орге/эджу.Read= читать родителя (state.params),Delete= обратный modify (count=0/needEnableAVI=false/ipSpaceName="no-needed"),Create/Update=modifyс параметрами.
- Доступ к выводимым значениям через API (сторона платформы): динамические
valueList+ цепочкаproviderVdc → providerGateway → ipSpace. Иначе юзер подсматривает в ЛК (ручной ввод как временный долг допустим, но поле надо делатьOptional+Computed, чтобы позже включить автоподстановку без breaking change).
Дизайн-требования, заложить сразу:
ip_space_name→Optional + Computed;- optional селектор шлюза (
t0_id/provider_gateway) — чтобы рост T0 не сломал схему; - не тащить доменные метки в универсальный YAML (см. §7).
6. Что можно делать уже сейчас, не дожидаясь платформы
vIPConfigure(аллокация IP на оргу) — можно делать начисто: блокеров нет, replace-семантика подтверждена тестом, Read/Delete выражаются черезstate.paramsиcount=0.needEnableAVI/virtualServicesCount— выразимы (есть и в create, и в modify).ipSpaceName— единственное, что упирается в платформу; временно — ввод юзером (значение он и так смотрит в ЛК).routedNetConfiguration— есть в create (1110) и modify (1112), выразимо.
Не решено (требует решения до кода):
- откуда генератор берёт список доменных ресурсов (это не данные API, а доменное знание — то самое место,
где раньше был реестр в
yaml-generator). Форму выбрать осознанно: явный список vs отдельный вход. - какие шаги вообще остаются на провайдерском (облачном) уровне, а какие отдаются тенанту (квота ipSpace / ALB — возможно, это уровень облака, и тогда в клиентский tf они не входят).
7. ⚠️ Исправленные ошибки (НЕ повторять!)
- Ложный факт «
vIPConfigureнакопительный». Был протащен в промпт для Opus как «подтверждённый», из-за чего Opus построил вывод «накопительный API несовместим с декларативной моделью» и объявил два «блокера» (Read счётчика, адресное освобождение). Оба ложны — тестORG_IP_MODIFIER_TEST_2026-09-22.mdдоказывает идемпотентность и работу в обе стороны. Документы исправлены. - Прежняя repo-память (
modifier-gotchas.md) содержала устаревшие утверждения (эпоха 09-21/22):kind: modifier,delete_strategy,nubes_vc_nsxt_network, «у vc_nsxt нет instance-modify», «Update = no-op». Файл перезаписан актуальными фактами. НЕ использовать старую формулировку. - Старые «модификаторы» были написаны и даже работали (09-22), но заход признан негодным: доменную логику вшили в универсальный генератор (метки в YAML). Соответствующие документы помечены баннером LEGACY.
8. Карта файлов
АКТУАЛЬНО (источник истины):
docs/CHAT_RESUME_IAC_2026-09-24.md← этот файлdocs/SHTURVAL_IAC_MODIFY_ANALYSIS_2026-09-23.md— анализ, варианты A–E, мнениеdocs/OPUS_ANSWER_IAC_SHTURVAL_MODIFY_2026-09-23.md— ответ Opus + поправки (ложные блокеры сняты)docs/ORG_IP_MODIFIER_TEST_2026-09-22.md— проверенные факты по vIPConfiguredocs/prompts/prompt_for_opus_iac_shturval_modify.md— промпт (факты исправлены)generated/dev/resources_yaml/19_vc_org.yaml,22_vc_nsxt.yaml— спеки (факты по операциям/параметрам)HAR/org_enough_.har,HAR/org2.har,HAR/edge_.har— live-семантика modify!/— прецедент Cloud Director (3 файлаvcd_*), НЕ наш код
LEGACY (история, НЕ источник истины):
PLAN_modifier_redesign.md⛔ (баннер добавлен)docs/60_strategy/modifier_resources_ideology_and_specification.md⛔ (баннер добавлен)docs/inverse_rollback_analysis_2026-09-23.mdprompt_for_opus_modifier_global_architecture.md,prompt_for_opus_modifier_review_2.md(корень)docs/prompts/prompt_for_opus_modifier_*.md,docs/prompts/prompt_for_opus_modifiable_architecture.mdHISTORY/OPUS/2026-09-22_modifier_*.mdPLAN_regenerate_providers_0.0.1.md— перекрытPLAN_FLASH_reversion_cleanup.md(0.0.1 объявлен легаси)
Примечание:
docs/ORG_IP_MODIFIER_TEST_2026-09-22.md— актуален (это отчёт по проверке, не план).
Инфра-контекст:
TOOLS/config/<стенд>/profile.env→NUBES_API_ENDPOINT,TOKEN_FILEVERSIONS.md— залитые версии (DEV на 09-22 = 2.0.13; вgenerated/dev/provider_build/лежат 2.0.17 — расхождение)
9. Развилка (ждёт решения)
| Вариант | Суть | Вердикт |
|---|---|---|
| A | Отдельные tf-ресурсы под modify (+ позже data-source для ipSpace) | канон; реализуемо сейчас для vIPConfigure |
| B | То же, но значения вводит юзер вручную | приемлемый временный долг при Optional+Computed |
| C | Ждать новых спеков платформы | часть работ всё равно можно начать сейчас |
| D | Ручной ЛК / скрипт вне tf | ❌ отклонено (требование IaC) |
| E | Пресеты/дефолтное окружение | снижает боль на старте, IaC не заменяет |
Не принято: делать ли modify-ресурсы доменными «руками» (и как их перечислять в генераторе) —
вопрос архитектуры; и что из шагов остаётся за облаком.
10. Открытые вопросы к людям
- Георгию/продукту: какие шаги цепочки — тенантские, а какие — уровень облака (квота ipSpace, ALB)? От этого зависит объём ресурсов в клиентском tf.
- Виталию (платформа): можете отдавать через API (а) динамические списки значений (
ipSpace), (б) цепочкуproviderVdc → providerGateway → ipSpace? - Виталию: файлы
!/— ваш инструмент провижининга от провайдерской УЗ или справочный пример? (в диалоге он сказал только «это провайдер от клауд директора») - Команде: откуда генератор берёт список доменных ресурсов-модификаций (форма решения, без меток в YAML).