mirror of
https://gitlab.sarex.io/infra/terraform-contour-mirror.git
synced 2026-08-05 18:31:00 +03:00
++ fail secrets plan on incomplete depends_on instead of writing empty data
This commit is contained in:
parent
c7e04cb836
commit
12e406acad
@ -247,6 +247,47 @@ locals {
|
||||
)
|
||||
}
|
||||
|
||||
# Явный контракт для типов с обязательным depends_on. Раньше отсутствующее
|
||||
# или неполное depends_on тихо резолвилось через try(..., "") в несуществующий
|
||||
# ключ outputs-карты, outputs_by_secret[name] становился null, и секрет молча
|
||||
# создавался ПУСТЫМ (без host/port/username/password) - без единой ошибки в
|
||||
# плане. Для type=yc_sa такой защиты не было вообще: null-источник просто не
|
||||
# проверялся, и итоговые access_key/secret_key/service_account_id молча
|
||||
# оставались пустыми строками. Здесь это - явная ошибка плана. Секреты с
|
||||
# готовым статическим data (adopt/1:1) под контракт не подпадают: они не
|
||||
# резолвят depends_on вообще.
|
||||
secrets_contract_errors = {
|
||||
for name, secret in local.secrets_map : name => (
|
||||
length(try(secret.data, {})) > 0 ? "" :
|
||||
secret.type == "database" || secret.type == "database_url" ? (
|
||||
try(secret.depends_on.cluster, "") == "" || try(secret.depends_on.db, "") == "" || try(secret.depends_on.user, "") == ""
|
||||
? "type=${secret.type} requires depends_on.cluster, depends_on.db, depends_on.user (got cluster=${try(secret.depends_on.cluster, "")}, db=${try(secret.depends_on.db, "")}, user=${try(secret.depends_on.user, "")})"
|
||||
: ""
|
||||
) :
|
||||
secret.type == "valkey" ? (
|
||||
local.valkey_dependency_keys[name].cluster == "" || local.valkey_dependency_keys[name].user == ""
|
||||
? "type=valkey requires depends_on.cluster (or valkey_cluster) and depends_on.user (or valkey_user)"
|
||||
: ""
|
||||
) :
|
||||
secret.type == "rabbitmq" ? (
|
||||
try(secret.depends_on.rabbitmq_vhost, try(secret.depends_on.vhost, "")) == "" || try(secret.depends_on.rabbitmq_user, try(secret.depends_on.user, "")) == ""
|
||||
? "type=rabbitmq requires depends_on.vhost (or rabbitmq_vhost) and depends_on.user (or rabbitmq_user)"
|
||||
: ""
|
||||
) :
|
||||
secret.type == "kafka" ? (
|
||||
try(coalesce(secret.depends_on.kafka_ref, secret.depends_on.cluster_ref, secret.depends_on.cluster), "") == "" || try(coalesce(secret.depends_on.kafka_user, secret.depends_on.user), "") == ""
|
||||
? "type=kafka requires depends_on.kafka_ref (or cluster_ref/cluster) and depends_on.kafka_user (or user)"
|
||||
: ""
|
||||
) :
|
||||
secret.type == "yc_sa" ? (
|
||||
try(secret.depends_on.service_account, "") == ""
|
||||
? "type=yc_sa requires depends_on.service_account"
|
||||
: ""
|
||||
) :
|
||||
""
|
||||
)
|
||||
}
|
||||
|
||||
# Если для секрета заданы явные значения (data) - используем их 1:1,
|
||||
# иначе собираем data из outputs/custom/constant/random как обычно.
|
||||
secrets_data = {
|
||||
@ -326,6 +367,10 @@ resource "kubernetes_secret" "with_ignore" {
|
||||
lifecycle {
|
||||
# Игнорируем data, type и metadata чтобы не было phantom updates
|
||||
ignore_changes = [data, type, metadata, wait_for_service_account_token]
|
||||
precondition {
|
||||
condition = local.secrets_contract_errors[each.key] == ""
|
||||
error_message = "Secret contract violation for ${each.key}: ${local.secrets_contract_errors[each.key]}"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -350,6 +395,10 @@ resource "kubernetes_secret" "without_ignore" {
|
||||
lifecycle {
|
||||
# type и metadata игнорируем чтобы не было phantom updates
|
||||
ignore_changes = [type, metadata, wait_for_service_account_token]
|
||||
precondition {
|
||||
condition = local.secrets_contract_errors[each.key] == ""
|
||||
error_message = "Secret contract violation for ${each.key}: ${local.secrets_contract_errors[each.key]}"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -363,4 +412,11 @@ resource "vault_kv_secret_v2" "this" {
|
||||
data_json = jsonencode(merge(each.value.data, {
|
||||
for key, config in each.value.random_keys : key => random_password.secrets["${each.key}:${key}"].result
|
||||
}))
|
||||
|
||||
lifecycle {
|
||||
precondition {
|
||||
condition = local.secrets_contract_errors[each.key] == ""
|
||||
error_message = "Secret contract violation for ${each.key}: ${local.secrets_contract_errors[each.key]}"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Loading…
Reference in New Issue
Block a user