terraform-contour-mirror/live/terragrunt.hcl
Kochetkov S a64eee3e4f
Some checks failed
Terraform Terragrunt (contour) / plan (push) Has been cancelled
Terraform Terragrunt (contour) / apply (push) Has been cancelled
Terraform Terragrunt (contour) / validate (push) Has been cancelled
++ fall back to provider defaults when contour vars are set but empty
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-08-12 12:17:38 +03:00

139 lines
6.3 KiB
HCL
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Contour root — in-cluster backend + providers.
#
# This branch (`contour`) serves ALL closed contours. Backend state lives in the
# contour MinIO; the concrete contour is selected by INFRA_ENV. Providers target
# in-cluster services (no managed YC). Infra-service admin creds are read from
# Vault by a workflow step and injected as env vars (see .gitea/workflows) —
# providers pick them up via get_env, so there is no cross-provider data-source
# ordering dependency on the vault-secrets stack.
# get_env подставляет дефолт только когда переменная НЕ ЗАДАНА. Воркфлоу
# маппит vars.* в env: безусловно, поэтому на контуре, где такая переменная
# в Gitea не заведена, она приходит пустой строкой - дефолт не срабатывает, и
# незакавыченные поля (port, tls_enabled) рендерятся как "port =" с пустой
# правой частью, что валит terraform init на Invalid expression.
locals {
pg_host = get_env("PG_ADMIN_HOST", "") != "" ? get_env("PG_ADMIN_HOST", "") : "postgresql.postgresql.svc.cluster.local"
pg_port = get_env("PG_ADMIN_PORT", "") != "" ? get_env("PG_ADMIN_PORT", "") : "5432"
pg_user = get_env("PG_ADMIN_USER", "") != "" ? get_env("PG_ADMIN_USER", "") : "postgres"
kafka_bootstrap = get_env("KAFKA_BOOTSTRAP", "") != "" ? get_env("KAFKA_BOOTSTRAP", "") : "kafka-kafka-contour-controller-0.kafka-kafka-contour-controller-headless.kafka.svc.cluster.local:9094"
kafka_tls = get_env("KAFKA_TLS_ENABLED", "") != "" ? get_env("KAFKA_TLS_ENABLED", "") : "false"
kafka_mechanism = get_env("KAFKA_SASL_MECHANISM", "") != "" ? get_env("KAFKA_SASL_MECHANISM", "") : "plain"
kafka_user = get_env("KAFKA_ADMIN_USER", "") != "" ? get_env("KAFKA_ADMIN_USER", "") : "inter_broker_user"
vault_k8s_role = get_env("VAULT_K8S_ROLE", "") != "" ? get_env("VAULT_K8S_ROLE", "") : "terraform"
vault_k8s_auth = get_env("VAULT_K8S_AUTH_BACKEND", "") != "" ? get_env("VAULT_K8S_AUTH_BACKEND", "") : "kubernetes"
}
remote_state {
backend = "s3"
generate = {
path = "backend.tf"
if_exists = "overwrite_terragrunt"
}
config = {
endpoint = get_env("TF_STATE_S3_ENDPOINT", "")
bucket = get_env("TF_STATE_S3_BUCKET", "")
key = "${path_relative_to_include()}/terraform.tfstate"
region = get_env("TF_STATE_S3_REGION", "ru-central1")
access_key = get_env("S3_ACCESS_KEY", get_env("AWS_ACCESS_KEY_ID", ""))
secret_key = get_env("S3_SECRET_KEY", get_env("AWS_SECRET_ACCESS_KEY", ""))
skip_region_validation = true
skip_credentials_validation = true
skip_metadata_api_check = true
skip_bucket_root_access = true
force_path_style = true
}
}
generate "provider" {
path = "provider.tf"
if_exists = "overwrite_terragrunt"
contents = <<EOF_PROVIDER
%{if path_relative_to_include() == "rabbitmq" && get_env("INFRA_ENV", "") == "brusnika-stage"~}
# rabbitmq module >= v1.0.0 (terraform-modules/rabbitmq, brusnika-stage pilot)
# declares its own required_providers and provider "rabbitmq" block, and this
# unit uses no other provider - the whole shared block below is intentionally
# skipped here to avoid "Duplicate required providers configuration".
%{else~}
terraform {
required_version = ">= 1.5.0"
required_providers {
kubernetes = { source = "hashicorp/kubernetes", version = "~> 2.23" }
vault = { source = "hashicorp/vault", version = "~> 4.2" }
kafka = { source = "Mongey/kafka", version = "0.10.4" }
postgresql = { source = "cyrilgdn/postgresql", version = "~> 1.21" }
rabbitmq = { source = "cyrilgdn/rabbitmq", version = "~> 1.8" }
minio = { source = "aminueza/minio", version = "~> 2.0" }
random = { source = "hashicorp/random", version = "~> 3.1" }
tls = { source = "hashicorp/tls", version = "~> 4.0" }
}
}
variable "kubeconfig_path" {
type = string
default = ""
}
variable "kube_context" {
type = string
default = ""
}
provider "kubernetes" {
# KUBECONFIG is set unconditionally at job level for the external-runner case
# (see .gitea/workflows/terraform.yml "Prepare kubeconfig"); on an in-cluster
# runner that file is never written (no KUBECONFIG_B64), so fileexists() must
# gate this - a non-empty path alone isn't enough, else the provider tries to
# read a file that was never created and falls over instead of using the pod
# ServiceAccount / in-cluster config.
config_path = var.kubeconfig_path != "" && fileexists(var.kubeconfig_path) ? var.kubeconfig_path : null
config_context = var.kubeconfig_path != "" && fileexists(var.kubeconfig_path) ? var.kube_context : null
}
# Vault: static VAULT_TOKEN if provided, else in-cluster k8s auth by the runner SA.
provider "vault" {
%{if get_env("VAULT_TOKEN", "") == ""~}
auth_login_kubernetes {
role = "${local.vault_k8s_role}"
mount_path = "auth/${local.vault_k8s_auth}"
}
%{endif~}
}
# In-cluster PostgreSQL (admin). Password injected from Vault secrets/postgresql/admin.
provider "postgresql" {
host = "${local.pg_host}"
port = ${local.pg_port}
username = "${local.pg_user}"
password = "${get_env("PG_ADMIN_PASSWORD", "")}"
sslmode = "disable"
superuser = false
}
# In-cluster Kafka (Bitnami). Admin = inter_broker super-user from Vault secrets/kafka/bootstrap.
provider "kafka" {
bootstrap_servers = ["${local.kafka_bootstrap}"]
tls_enabled = ${local.kafka_tls}
%{if get_env("KAFKA_CA_CERT", "") != ""~}
ca_cert = <<-EOT
${get_env("KAFKA_CA_CERT", "")}
EOT
%{endif~}
%{if get_env("KAFKA_ADMIN_PASSWORD", "") != ""~}
sasl_mechanism = "${local.kafka_mechanism}"
sasl_username = "${local.kafka_user}"
sasl_password = "${get_env("KAFKA_ADMIN_PASSWORD", "")}"
%{endif~}
}
# RabbitMQ provider is configured INSIDE modules/rabbitmq (from its management_*
# inputs), so it is intentionally NOT generated here to avoid a duplicate config.
# MinIO provider is configured INSIDE modules/minio-buckets (endpoint from
# infrastructure.yaml, admin creds from Vault via the s3 unit), so it is not
# generated here.
%{endif~}
EOF_PROVIDER
}