CI: валидировать custom resources по схемам CRD развёрнутых версий #400

Open
opened 2026-10-12 16:28:14 +00:00 by hermes · 0 comments
Collaborator

Что произошло

После мержа #397 и #398 пайплайн был зелёным, а в кластере обе Kustomization env — в grachevko и grachevaeu — встали:

ExternalSecret/grachevko/hermes-managed-env dry-run failed: failed to create typed patch object
(grachevko/hermes-managed-env; external-secrets.io/v1, Kind=ExternalSecret):
.spec.data[0].sourceRef.kind: field not declared in schema

spec.data[].sourceRef в External Secrets — это StoreSourceRef: ровно одно из storeRef и generatorRef (maxProperties: 1), а kind и name живут внутри storeRef. В манифесте они стояли прямо под sourceRef, то есть объект несёт два необъявленных свойства: API-сервер его отклоняет, env не становится Ready, за ней ждёт hermes, и вся смёрженная работа в кластер не доезжает (файловый менеджер, переехавший в под агента, ждёт ту же цепочку). Фикс — #399.

Почему CI пропустил

  • flate test all — ✓ и на сломанной форме, и на исправленной: CRD External Secrets ему неизвестны (проверено на обеих ветках, разница только в недоступном источнике network/k8s-gateway, codeberg отвечает 503).
  • Flux Local — значения HelmRelease сверяются с values.schema.json чарта, тела custom resources не проверяет никто.

Что добавить

Шаг, который валидирует отрендеренные custom resources по схемам CRD развёрнутых версий, а не по встроенному набору:

  1. собрать схемы из пинов репозитория: для External Secrets — deploy/crds/bundle.yaml тега v2.12.0 (версия чарта — в kubernetes/apps/security/external-secrets/app/ocirepository.yaml);
  2. прогнать kubeconform с -schema-location, указывающим на этот bundle (либо kubectl apply --dry-run=server на эфемерном кластере).

Проверка ловит это без кластера: у spec.data[].sourceRef объявлены только storeRef и generatorRef при maxProperties: 1, поэтому плоская форма даёт и неизвестные поля, и второе свойство. Тот же шаг закрывает остальные CR'ы репозитория (ExternalSecret, SecretStore, генераторы, OCIRepository, PocketID*).

Критерий приёмки

  • на манифесте из #397 (плоская форма) шаг краснеет;
  • на манифесте после #399 — зелёный;
  • в кластер не уходит объект, про который API-сервер говорит field not declared in schema.

Связь

Парный issue — #401: он про правила admission-вебхука, этот — про схемы CRD; класс ошибки один (манифест проходит локальный рендер и отвергается API-сервером), обвязка проверки общая.

## Что произошло После мержа #397 и #398 пайплайн был зелёным, а в кластере обе Kustomization `env` — в `grachevko` и `grachevaeu` — встали: ``` ExternalSecret/grachevko/hermes-managed-env dry-run failed: failed to create typed patch object (grachevko/hermes-managed-env; external-secrets.io/v1, Kind=ExternalSecret): .spec.data[0].sourceRef.kind: field not declared in schema ``` `spec.data[].sourceRef` в External Secrets — это `StoreSourceRef`: ровно одно из `storeRef` и `generatorRef` (`maxProperties: 1`), а `kind` и `name` живут внутри `storeRef`. В манифесте они стояли прямо под `sourceRef`, то есть объект несёт два необъявленных свойства: API-сервер его отклоняет, `env` не становится Ready, за ней ждёт `hermes`, и вся смёрженная работа в кластер не доезжает (файловый менеджер, переехавший в под агента, ждёт ту же цепочку). Фикс — #399. ## Почему CI пропустил - `flate test all` — `✓` и на сломанной форме, и на исправленной: CRD External Secrets ему неизвестны (проверено на обеих ветках, разница только в недоступном источнике `network/k8s-gateway`, codeberg отвечает 503). - `Flux Local` — значения HelmRelease сверяются с `values.schema.json` чарта, тела custom resources не проверяет никто. ## Что добавить Шаг, который валидирует отрендеренные custom resources по схемам CRD **развёрнутых** версий, а не по встроенному набору: 1. собрать схемы из пинов репозитория: для External Secrets — `deploy/crds/bundle.yaml` тега `v2.12.0` (версия чарта — в `kubernetes/apps/security/external-secrets/app/ocirepository.yaml`); 2. прогнать `kubeconform` с `-schema-location`, указывающим на этот bundle (либо `kubectl apply --dry-run=server` на эфемерном кластере). Проверка ловит это без кластера: у `spec.data[].sourceRef` объявлены только `storeRef` и `generatorRef` при `maxProperties: 1`, поэтому плоская форма даёт и неизвестные поля, и второе свойство. Тот же шаг закрывает остальные CR'ы репозитория (`ExternalSecret`, `SecretStore`, генераторы, `OCIRepository`, `PocketID*`). ## Критерий приёмки - на манифесте из #397 (плоская форма) шаг краснеет; - на манифесте после #399 — зелёный; - в кластер не уходит объект, про который API-сервер говорит `field not declared in schema`. ## Связь Парный issue — #401: он про правила admission-вебхука, этот — про схемы CRD; класс ошибки один (манифест проходит локальный рендер и отвергается API-сервером), обвязка проверки общая.
Sign in to join this conversation.
No labels
No milestone
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
grachevko/home-ops#400
No description provided.