Add context support to artifact-registry, net-lb-app-int, cloudsql modules (#3784)
* artifact-registry * net-lb-app-int * copyright * cloudsql * fix linting
This commit is contained in:
committed by
GitHub
parent
8c07d09eab
commit
a6c284a273
105
GEMINI.md
105
GEMINI.md
@@ -53,16 +53,25 @@ Cloud Foundation Fabric is a comprehensive suite of Terraform modules and end-to
|
||||
Always format code and update documentation before committing.
|
||||
|
||||
```bash
|
||||
# Format Terraform code
|
||||
terraform fmt -recursive
|
||||
# Format Terraform code (check then fix)
|
||||
terraform fmt -check -recursive modules/<module-name>
|
||||
terraform fmt -recursive modules/<module-name>
|
||||
|
||||
# Update module documentation (variables/outputs tables)
|
||||
./tools/tfdoc.py modules/<module-name>
|
||||
# Check README consistency (variables table must match variables.tf)
|
||||
python3 tools/check_documentation.py modules/<module-name>
|
||||
|
||||
# Run all lint checks (wraps pre-commit hooks)
|
||||
./tools/lint.sh
|
||||
# Regenerate README variables/outputs tables when check fails
|
||||
python3 tools/tfdoc.py --replace modules/<module-name>
|
||||
|
||||
# YAML linting
|
||||
yamllint -c .yamllint --no-warnings <yaml-files>
|
||||
|
||||
# License/boilerplate check
|
||||
python3 tools/check_boilerplate.py --scan-files <files>
|
||||
```
|
||||
|
||||
**Common gotcha — unsorted variables (`[SV]` error):** `check_documentation.py` requires variables in `variables.tf` to be in strict alphabetical order. When adding a new variable, insert it at the correct alphabetical position, not at the top of the file.
|
||||
|
||||
#### 2. Testing
|
||||
|
||||
Tests are written in Python using `pytest` and the [`tftest`](https://pypi.org/project/tftest/) library.
|
||||
@@ -86,6 +95,90 @@ pytest tests/examples/test_plan.py
|
||||
* **Commits:** Atomic commits with clear messages.
|
||||
* **Docs:** Do not manually edit the variables/outputs tables in READMEs; use `tfdoc.py`.
|
||||
|
||||
## Adding Context Support to a Module
|
||||
|
||||
Several modules support symbolic variable interpolation via a `context` variable. This allows callers to pass symbolic references like `"$project_ids:myprj"` instead of raw values, which get resolved at plan time.
|
||||
|
||||
### Pattern
|
||||
|
||||
**1. Add a `context` variable** in `variables.tf` at its alphabetical position. Use keys relevant to the module — standard keys are `locations`, `networks`, `project_ids`, `subnets`; module-specific keys may be added (e.g., `kms_keys`, `artifact_registries`, `secrets`):
|
||||
|
||||
```hcl
|
||||
variable "context" {
|
||||
description = "Context-specific interpolations."
|
||||
type = object({
|
||||
kms_keys = optional(map(string), {})
|
||||
locations = optional(map(string), {})
|
||||
networks = optional(map(string), {})
|
||||
project_ids = optional(map(string), {})
|
||||
})
|
||||
default = {}
|
||||
nullable = false
|
||||
}
|
||||
```
|
||||
|
||||
**2. Build `ctx` and `ctx_p` locals** in `main.tf`. If the module has IAM condition support, exclude `condition_vars` from the flattening (it is passed directly to `templatestring()`):
|
||||
|
||||
```hcl
|
||||
locals {
|
||||
ctx = {
|
||||
for k, v in var.context : k => {
|
||||
for kk, vv in v : "${local.ctx_p}${k}:${kk}" => vv
|
||||
} # add: if k != "condition_vars" — only when condition_vars is a key
|
||||
}
|
||||
ctx_p = "$"
|
||||
project_id = lookup(local.ctx.project_ids, var.project_id, var.project_id)
|
||||
region = lookup(local.ctx.locations, var.region, var.region)
|
||||
}
|
||||
```
|
||||
|
||||
**3. Apply lookups in resources.** Three patterns:
|
||||
|
||||
```hcl
|
||||
# Simple field
|
||||
project = local.project_id
|
||||
|
||||
# Nullable field (null must stay null, not looked up)
|
||||
encryption_key_name = (
|
||||
var.encryption_key_name == null
|
||||
? null
|
||||
: lookup(local.ctx.kms_keys, var.encryption_key_name, var.encryption_key_name)
|
||||
)
|
||||
|
||||
# Deeply optional nested field
|
||||
private_network = (
|
||||
try(var.network_config.psa_config.private_network, null) == null
|
||||
? null
|
||||
: lookup(local.ctx.networks, var.network_config.psa_config.private_network,
|
||||
var.network_config.psa_config.private_network)
|
||||
)
|
||||
|
||||
# Per-element list
|
||||
nat_subnets = [for s in var.nat_subnets : lookup(local.ctx.subnets, s, s)]
|
||||
```
|
||||
|
||||
**4. Long ternaries** are wrapped in parentheses with condition and branches on separate lines:
|
||||
|
||||
```hcl
|
||||
ip_address = (
|
||||
var.address == null
|
||||
? null
|
||||
: lookup(local.ctx.addresses, var.address, var.address)
|
||||
)
|
||||
```
|
||||
|
||||
### Tests
|
||||
|
||||
Add a `context` test alongside existing module tests:
|
||||
|
||||
- `tests/modules/<module_name>/tftest.yaml` — declare the module path and list `context:` under `tests:`
|
||||
- `tests/modules/<module_name>/context.tfvars` — provide all required module variables using symbolic references; include a `context` block with maps that resolve them
|
||||
- `tests/modules/<module_name>/context.yaml` — assert resolved (concrete) values in the plan output
|
||||
|
||||
### README example
|
||||
|
||||
Modify one existing README example (do not add a new one) to demonstrate context usage. The resolved values should match the existing inventory YAML so no inventory changes are needed.
|
||||
|
||||
## Architecture & Conventions
|
||||
|
||||
* **Variables:** Prefer object variables (e.g., `iam = { ... }`) over many individual scalar variables.
|
||||
|
||||
@@ -232,15 +232,27 @@ This module implements the same IAM interface than the other modules.
|
||||
You can choose one (and only one) of the three options below:
|
||||
|
||||
```hcl
|
||||
# Authoritative IAM bindings
|
||||
# Authoritative IAM bindings with context interpolation for project, location,
|
||||
# and IAM principals
|
||||
module "authoritative_iam" {
|
||||
source = "./fabric/modules/artifact-registry"
|
||||
project_id = "myproject"
|
||||
location = "europe-west1"
|
||||
project_id = "$project_ids:myproject"
|
||||
location = "$locations:ew1"
|
||||
name = "myregistry"
|
||||
format = { docker = { standard = {} } }
|
||||
context = {
|
||||
locations = {
|
||||
ew1 = "europe-west1"
|
||||
}
|
||||
iam_principals = {
|
||||
cicd-team = "group:cicd@example.com"
|
||||
}
|
||||
project_ids = {
|
||||
myproject = "myproject"
|
||||
}
|
||||
}
|
||||
iam = {
|
||||
"roles/artifactregistry.admin" = ["group:cicd@example.com"]
|
||||
"roles/artifactregistry.admin" = ["$iam_principals:cicd-team"]
|
||||
}
|
||||
}
|
||||
|
||||
@@ -300,21 +312,22 @@ module "additive_iam" {
|
||||
| name | description | type | required | default |
|
||||
|---|---|:---:|:---:|:---:|
|
||||
| [cleanup_policies](variables.tf#L17) | Object containing details about the cleanup policies for an Artifact Registry repository. | <code title="map(object({ action = string condition = optional(object({ tag_state = optional(string) tag_prefixes = optional(list(string)) older_than = optional(string) newer_than = optional(string) package_name_prefixes = optional(list(string)) version_name_prefixes = optional(list(string)) })) most_recent_versions = optional(object({ package_name_prefixes = optional(list(string)) keep_count = optional(number) })) })) default = null">map(object({…default = null</code> | ✓ | |
|
||||
| [format](variables.tf#L62) | Repository format. | <code title="object({ apt = optional(object({ remote = optional(object({ public_repository = string # "BASE path" disable_upstream_validation = optional(bool) upstream_credentials = optional(object({ username = string password_secret_version = string })) })) standard = optional(bool) })) docker = optional(object({ remote = optional(object({ public_repository = optional(string) common_repository = optional(string) custom_repository = optional(string) disable_upstream_validation = optional(bool) upstream_credentials = optional(object({ username = string password_secret_version = string })) })) standard = optional(object({ immutable_tags = optional(bool) })) virtual = optional(map(object({ repository = string priority = number }))) })) kfp = optional(object({ standard = optional(bool) })) generic = optional(object({ standard = optional(bool) })) go = optional(object({ standard = optional(bool) })) googet = optional(object({ standard = optional(bool) })) maven = optional(object({ remote = optional(object({ public_repository = optional(string) custom_repository = optional(string) disable_upstream_validation = optional(bool) upstream_credentials = optional(object({ username = string password_secret_version = string })) })) standard = optional(object({ allow_snapshot_overwrites = optional(bool) version_policy = optional(string) })) virtual = optional(map(object({ repository = string priority = number }))) })) npm = optional(object({ remote = optional(object({ public_repository = optional(string) custom_repository = optional(string) disable_upstream_validation = optional(bool) upstream_credentials = optional(object({ username = string password_secret_version = string })) })) standard = optional(bool) virtual = optional(map(object({ repository = string priority = number }))) })) python = optional(object({ remote = optional(object({ public_repository = optional(string) custom_repository = optional(string) disable_upstream_validation = optional(bool) upstream_credentials = optional(object({ username = string password_secret_version = string })) })) standard = optional(bool) virtual = optional(map(object({ repository = string priority = number }))) })) yum = optional(object({ remote = optional(object({ public_repository = string # "BASE path" disable_upstream_validation = optional(bool) upstream_credentials = optional(object({ username = string password_secret_version = string })) })) standard = optional(bool) })) })">object({…})</code> | ✓ | |
|
||||
| [location](variables.tf#L212) | Registry location. Use `gcloud beta artifacts locations list' to get valid values. | <code>string</code> | ✓ | |
|
||||
| [name](variables.tf#L217) | Registry name. | <code>string</code> | ✓ | |
|
||||
| [project_id](variables.tf#L222) | Registry project id. | <code>string</code> | ✓ | |
|
||||
| [format](variables.tf#L79) | Repository format. | <code title="object({ apt = optional(object({ remote = optional(object({ public_repository = string # "BASE path" disable_upstream_validation = optional(bool) upstream_credentials = optional(object({ username = string password_secret_version = string })) })) standard = optional(bool) })) docker = optional(object({ remote = optional(object({ public_repository = optional(string) common_repository = optional(string) custom_repository = optional(string) disable_upstream_validation = optional(bool) upstream_credentials = optional(object({ username = string password_secret_version = string })) })) standard = optional(object({ immutable_tags = optional(bool) })) virtual = optional(map(object({ repository = string priority = number }))) })) kfp = optional(object({ standard = optional(bool) })) generic = optional(object({ standard = optional(bool) })) go = optional(object({ standard = optional(bool) })) googet = optional(object({ standard = optional(bool) })) maven = optional(object({ remote = optional(object({ public_repository = optional(string) custom_repository = optional(string) disable_upstream_validation = optional(bool) upstream_credentials = optional(object({ username = string password_secret_version = string })) })) standard = optional(object({ allow_snapshot_overwrites = optional(bool) version_policy = optional(string) })) virtual = optional(map(object({ repository = string priority = number }))) })) npm = optional(object({ remote = optional(object({ public_repository = optional(string) custom_repository = optional(string) disable_upstream_validation = optional(bool) upstream_credentials = optional(object({ username = string password_secret_version = string })) })) standard = optional(bool) virtual = optional(map(object({ repository = string priority = number }))) })) python = optional(object({ remote = optional(object({ public_repository = optional(string) custom_repository = optional(string) disable_upstream_validation = optional(bool) upstream_credentials = optional(object({ username = string password_secret_version = string })) })) standard = optional(bool) virtual = optional(map(object({ repository = string priority = number }))) })) yum = optional(object({ remote = optional(object({ public_repository = string # "BASE path" disable_upstream_validation = optional(bool) upstream_credentials = optional(object({ username = string password_secret_version = string })) })) standard = optional(bool) })) })">object({…})</code> | ✓ | |
|
||||
| [location](variables.tf#L229) | Registry location. Use `gcloud beta artifacts locations list' to get valid values. | <code>string</code> | ✓ | |
|
||||
| [name](variables.tf#L234) | Registry name. | <code>string</code> | ✓ | |
|
||||
| [project_id](variables.tf#L239) | Registry project id. | <code>string</code> | ✓ | |
|
||||
| [cleanup_policy_dry_run](variables.tf#L38) | If true, the cleanup pipeline is prevented from deleting versions in this repository. | <code>bool</code> | | <code>null</code> |
|
||||
| [description](variables.tf#L44) | An optional description for the repository. | <code>string</code> | | <code>"Terraform-managed registry"</code> |
|
||||
| [enable_vulnerability_scanning](variables.tf#L50) | Whether vulnerability scanning should be enabled in the repository. | <code>bool</code> | | <code>null</code> |
|
||||
| [encryption_key](variables.tf#L56) | The KMS key name to use for encryption at rest. | <code>string</code> | | <code>null</code> |
|
||||
| [context](variables.tf#L44) | Context-specific interpolations. | <code title="object({ artifact_registries = optional(map(string), {}) condition_vars = optional(map(map(string)), {}) custom_roles = optional(map(string), {}) iam_principals = optional(map(string), {}) kms_keys = optional(map(string), {}) locations = optional(map(string), {}) project_ids = optional(map(string), {}) secrets = optional(map(string), {}) tag_values = optional(map(string), {}) })">object({…})</code> | | <code>{}</code> |
|
||||
| [description](variables.tf#L61) | An optional description for the repository. | <code>string</code> | | <code>"Terraform-managed registry"</code> |
|
||||
| [enable_vulnerability_scanning](variables.tf#L67) | Whether vulnerability scanning should be enabled in the repository. | <code>bool</code> | | <code>null</code> |
|
||||
| [encryption_key](variables.tf#L73) | The KMS key name to use for encryption at rest. | <code>string</code> | | <code>null</code> |
|
||||
| [iam](variables-iam.tf#L36) | IAM bindings in {ROLE => [MEMBERS]} format. | <code>map(list(string))</code> | | <code>{}</code> |
|
||||
| [iam_bindings](variables-iam.tf#L43) | Authoritative IAM bindings in {KEY => {role = ROLE, members = [], condition = {}}}. Keys are arbitrary. | <code title="map(object({ members = list(string) role = string condition = optional(object({ expression = string title = string description = optional(string) })) }))">map(object({…}))</code> | | <code>{}</code> |
|
||||
| [iam_bindings_additive](variables-iam.tf#L58) | Individual additive IAM bindings. Keys are arbitrary. | <code title="map(object({ member = string role = string condition = optional(object({ expression = string title = string description = optional(string) })) }))">map(object({…}))</code> | | <code>{}</code> |
|
||||
| [iam_by_principals](variables-iam.tf#L73) | Authoritative IAM binding in {PRINCIPAL => [ROLES]} format. Principals need to be statically defined to avoid cycle errors. Merged internally with the `iam` variable. | <code>map(list(string))</code> | | <code>{}</code> |
|
||||
| [labels](variables.tf#L206) | Labels to be attached to the registry. | <code>map(string)</code> | | <code>{}</code> |
|
||||
| [tag_bindings](variables.tf#L227) | Tag bindings for this repository, in key => tag value id format. | <code>map(string)</code> | | <code>{}</code> |
|
||||
| [universe](variables.tf#L234) | GCP universe where to deploy the project. The prefix will be prepended to the project id. | <code title="object({ package_domain = string prefix = string })">object({…})</code> | | <code>null</code> |
|
||||
| [labels](variables.tf#L223) | Labels to be attached to the registry. | <code>map(string)</code> | | <code>{}</code> |
|
||||
| [tag_bindings](variables.tf#L244) | Tag bindings for this repository, in key => tag value id format. | <code>map(string)</code> | | <code>{}</code> |
|
||||
| [universe](variables.tf#L251) | GCP universe where to deploy the project. The prefix will be prepended to the project id. | <code title="object({ package_domain = string prefix = string })">object({…})</code> | | <code>null</code> |
|
||||
|
||||
## Outputs
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright 2024 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -22,26 +22,32 @@ moved {
|
||||
resource "google_artifact_registry_repository_iam_binding" "authoritative" {
|
||||
provider = google-beta
|
||||
for_each = local.iam
|
||||
project = var.project_id
|
||||
location = google_artifact_registry_repository.registry.location
|
||||
project = local.project_id
|
||||
location = local.location
|
||||
repository = google_artifact_registry_repository.registry.name
|
||||
role = each.key
|
||||
members = each.value
|
||||
role = lookup(local.ctx.custom_roles, each.key, each.key)
|
||||
members = [
|
||||
for v in each.value : lookup(local.ctx.iam_principals, v, v)
|
||||
]
|
||||
}
|
||||
|
||||
# renamed as bindings2 to allow the moved block above
|
||||
resource "google_artifact_registry_repository_iam_binding" "bindings2" {
|
||||
for_each = var.iam_bindings
|
||||
project = var.project_id
|
||||
location = google_artifact_registry_repository.registry.location
|
||||
project = local.project_id
|
||||
location = local.location
|
||||
repository = google_artifact_registry_repository.registry.name
|
||||
role = each.value.role
|
||||
members = each.value.members
|
||||
role = lookup(local.ctx.custom_roles, each.value.role, each.value.role)
|
||||
members = [
|
||||
for v in each.value.members : lookup(local.ctx.iam_principals, v, v)
|
||||
]
|
||||
|
||||
dynamic "condition" {
|
||||
for_each = each.value.condition == null ? [] : [""]
|
||||
content {
|
||||
expression = each.value.condition.expression
|
||||
expression = templatestring(
|
||||
each.value.condition.expression, var.context.condition_vars
|
||||
)
|
||||
title = each.value.condition.title
|
||||
description = each.value.condition.description
|
||||
}
|
||||
@@ -50,16 +56,20 @@ resource "google_artifact_registry_repository_iam_binding" "bindings2" {
|
||||
|
||||
resource "google_artifact_registry_repository_iam_member" "members" {
|
||||
for_each = var.iam_bindings_additive
|
||||
project = var.project_id
|
||||
location = google_artifact_registry_repository.registry.location
|
||||
project = local.project_id
|
||||
location = local.location
|
||||
repository = google_artifact_registry_repository.registry.name
|
||||
role = each.value.role
|
||||
member = each.value.member
|
||||
role = lookup(local.ctx.custom_roles, each.value.role, each.value.role)
|
||||
member = lookup(
|
||||
local.ctx.iam_principals, each.value.member, each.value.member
|
||||
)
|
||||
|
||||
dynamic "condition" {
|
||||
for_each = each.value.condition == null ? [] : [""]
|
||||
content {
|
||||
expression = each.value.condition.expression
|
||||
expression = templatestring(
|
||||
each.value.condition.expression, var.context.condition_vars
|
||||
)
|
||||
title = each.value.condition.title
|
||||
description = each.value.condition.description
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright 2025 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -15,21 +15,31 @@
|
||||
*/
|
||||
|
||||
locals {
|
||||
ctx = {
|
||||
for k, v in var.context : k => {
|
||||
for kk, vv in v : "${local.ctx_p}${k}:${kk}" => vv
|
||||
} if k != "condition_vars"
|
||||
}
|
||||
ctx_p = "$"
|
||||
format_obj = one([for k, v in var.format : v if v != null])
|
||||
format_string = one([for k, v in var.format : k if v != null])
|
||||
location = lookup(local.ctx.locations, var.location, var.location)
|
||||
mode_string = one([for k, v in local.format_obj : k if v != null && v != false])
|
||||
project_id = lookup(local.ctx.project_ids, var.project_id, var.project_id)
|
||||
}
|
||||
|
||||
resource "google_artifact_registry_repository" "registry" {
|
||||
provider = google-beta
|
||||
project = var.project_id
|
||||
location = var.location
|
||||
description = var.description
|
||||
format = upper(local.format_string)
|
||||
labels = var.labels
|
||||
repository_id = var.name
|
||||
mode = "${upper(local.mode_string)}_REPOSITORY"
|
||||
kms_key_name = var.encryption_key
|
||||
provider = google-beta
|
||||
project = local.project_id
|
||||
location = local.location
|
||||
description = var.description
|
||||
format = upper(local.format_string)
|
||||
labels = var.labels
|
||||
repository_id = var.name
|
||||
mode = "${upper(local.mode_string)}_REPOSITORY"
|
||||
kms_key_name = var.encryption_key == null ? null : lookup(
|
||||
local.ctx.kms_keys, var.encryption_key, var.encryption_key
|
||||
)
|
||||
cleanup_policy_dry_run = var.cleanup_policy_dry_run
|
||||
|
||||
vulnerability_scanning_config {
|
||||
@@ -95,8 +105,12 @@ resource "google_artifact_registry_repository" "registry" {
|
||||
for_each = local.format_obj.remote.upstream_credentials != null ? [""] : []
|
||||
content {
|
||||
username_password_credentials {
|
||||
username = local.format_obj.remote.upstream_credentials.username
|
||||
password_secret_version = local.format_obj.remote.upstream_credentials.password_secret_version
|
||||
username = local.format_obj.remote.upstream_credentials.username
|
||||
password_secret_version = lookup(
|
||||
local.ctx.secrets,
|
||||
local.format_obj.remote.upstream_credentials.password_secret_version,
|
||||
local.format_obj.remote.upstream_credentials.password_secret_version
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -199,9 +213,13 @@ resource "google_artifact_registry_repository" "registry" {
|
||||
dynamic "upstream_policies" {
|
||||
for_each = local.format_obj.virtual
|
||||
content {
|
||||
id = upstream_policies.key
|
||||
repository = upstream_policies.value.repository
|
||||
priority = upstream_policies.value.priority
|
||||
id = upstream_policies.key
|
||||
repository = lookup(
|
||||
local.ctx.artifact_registries,
|
||||
upstream_policies.value.repository,
|
||||
upstream_policies.value.repository
|
||||
)
|
||||
priority = upstream_policies.value.priority
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -221,6 +239,6 @@ resource "google_artifact_registry_repository" "registry" {
|
||||
resource "google_tags_location_tag_binding" "binding" {
|
||||
for_each = var.tag_bindings
|
||||
parent = "//artifactregistry.googleapis.com/${google_artifact_registry_repository.registry.id}"
|
||||
location = var.location
|
||||
tag_value = each.value
|
||||
location = local.location
|
||||
tag_value = lookup(local.ctx.tag_values, each.value, each.value)
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright 2024 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -18,14 +18,14 @@ locals {
|
||||
url = (
|
||||
var.universe == null
|
||||
? join("/", [
|
||||
"${var.location}-${local.format_string}.pkg.dev",
|
||||
var.project_id,
|
||||
"${local.location}-${local.format_string}.pkg.dev",
|
||||
local.project_id,
|
||||
var.name
|
||||
])
|
||||
: join("/", [
|
||||
"${local.format_string}.${var.universe.package_domain}",
|
||||
var.universe.prefix,
|
||||
element(split(":", var.project_id), 1),
|
||||
element(split(":", local.project_id), 1),
|
||||
var.name
|
||||
])
|
||||
)
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright 2024 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -41,6 +41,23 @@ variable "cleanup_policy_dry_run" {
|
||||
default = null
|
||||
}
|
||||
|
||||
variable "context" {
|
||||
description = "Context-specific interpolations."
|
||||
type = object({
|
||||
artifact_registries = optional(map(string), {})
|
||||
condition_vars = optional(map(map(string)), {})
|
||||
custom_roles = optional(map(string), {})
|
||||
iam_principals = optional(map(string), {})
|
||||
kms_keys = optional(map(string), {})
|
||||
locations = optional(map(string), {})
|
||||
project_ids = optional(map(string), {})
|
||||
secrets = optional(map(string), {})
|
||||
tag_values = optional(map(string), {})
|
||||
})
|
||||
default = {}
|
||||
nullable = false
|
||||
}
|
||||
|
||||
variable "description" {
|
||||
description = "An optional description for the repository."
|
||||
type = string
|
||||
|
||||
@@ -86,17 +86,22 @@ module "db" {
|
||||
```hcl
|
||||
module "db" {
|
||||
source = "./fabric/modules/cloudsql-instance"
|
||||
project_id = var.project_id
|
||||
project_id = "$project_ids:myprj"
|
||||
context = {
|
||||
networks = { myvpc = "https://www.googleapis.com/compute/v1/projects/xxx/global/networks/aaa" }
|
||||
locations = { ew8 = "europe-west8" }
|
||||
project_ids = { myprj = "project-id" }
|
||||
}
|
||||
network_config = {
|
||||
connectivity = {
|
||||
psa_config = {
|
||||
private_network = var.vpc.self_link
|
||||
private_network = "$networks:myvpc"
|
||||
}
|
||||
}
|
||||
}
|
||||
name = "db"
|
||||
prefix = "myprefix"
|
||||
region = var.region
|
||||
region = "$locations:ew8"
|
||||
database_version = "POSTGRES_16"
|
||||
tier = "db-g1-small"
|
||||
|
||||
@@ -408,38 +413,39 @@ module "db" {
|
||||
|
||||
| name | description | type | required | default |
|
||||
|---|---|:---:|:---:|:---:|
|
||||
| [database_version](variables.tf#L72) | Database type and version to create. | <code>string</code> | ✓ | |
|
||||
| [name](variables.tf#L188) | Name of primary instance. | <code>string</code> | ✓ | |
|
||||
| [network_config](variables.tf#L193) | Network configuration for the instance. Only one between private_network and psc_config can be used. | <code title="object({ authorized_networks = optional(map(string)) connectivity = object({ public_ipv4 = optional(bool, false) psa_config = optional(object({ private_network = string allocated_ip_ranges = optional(object({ primary = optional(string) replica = optional(string) })) })) psc_allowed_consumer_projects = optional(list(string)) enable_private_path_for_services = optional(bool, false) }) })">object({…})</code> | ✓ | |
|
||||
| [project_id](variables.tf#L236) | The ID of the project where this instances will be created. | <code>string</code> | ✓ | |
|
||||
| [region](variables.tf#L241) | Region of the primary instance. | <code>string</code> | ✓ | |
|
||||
| [tier](variables.tf#L293) | The machine type to use for the instances. | <code>string</code> | ✓ | |
|
||||
| [activation_policy](variables.tf#L16) | This variable specifies when the instance should be active. Can be either ALWAYS, NEVER or ON_DEMAND. Default is ALWAYS. | <code>string</code> | | <code>"ALWAYS"</code> |
|
||||
| [availability_type](variables.tf#L27) | Availability type for the primary replica. Either `ZONAL` or `REGIONAL`. | <code>string</code> | | <code>"ZONAL"</code> |
|
||||
| [backup_configuration](variables.tf#L33) | Backup settings for primary instance. Set to null to leave existing GCP backup settings unmanaged. When set, all fields are managed by Terraform including disabling backups when enabled=false. | <code title="object({ enabled = optional(bool, false) binary_log_enabled = optional(bool, false) start_time = optional(string, "23:00") location = optional(string) log_retention_days = optional(number, 7) point_in_time_recovery_enabled = optional(bool) retention_count = optional(number, 7) retain_backups_on_delete = optional(bool) final_backup = optional(object({ enabled = optional(bool, false) retention_days = optional(number, 7) })) })">object({…})</code> | | <code>null</code> |
|
||||
| [collation](variables.tf#L53) | The name of server instance collation. | <code>string</code> | | <code>null</code> |
|
||||
| [connector_enforcement](variables.tf#L59) | Specifies if connections must use Cloud SQL connectors. | <code>string</code> | | <code>null</code> |
|
||||
| [data_cache](variables.tf#L65) | Enable data cache. Only used for Enterprise MYSQL and PostgreSQL. | <code>bool</code> | | <code>false</code> |
|
||||
| [databases](variables.tf#L77) | Databases to create once the primary instance is created. | <code>list(string)</code> | | <code>null</code> |
|
||||
| [disk_autoresize_limit](variables.tf#L83) | The maximum size to which storage capacity can be automatically increased. The default value is 0, which specifies that there is no limit. | <code>number</code> | | <code>0</code> |
|
||||
| [disk_size](variables.tf#L89) | Disk size in GB. Set to null to enable autoresize. | <code>number</code> | | <code>null</code> |
|
||||
| [disk_type](variables.tf#L95) | The type of data disk: `PD_SSD` or `PD_HDD`. | <code>string</code> | | <code>"PD_SSD"</code> |
|
||||
| [edition](variables.tf#L101) | The edition of the instance, can be ENTERPRISE or ENTERPRISE_PLUS. | <code>string</code> | | <code>"ENTERPRISE"</code> |
|
||||
| [encryption_key_name](variables.tf#L107) | The full path to the encryption key used for the CMEK disk encryption of the primary instance. | <code>string</code> | | <code>null</code> |
|
||||
| [flags](variables.tf#L113) | Map FLAG_NAME=>VALUE for database-specific tuning. | <code>map(string)</code> | | <code>null</code> |
|
||||
| [gcp_deletion_protection](variables.tf#L119) | Set Google's deletion protection attribute which applies across all surfaces (UI, API, & Terraform). | <code>bool</code> | | <code>true</code> |
|
||||
| [insights_config](variables.tf#L126) | Query Insights configuration. Defaults to null which disables Query Insights. | <code title="object({ query_string_length = optional(number, 1024) record_application_tags = optional(bool, false) record_client_address = optional(bool, false) query_plans_per_minute = optional(number, 5) })">object({…})</code> | | <code>null</code> |
|
||||
| [labels](variables.tf#L137) | Labels to be attached to all instances. | <code>map(string)</code> | | <code>null</code> |
|
||||
| [maintenance_config](variables.tf#L143) | Set maintenance window configuration and maintenance deny period (up to 90 days). Date format: 'yyyy-mm-dd'. | <code title="object({ maintenance_window = optional(object({ day = optional(number) hour = number update_track = optional(string, null) }), null) deny_maintenance_period = optional(object({ start_date = string end_date = string start_time = optional(string, "00:00:00") }), null) })">object({…})</code> | | <code>{}</code> |
|
||||
| [managed_connection_pooling_config](variables.tf#L178) | Configuration for Managed Connection Pooling. NOTE: This feature is only available for PostgreSQL on Enterprise Plus edition instances. | <code title="object({ enabled = optional(bool, false) flags = optional(map(string), {}) })">object({…})</code> | | <code>{}</code> |
|
||||
| [password_validation_policy](variables.tf#L212) | Password validation policy configuration for instances. | <code title="object({ enabled = optional(bool, true) change_interval = optional(number) default_complexity = optional(bool) disallow_username_substring = optional(bool) min_length = optional(number) reuse_interval = optional(number) })">object({…})</code> | | <code>null</code> |
|
||||
| [prefix](variables.tf#L226) | Optional prefix used to generate instance names. | <code>string</code> | | <code>null</code> |
|
||||
| [replicas](variables.tf#L246) | Map of NAME=> {REGION, KMS_KEY, AVAILABILITY_TYPE} for additional read replicas. Set to null to disable replica creation. | <code title="map(object({ region = string encryption_key_name = optional(string) availability_type = optional(string) }))">map(object({…}))</code> | | <code>{}</code> |
|
||||
| [root_password](variables.tf#L257) | Root password of the Cloud SQL instance, or flag to create a random password. Required for MS SQL Server. | <code title="object({ password = optional(string) random_password = optional(bool, false) })">object({…})</code> | | <code>{}</code> |
|
||||
| [ssl](variables.tf#L271) | Setting to enable SSL, set config and certificates. | <code title="object({ client_certificates = optional(list(string)) mode = optional(string) })">object({…})</code> | | <code>{}</code> |
|
||||
| [terraform_deletion_protection](variables.tf#L286) | Prevent terraform from deleting instances. | <code>bool</code> | | <code>true</code> |
|
||||
| [time_zone](variables.tf#L298) | The time_zone to be used by the database engine (supported only for SQL Server), in SQL Server timezone format. | <code>string</code> | | <code>null</code> |
|
||||
| [users](variables.tf#L304) | Map of users to create in the primary instance (and replicated to other replicas). For MySQL, anything after the first `@` (if present) will be used as the user's host. Set PASSWORD to null if you want to get an autogenerated password. The user types available are: 'BUILT_IN', 'CLOUD_IAM_USER' or 'CLOUD_IAM_SERVICE_ACCOUNT'. | <code title="map(object({ password = optional(string) password_version = optional(number) type = optional(string, "BUILT_IN") }))">map(object({…}))</code> | | <code>{}</code> |
|
||||
| [database_version](variables.tf#L85) | Database type and version to create. | <code>string</code> | ✓ | |
|
||||
| [name](variables.tf#L201) | Name of primary instance. | <code>string</code> | ✓ | |
|
||||
| [network_config](variables.tf#L206) | Network configuration for the instance. Only one between private_network and psc_config can be used. | <code title="object({ authorized_networks = optional(map(string)) connectivity = object({ public_ipv4 = optional(bool, false) psa_config = optional(object({ private_network = string allocated_ip_ranges = optional(object({ primary = optional(string) replica = optional(string) })) })) psc_allowed_consumer_projects = optional(list(string)) enable_private_path_for_services = optional(bool, false) }) })">object({…})</code> | ✓ | |
|
||||
| [project_id](variables.tf#L249) | The ID of the project where this instances will be created. | <code>string</code> | ✓ | |
|
||||
| [region](variables.tf#L254) | Region of the primary instance. | <code>string</code> | ✓ | |
|
||||
| [tier](variables.tf#L306) | The machine type to use for the instances. | <code>string</code> | ✓ | |
|
||||
| [activation_policy](variables.tf#L17) | This variable specifies when the instance should be active. Can be either ALWAYS, NEVER or ON_DEMAND. Default is ALWAYS. | <code>string</code> | | <code>"ALWAYS"</code> |
|
||||
| [availability_type](variables.tf#L28) | Availability type for the primary replica. Either `ZONAL` or `REGIONAL`. | <code>string</code> | | <code>"ZONAL"</code> |
|
||||
| [backup_configuration](variables.tf#L34) | Backup settings for primary instance. Set to null to leave existing GCP backup settings unmanaged. When set, all fields are managed by Terraform including disabling backups when enabled=false. | <code title="object({ enabled = optional(bool, false) binary_log_enabled = optional(bool, false) start_time = optional(string, "23:00") location = optional(string) log_retention_days = optional(number, 7) point_in_time_recovery_enabled = optional(bool) retention_count = optional(number, 7) retain_backups_on_delete = optional(bool) final_backup = optional(object({ enabled = optional(bool, false) retention_days = optional(number, 7) })) })">object({…})</code> | | <code>null</code> |
|
||||
| [collation](variables.tf#L54) | The name of server instance collation. | <code>string</code> | | <code>null</code> |
|
||||
| [connector_enforcement](variables.tf#L60) | Specifies if connections must use Cloud SQL connectors. | <code>string</code> | | <code>null</code> |
|
||||
| [context](variables.tf#L66) | Context-specific interpolations. | <code title="object({ kms_keys = optional(map(string), {}) locations = optional(map(string), {}) networks = optional(map(string), {}) project_ids = optional(map(string), {}) })">object({…})</code> | | <code>{}</code> |
|
||||
| [data_cache](variables.tf#L78) | Enable data cache. Only used for Enterprise MYSQL and PostgreSQL. | <code>bool</code> | | <code>false</code> |
|
||||
| [databases](variables.tf#L90) | Databases to create once the primary instance is created. | <code>list(string)</code> | | <code>null</code> |
|
||||
| [disk_autoresize_limit](variables.tf#L96) | The maximum size to which storage capacity can be automatically increased. The default value is 0, which specifies that there is no limit. | <code>number</code> | | <code>0</code> |
|
||||
| [disk_size](variables.tf#L102) | Disk size in GB. Set to null to enable autoresize. | <code>number</code> | | <code>null</code> |
|
||||
| [disk_type](variables.tf#L108) | The type of data disk: `PD_SSD` or `PD_HDD`. | <code>string</code> | | <code>"PD_SSD"</code> |
|
||||
| [edition](variables.tf#L114) | The edition of the instance, can be ENTERPRISE or ENTERPRISE_PLUS. | <code>string</code> | | <code>"ENTERPRISE"</code> |
|
||||
| [encryption_key_name](variables.tf#L120) | The full path to the encryption key used for the CMEK disk encryption of the primary instance. | <code>string</code> | | <code>null</code> |
|
||||
| [flags](variables.tf#L126) | Map FLAG_NAME=>VALUE for database-specific tuning. | <code>map(string)</code> | | <code>null</code> |
|
||||
| [gcp_deletion_protection](variables.tf#L132) | Set Google's deletion protection attribute which applies across all surfaces (UI, API, & Terraform). | <code>bool</code> | | <code>true</code> |
|
||||
| [insights_config](variables.tf#L139) | Query Insights configuration. Defaults to null which disables Query Insights. | <code title="object({ query_string_length = optional(number, 1024) record_application_tags = optional(bool, false) record_client_address = optional(bool, false) query_plans_per_minute = optional(number, 5) })">object({…})</code> | | <code>null</code> |
|
||||
| [labels](variables.tf#L150) | Labels to be attached to all instances. | <code>map(string)</code> | | <code>null</code> |
|
||||
| [maintenance_config](variables.tf#L156) | Set maintenance window configuration and maintenance deny period (up to 90 days). Date format: 'yyyy-mm-dd'. | <code title="object({ maintenance_window = optional(object({ day = optional(number) hour = number update_track = optional(string, null) }), null) deny_maintenance_period = optional(object({ start_date = string end_date = string start_time = optional(string, "00:00:00") }), null) })">object({…})</code> | | <code>{}</code> |
|
||||
| [managed_connection_pooling_config](variables.tf#L191) | Configuration for Managed Connection Pooling. NOTE: This feature is only available for PostgreSQL on Enterprise Plus edition instances. | <code title="object({ enabled = optional(bool, false) flags = optional(map(string), {}) })">object({…})</code> | | <code>{}</code> |
|
||||
| [password_validation_policy](variables.tf#L225) | Password validation policy configuration for instances. | <code title="object({ enabled = optional(bool, true) change_interval = optional(number) default_complexity = optional(bool) disallow_username_substring = optional(bool) min_length = optional(number) reuse_interval = optional(number) })">object({…})</code> | | <code>null</code> |
|
||||
| [prefix](variables.tf#L239) | Optional prefix used to generate instance names. | <code>string</code> | | <code>null</code> |
|
||||
| [replicas](variables.tf#L259) | Map of NAME=> {REGION, KMS_KEY, AVAILABILITY_TYPE} for additional read replicas. Set to null to disable replica creation. | <code title="map(object({ region = string encryption_key_name = optional(string) availability_type = optional(string) }))">map(object({…}))</code> | | <code>{}</code> |
|
||||
| [root_password](variables.tf#L270) | Root password of the Cloud SQL instance, or flag to create a random password. Required for MS SQL Server. | <code title="object({ password = optional(string) random_password = optional(bool, false) })">object({…})</code> | | <code>{}</code> |
|
||||
| [ssl](variables.tf#L284) | Setting to enable SSL, set config and certificates. | <code title="object({ client_certificates = optional(list(string)) mode = optional(string) })">object({…})</code> | | <code>{}</code> |
|
||||
| [terraform_deletion_protection](variables.tf#L299) | Prevent terraform from deleting instances. | <code>bool</code> | | <code>true</code> |
|
||||
| [time_zone](variables.tf#L311) | The time_zone to be used by the database engine (supported only for SQL Server), in SQL Server timezone format. | <code>string</code> | | <code>null</code> |
|
||||
| [users](variables.tf#L317) | Map of users to create in the primary instance (and replicated to other replicas). For MySQL, anything after the first `@` (if present) will be used as the user's host. Set PASSWORD to null if you want to get an autogenerated password. The user types available are: 'BUILT_IN', 'CLOUD_IAM_USER' or 'CLOUD_IAM_SERVICE_ACCOUNT'. | <code title="map(object({ password = optional(string) password_version = optional(number) type = optional(string, "BUILT_IN") }))">map(object({…}))</code> | | <code>{}</code> |
|
||||
|
||||
## Outputs
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/** TO MOD
|
||||
* Copyright 2024 Google LLC
|
||||
/**
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -15,11 +15,33 @@
|
||||
*/
|
||||
|
||||
locals {
|
||||
prefix = var.prefix == null ? "" : "${var.prefix}-"
|
||||
ctx = {
|
||||
for k, v in var.context : k => {
|
||||
for kk, vv in v : "${local.ctx_p}${k}:${kk}" => vv
|
||||
}
|
||||
}
|
||||
ctx_p = "$"
|
||||
encryption_key_name = (
|
||||
var.encryption_key_name == null
|
||||
? null
|
||||
: lookup(local.ctx.kms_keys, var.encryption_key_name, var.encryption_key_name)
|
||||
)
|
||||
has_replicas = length(var.replicas) > 0
|
||||
is_mysql = can(regex("^MYSQL", var.database_version))
|
||||
is_postgres = can(regex("^POSTGRES", var.database_version))
|
||||
has_replicas = length(var.replicas) > 0
|
||||
is_regional = var.availability_type == "REGIONAL" ? true : false
|
||||
psa_private_network = (
|
||||
try(var.network_config.connectivity.psa_config.private_network, null) == null
|
||||
? null
|
||||
: lookup(
|
||||
local.ctx.networks,
|
||||
var.network_config.connectivity.psa_config.private_network,
|
||||
var.network_config.connectivity.psa_config.private_network
|
||||
)
|
||||
)
|
||||
prefix = var.prefix == null ? "" : "${var.prefix}-"
|
||||
project_id = lookup(local.ctx.project_ids, var.project_id, var.project_id)
|
||||
region = lookup(local.ctx.locations, var.region, var.region)
|
||||
|
||||
users = {
|
||||
for k, v in var.users : k =>
|
||||
@@ -41,11 +63,11 @@ locals {
|
||||
|
||||
resource "google_sql_database_instance" "primary" {
|
||||
provider = google-beta
|
||||
project = var.project_id
|
||||
project = local.project_id
|
||||
name = "${local.prefix}${var.name}"
|
||||
region = var.region
|
||||
region = local.region
|
||||
database_version = var.database_version
|
||||
encryption_key_name = var.encryption_key_name
|
||||
encryption_key_name = local.encryption_key_name
|
||||
root_password = var.root_password.random_password ? random_password.root_password[0].result : var.root_password.password
|
||||
|
||||
settings {
|
||||
@@ -65,10 +87,8 @@ resource "google_sql_database_instance" "primary" {
|
||||
retain_backups_on_delete = try(var.backup_configuration.retain_backups_on_delete, null)
|
||||
|
||||
ip_configuration {
|
||||
ipv4_enabled = var.network_config.connectivity.public_ipv4
|
||||
private_network = try(
|
||||
var.network_config.connectivity.psa_config.private_network, null
|
||||
)
|
||||
ipv4_enabled = var.network_config.connectivity.public_ipv4
|
||||
private_network = local.psa_private_network
|
||||
allocated_ip_range = try(
|
||||
var.network_config.connectivity.psa_config.allocated_ip_ranges.primary, null
|
||||
)
|
||||
@@ -234,13 +254,17 @@ resource "google_sql_database_instance" "primary" {
|
||||
}
|
||||
|
||||
resource "google_sql_database_instance" "replicas" {
|
||||
provider = google-beta
|
||||
for_each = local.has_replicas ? var.replicas : {}
|
||||
project = var.project_id
|
||||
name = "${local.prefix}${each.key}"
|
||||
region = each.value.region
|
||||
database_version = var.database_version
|
||||
encryption_key_name = each.value.encryption_key_name
|
||||
provider = google-beta
|
||||
for_each = local.has_replicas ? var.replicas : {}
|
||||
project = local.project_id
|
||||
name = "${local.prefix}${each.key}"
|
||||
region = lookup(local.ctx.locations, each.value.region, each.value.region)
|
||||
database_version = var.database_version
|
||||
encryption_key_name = (
|
||||
each.value.encryption_key_name == null
|
||||
? null
|
||||
: lookup(local.ctx.kms_keys, each.value.encryption_key_name, each.value.encryption_key_name)
|
||||
)
|
||||
master_instance_name = google_sql_database_instance.primary.name
|
||||
|
||||
settings {
|
||||
@@ -263,9 +287,7 @@ resource "google_sql_database_instance" "replicas" {
|
||||
ipv4_enabled = (
|
||||
var.network_config.connectivity.public_ipv4
|
||||
)
|
||||
private_network = (
|
||||
try(var.network_config.connectivity.psa_config.private_network, null)
|
||||
)
|
||||
private_network = local.psa_private_network
|
||||
allocated_ip_range = try(
|
||||
var.network_config.connectivity.psa_config.allocated_ip_ranges.replica, null
|
||||
)
|
||||
@@ -314,7 +336,7 @@ resource "google_sql_database_instance" "replicas" {
|
||||
|
||||
resource "google_sql_database" "databases" {
|
||||
for_each = var.databases != null ? toset(var.databases) : toset([])
|
||||
project = var.project_id
|
||||
project = local.project_id
|
||||
instance = google_sql_database_instance.primary.name
|
||||
name = each.key
|
||||
}
|
||||
@@ -345,7 +367,7 @@ resource "random_password" "root_password" {
|
||||
|
||||
resource "google_sql_user" "users" {
|
||||
for_each = local.users
|
||||
project = var.project_id
|
||||
project = local.project_id
|
||||
instance = google_sql_database_instance.primary.name
|
||||
name = each.value.name
|
||||
host = each.value.host
|
||||
@@ -365,7 +387,7 @@ resource "google_sql_ssl_cert" "client_certificates" {
|
||||
: toset([])
|
||||
)
|
||||
provider = google-beta
|
||||
project = var.project_id
|
||||
project = local.project_id
|
||||
instance = google_sql_database_instance.primary.name
|
||||
common_name = each.key
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright 2022 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright 2025 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -13,6 +13,7 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
variable "activation_policy" {
|
||||
description = "This variable specifies when the instance should be active. Can be either ALWAYS, NEVER or ON_DEMAND. Default is ALWAYS."
|
||||
type = string
|
||||
@@ -62,6 +63,18 @@ variable "connector_enforcement" {
|
||||
default = null
|
||||
}
|
||||
|
||||
variable "context" {
|
||||
description = "Context-specific interpolations."
|
||||
type = object({
|
||||
kms_keys = optional(map(string), {})
|
||||
locations = optional(map(string), {})
|
||||
networks = optional(map(string), {})
|
||||
project_ids = optional(map(string), {})
|
||||
})
|
||||
default = {}
|
||||
nullable = false
|
||||
}
|
||||
|
||||
variable "data_cache" {
|
||||
description = "Enable data cache. Only used for Enterprise MYSQL and PostgreSQL."
|
||||
type = bool
|
||||
|
||||
File diff suppressed because one or more lines are too long
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright 2022 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -47,10 +47,10 @@ resource "google_compute_region_backend_service" "default" {
|
||||
for_each = var.backend_service_configs
|
||||
project = (
|
||||
each.value.project_id == null
|
||||
? var.project_id
|
||||
? local.project_id
|
||||
: each.value.project_id
|
||||
)
|
||||
region = var.region
|
||||
region = local.region
|
||||
name = coalesce(each.value.name, "${var.name}-${each.key}")
|
||||
description = each.value.description
|
||||
affinity_cookie_ttl_sec = each.value.affinity_cookie_ttl_sec
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright 2023 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -18,7 +18,7 @@ resource "google_compute_instance_group" "default" {
|
||||
for_each = var.group_configs
|
||||
project = (
|
||||
each.value.project_id == null
|
||||
? var.project_id
|
||||
? local.project_id
|
||||
: each.value.project_id
|
||||
)
|
||||
zone = each.value.zone
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright 2022 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -21,7 +21,7 @@ resource "google_compute_health_check" "default" {
|
||||
for_each = var.health_check_configs
|
||||
project = (
|
||||
each.value.project_id == null
|
||||
? var.project_id
|
||||
? local.project_id
|
||||
: each.value.project_id
|
||||
)
|
||||
name = coalesce(each.value.name, "${var.name}-${each.key}")
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright 2022 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -14,6 +14,19 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
locals {
|
||||
ctx = {
|
||||
for k, v in var.context : k => {
|
||||
for kk, vv in v : "${local.ctx_p}${k}:${kk}" => vv
|
||||
}
|
||||
}
|
||||
ctx_p = "$"
|
||||
network = lookup(local.ctx.networks, var.vpc_config.network, var.vpc_config.network)
|
||||
project_id = lookup(local.ctx.project_ids, var.project_id, var.project_id)
|
||||
region = lookup(local.ctx.locations, var.region, var.region)
|
||||
subnetwork = lookup(local.ctx.subnets, var.vpc_config.subnetwork, var.vpc_config.subnetwork)
|
||||
}
|
||||
|
||||
locals {
|
||||
# we need keys in the endpoint type to address issue #1055
|
||||
_neg_endpoints = flatten([
|
||||
@@ -60,18 +73,22 @@ locals {
|
||||
}
|
||||
|
||||
resource "google_compute_forwarding_rule" "default" {
|
||||
provider = google-beta
|
||||
project = var.project_id
|
||||
region = var.region
|
||||
name = var.name
|
||||
description = var.description
|
||||
ip_address = var.address
|
||||
provider = google-beta
|
||||
project = local.project_id
|
||||
region = local.region
|
||||
name = var.name
|
||||
description = var.description
|
||||
ip_address = (
|
||||
var.address == null
|
||||
? null
|
||||
: lookup(local.ctx.addresses, var.address, var.address)
|
||||
)
|
||||
ip_protocol = "TCP"
|
||||
load_balancing_scheme = "INTERNAL_MANAGED"
|
||||
network = var.vpc_config.network
|
||||
network = local.network
|
||||
network_tier = var.network_tier_premium ? "PREMIUM" : "STANDARD"
|
||||
port_range = join(",", local.fwd_rule_ports)
|
||||
subnetwork = var.vpc_config.subnetwork
|
||||
subnetwork = local.subnetwork
|
||||
labels = var.labels
|
||||
target = local.fwd_rule_target
|
||||
# during the preview phase you cannot change this attribute on an existing rule
|
||||
@@ -87,8 +104,8 @@ resource "google_compute_forwarding_rule" "default" {
|
||||
|
||||
resource "google_compute_region_ssl_certificate" "default" {
|
||||
for_each = var.ssl_certificates.create_configs
|
||||
project = var.project_id
|
||||
region = var.region
|
||||
project = local.project_id
|
||||
region = local.region
|
||||
name = coalesce(each.value.name, "${var.name}-${each.key}")
|
||||
certificate = each.value.certificate
|
||||
private_key = each.value.private_key
|
||||
@@ -100,8 +117,8 @@ resource "google_compute_region_ssl_certificate" "default" {
|
||||
|
||||
resource "google_compute_region_target_http_proxy" "default" {
|
||||
count = var.protocol == "HTTPS" ? 0 : 1
|
||||
project = var.project_id
|
||||
region = var.region
|
||||
project = local.project_id
|
||||
region = local.region
|
||||
name = coalesce(var.https_proxy_config.name, var.name)
|
||||
description = var.http_proxy_config.description
|
||||
url_map = google_compute_region_url_map.default.id
|
||||
@@ -109,8 +126,8 @@ resource "google_compute_region_target_http_proxy" "default" {
|
||||
|
||||
resource "google_compute_region_target_https_proxy" "default" {
|
||||
count = var.protocol == "HTTPS" ? 1 : 0
|
||||
project = var.project_id
|
||||
region = var.region
|
||||
project = local.project_id
|
||||
region = local.region
|
||||
name = coalesce(var.https_proxy_config.name, var.name)
|
||||
description = var.https_proxy_config.description
|
||||
ssl_certificates = length(local.proxy_ssl_certificates) == 0 ? null : local.proxy_ssl_certificates
|
||||
@@ -121,12 +138,14 @@ resource "google_compute_region_target_https_proxy" "default" {
|
||||
|
||||
resource "google_compute_service_attachment" "default" {
|
||||
count = var.service_attachment == null ? 0 : 1
|
||||
project = var.project_id
|
||||
region = var.region
|
||||
project = local.project_id
|
||||
region = local.region
|
||||
name = var.name
|
||||
description = var.description
|
||||
target_service = google_compute_forwarding_rule.default.id
|
||||
nat_subnets = var.service_attachment.nat_subnets
|
||||
nat_subnets = [
|
||||
for s in var.service_attachment.nat_subnets : lookup(local.ctx.subnets, s, s)
|
||||
]
|
||||
connection_preference = (
|
||||
var.service_attachment.automatic_connection
|
||||
? "ACCEPT_AUTOMATIC"
|
||||
@@ -154,7 +173,7 @@ resource "google_compute_network_endpoint_group" "default" {
|
||||
for_each = local.neg_zonal
|
||||
project = (
|
||||
each.value.project_id == null
|
||||
? var.project_id
|
||||
? local.project_id
|
||||
: each.value.project_id
|
||||
)
|
||||
zone = each.value.zone
|
||||
@@ -164,12 +183,12 @@ resource "google_compute_network_endpoint_group" "default" {
|
||||
description = var.description
|
||||
network_endpoint_type = each.value.type
|
||||
network = (
|
||||
each.value.network != null ? each.value.network : var.vpc_config.network
|
||||
each.value.network != null ? each.value.network : local.network
|
||||
)
|
||||
subnetwork = (
|
||||
each.value.type == "NON_GCP_PRIVATE_IP_PORT"
|
||||
? null
|
||||
: coalesce(each.value.subnetwork, var.vpc_config.subnetwork)
|
||||
: coalesce(each.value.subnetwork, local.subnetwork)
|
||||
)
|
||||
}
|
||||
|
||||
@@ -191,7 +210,7 @@ resource "google_compute_region_network_endpoint_group" "default" {
|
||||
for_each = local.neg_regional
|
||||
project = (
|
||||
each.value.project_id == null
|
||||
? var.project_id
|
||||
? local.project_id
|
||||
: each.value.project_id
|
||||
)
|
||||
region = each.value.region
|
||||
@@ -211,7 +230,7 @@ resource "google_compute_region_network_endpoint_group" "psc" {
|
||||
for_each = local.neg_regional_psc
|
||||
project = (
|
||||
each.value.project_id == null
|
||||
? var.project_id
|
||||
? local.project_id
|
||||
: each.value.project_id
|
||||
)
|
||||
region = each.value.psc.region
|
||||
@@ -246,7 +265,7 @@ locals {
|
||||
|
||||
resource "google_compute_region_network_endpoint_group" "internet" {
|
||||
for_each = local.neg_internet
|
||||
project = var.project_id
|
||||
project = local.project_id
|
||||
name = "${var.name}-${each.key}"
|
||||
region = each.value.internet.region
|
||||
# re-enable once provider properly supports this
|
||||
@@ -255,7 +274,7 @@ resource "google_compute_region_network_endpoint_group" "internet" {
|
||||
network_endpoint_type = (
|
||||
each.value.internet.use_fqdn ? "INTERNET_FQDN_PORT" : "INTERNET_IP_PORT"
|
||||
)
|
||||
network = var.vpc_config.network
|
||||
network = local.network
|
||||
}
|
||||
|
||||
resource "google_compute_region_network_endpoint" "internet" {
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright 2022 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -24,8 +24,8 @@ locals {
|
||||
|
||||
resource "google_compute_region_url_map" "default" {
|
||||
provider = google-beta
|
||||
project = var.project_id
|
||||
region = var.region
|
||||
project = local.project_id
|
||||
region = local.region
|
||||
name = var.name
|
||||
description = var.urlmap_config.description
|
||||
default_service = (
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright 2022 Google LLC
|
||||
* Copyright 2026 Google LLC
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -20,6 +20,19 @@ variable "address" {
|
||||
default = null
|
||||
}
|
||||
|
||||
variable "context" {
|
||||
description = "Context-specific interpolations."
|
||||
type = object({
|
||||
addresses = optional(map(string), {})
|
||||
locations = optional(map(string), {})
|
||||
networks = optional(map(string), {})
|
||||
project_ids = optional(map(string), {})
|
||||
subnets = optional(map(string), {})
|
||||
})
|
||||
default = {}
|
||||
nullable = false
|
||||
}
|
||||
|
||||
variable "description" {
|
||||
description = "Optional description used for resources."
|
||||
type = string
|
||||
|
||||
73
tests/modules/artifact_registry/context.tfvars
Normal file
73
tests/modules/artifact_registry/context.tfvars
Normal file
@@ -0,0 +1,73 @@
|
||||
context = {
|
||||
artifact_registries = {
|
||||
upstream-one = "projects/actual-project-id/locations/europe-west8/repositories/upstream"
|
||||
}
|
||||
condition_vars = {
|
||||
organization = {
|
||||
id = "1234567890"
|
||||
}
|
||||
}
|
||||
custom_roles = {
|
||||
myrole_one = "organizations/366118655033/roles/myRoleOne"
|
||||
myrole_two = "organizations/366118655033/roles/myRoleTwo"
|
||||
myrole_three = "organizations/366118655033/roles/myRoleThree"
|
||||
myrole_four = "organizations/366118655033/roles/myRoleFour"
|
||||
}
|
||||
iam_principals = {
|
||||
mysa = "serviceAccount:test@test-project.iam.gserviceaccount.com"
|
||||
myuser = "user:test-user@example.com"
|
||||
myuser2 = "user:test-user2@example.com"
|
||||
}
|
||||
locations = {
|
||||
ew8 = "europe-west8"
|
||||
}
|
||||
project_ids = {
|
||||
myproject = "actual-project-id"
|
||||
}
|
||||
tag_values = {
|
||||
"test/one" = "tagValues/1234567890"
|
||||
}
|
||||
}
|
||||
project_id = "$project_ids:myproject"
|
||||
name = "myregistry"
|
||||
location = "$locations:ew8"
|
||||
format = {
|
||||
docker = {
|
||||
virtual = {
|
||||
upstream-one = {
|
||||
repository = "$artifact_registries:upstream-one"
|
||||
priority = 100
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
iam = {
|
||||
"$custom_roles:myrole_one" = ["$iam_principals:myuser"]
|
||||
"roles/viewer" = ["$iam_principals:mysa"]
|
||||
}
|
||||
iam_bindings = {
|
||||
myrole_two = {
|
||||
role = "$custom_roles:myrole_two"
|
||||
members = ["$iam_principals:mysa"]
|
||||
condition = {
|
||||
title = "Test"
|
||||
expression = "resource.matchTag('$${organization.id}/environment', 'development')"
|
||||
}
|
||||
}
|
||||
}
|
||||
iam_bindings_additive = {
|
||||
myrole_three = {
|
||||
role = "$custom_roles:myrole_three"
|
||||
member = "$iam_principals:mysa"
|
||||
}
|
||||
}
|
||||
iam_by_principals = {
|
||||
"$iam_principals:myuser2" = [
|
||||
"$custom_roles:myrole_three",
|
||||
"$custom_roles:myrole_four",
|
||||
"roles/owner",
|
||||
]
|
||||
}
|
||||
tag_bindings = {
|
||||
foo = "$tag_values:test/one"
|
||||
}
|
||||
108
tests/modules/artifact_registry/context.yaml
Normal file
108
tests/modules/artifact_registry/context.yaml
Normal file
@@ -0,0 +1,108 @@
|
||||
# Copyright 2026 Google LLC
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
values:
|
||||
google_artifact_registry_repository.registry:
|
||||
cleanup_policies: []
|
||||
cleanup_policy_dry_run: null
|
||||
description: Terraform-managed registry
|
||||
docker_config: []
|
||||
effective_labels:
|
||||
goog-terraform-provisioned: 'true'
|
||||
format: DOCKER
|
||||
kms_key_name: null
|
||||
labels: null
|
||||
location: europe-west8
|
||||
maven_config: []
|
||||
mode: VIRTUAL_REPOSITORY
|
||||
project: actual-project-id
|
||||
remote_repository_config: []
|
||||
repository_id: myregistry
|
||||
terraform_labels:
|
||||
goog-terraform-provisioned: 'true'
|
||||
timeouts: null
|
||||
virtual_repository_config:
|
||||
- upstream_policies:
|
||||
- id: upstream-one
|
||||
priority: 100
|
||||
repository: projects/actual-project-id/locations/europe-west8/repositories/upstream
|
||||
google_artifact_registry_repository_iam_binding.authoritative["$custom_roles:myrole_four"]:
|
||||
condition: []
|
||||
location: europe-west8
|
||||
members:
|
||||
- user:test-user2@example.com
|
||||
project: actual-project-id
|
||||
role: organizations/366118655033/roles/myRoleFour
|
||||
google_artifact_registry_repository_iam_binding.authoritative["$custom_roles:myrole_one"]:
|
||||
condition: []
|
||||
location: europe-west8
|
||||
members:
|
||||
- user:test-user@example.com
|
||||
project: actual-project-id
|
||||
role: organizations/366118655033/roles/myRoleOne
|
||||
google_artifact_registry_repository_iam_binding.authoritative["$custom_roles:myrole_three"]:
|
||||
condition: []
|
||||
location: europe-west8
|
||||
members:
|
||||
- user:test-user2@example.com
|
||||
project: actual-project-id
|
||||
role: organizations/366118655033/roles/myRoleThree
|
||||
google_artifact_registry_repository_iam_binding.authoritative["roles/owner"]:
|
||||
condition: []
|
||||
location: europe-west8
|
||||
members:
|
||||
- user:test-user2@example.com
|
||||
project: actual-project-id
|
||||
role: roles/owner
|
||||
google_artifact_registry_repository_iam_binding.authoritative["roles/viewer"]:
|
||||
condition: []
|
||||
location: europe-west8
|
||||
members:
|
||||
- serviceAccount:test@test-project.iam.gserviceaccount.com
|
||||
project: actual-project-id
|
||||
role: roles/viewer
|
||||
google_artifact_registry_repository_iam_binding.bindings2["myrole_two"]:
|
||||
condition:
|
||||
- description: null
|
||||
expression: resource.matchTag('1234567890/environment', 'development')
|
||||
title: Test
|
||||
location: europe-west8
|
||||
members:
|
||||
- serviceAccount:test@test-project.iam.gserviceaccount.com
|
||||
project: actual-project-id
|
||||
role: organizations/366118655033/roles/myRoleTwo
|
||||
google_artifact_registry_repository_iam_member.members["myrole_three"]:
|
||||
condition: []
|
||||
location: europe-west8
|
||||
member: serviceAccount:test@test-project.iam.gserviceaccount.com
|
||||
project: actual-project-id
|
||||
role: organizations/366118655033/roles/myRoleThree
|
||||
google_tags_location_tag_binding.binding["foo"]:
|
||||
location: europe-west8
|
||||
tag_value: tagValues/1234567890
|
||||
timeouts: null
|
||||
|
||||
counts:
|
||||
google_artifact_registry_repository: 1
|
||||
google_artifact_registry_repository_iam_binding: 6
|
||||
google_artifact_registry_repository_iam_member: 1
|
||||
google_tags_location_tag_binding: 1
|
||||
modules: 0
|
||||
resources: 9
|
||||
|
||||
outputs:
|
||||
id: __missing__
|
||||
name: __missing__
|
||||
repository: __missing__
|
||||
url: europe-west8-docker.pkg.dev/actual-project-id/myregistry
|
||||
@@ -15,4 +15,5 @@
|
||||
module: modules/artifact-registry
|
||||
|
||||
tests:
|
||||
context:
|
||||
universe:
|
||||
|
||||
21
tests/modules/cloudsql_instance/context.tfvars
Normal file
21
tests/modules/cloudsql_instance/context.tfvars
Normal file
@@ -0,0 +1,21 @@
|
||||
context = {
|
||||
kms_keys = { mykey = "projects/myprj/locations/europe-west8/keyRings/mykr/cryptoKeys/mykey" }
|
||||
locations = { ew8 = "europe-west8" }
|
||||
networks = { myvpc = "projects/myprj/global/networks/myvpc" }
|
||||
project_ids = { myprj = "my-project" }
|
||||
}
|
||||
project_id = "$project_ids:myprj"
|
||||
region = "$locations:ew8"
|
||||
name = "db-test"
|
||||
database_version = "POSTGRES_13"
|
||||
tier = "db-g1-small"
|
||||
network_config = {
|
||||
connectivity = {
|
||||
psa_config = {
|
||||
private_network = "$networks:myvpc"
|
||||
}
|
||||
}
|
||||
}
|
||||
encryption_key_name = "$kms_keys:mykey"
|
||||
gcp_deletion_protection = false
|
||||
terraform_deletion_protection = false
|
||||
30
tests/modules/cloudsql_instance/context.yaml
Normal file
30
tests/modules/cloudsql_instance/context.yaml
Normal file
@@ -0,0 +1,30 @@
|
||||
# Copyright 2026 Google LLC
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
values:
|
||||
google_sql_database_instance.primary:
|
||||
database_version: POSTGRES_13
|
||||
encryption_key_name: projects/myprj/locations/europe-west8/keyRings/mykr/cryptoKeys/mykey
|
||||
name: db-test
|
||||
project: my-project
|
||||
region: europe-west8
|
||||
settings:
|
||||
- ip_configuration:
|
||||
- ipv4_enabled: false
|
||||
private_network: projects/myprj/global/networks/myvpc
|
||||
|
||||
counts:
|
||||
google_sql_database_instance: 1
|
||||
modules: 0
|
||||
resources: 1
|
||||
18
tests/modules/cloudsql_instance/tftest.yaml
Normal file
18
tests/modules/cloudsql_instance/tftest.yaml
Normal file
@@ -0,0 +1,18 @@
|
||||
# Copyright 2026 Google LLC
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
module: modules/cloudsql-instance
|
||||
|
||||
tests:
|
||||
context:
|
||||
35
tests/modules/net_lb_app_int/context.tfvars
Normal file
35
tests/modules/net_lb_app_int/context.tfvars
Normal file
@@ -0,0 +1,35 @@
|
||||
context = {
|
||||
addresses = {
|
||||
test = "10.0.0.10"
|
||||
}
|
||||
locations = {
|
||||
ew8 = "europe-west8"
|
||||
}
|
||||
networks = {
|
||||
test = "projects/foo-dev-net-spoke-0/global/networks/dev-spoke-0"
|
||||
}
|
||||
project_ids = {
|
||||
test = "foo-test-0"
|
||||
}
|
||||
subnets = {
|
||||
test = "projects/foo-dev-net-spoke-0/regions/europe-west8/subnetworks/gce"
|
||||
test-nat = "projects/foo-dev-net-spoke-0/regions/europe-west8/subnetworks/test-nat"
|
||||
}
|
||||
}
|
||||
project_id = "$project_ids:test"
|
||||
region = "$locations:ew8"
|
||||
vpc_config = {
|
||||
network = "$networks:test"
|
||||
subnetwork = "$subnets:test"
|
||||
}
|
||||
address = "$addresses:test"
|
||||
backend_service_configs = {
|
||||
default = {
|
||||
backends = [{
|
||||
group = "projects/foo-test-0/zones/europe-west8-a/instanceGroups/my-ig"
|
||||
}]
|
||||
}
|
||||
}
|
||||
service_attachment = {
|
||||
nat_subnets = ["$subnets:test-nat"]
|
||||
}
|
||||
49
tests/modules/net_lb_app_int/context.yaml
Normal file
49
tests/modules/net_lb_app_int/context.yaml
Normal file
@@ -0,0 +1,49 @@
|
||||
# Copyright 2026 Google LLC
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
values:
|
||||
google_compute_forwarding_rule.default:
|
||||
ip_address: 10.0.0.10
|
||||
load_balancing_scheme: INTERNAL_MANAGED
|
||||
name: ilb-l7-test
|
||||
network: projects/foo-dev-net-spoke-0/global/networks/dev-spoke-0
|
||||
project: foo-test-0
|
||||
region: europe-west8
|
||||
subnetwork: projects/foo-dev-net-spoke-0/regions/europe-west8/subnetworks/gce
|
||||
google_compute_health_check.default["default"]:
|
||||
project: foo-test-0
|
||||
google_compute_region_backend_service.default["default"]:
|
||||
project: foo-test-0
|
||||
region: europe-west8
|
||||
google_compute_region_target_http_proxy.default[0]:
|
||||
project: foo-test-0
|
||||
region: europe-west8
|
||||
google_compute_region_url_map.default:
|
||||
project: foo-test-0
|
||||
region: europe-west8
|
||||
google_compute_service_attachment.default[0]:
|
||||
nat_subnets:
|
||||
- projects/foo-dev-net-spoke-0/regions/europe-west8/subnetworks/test-nat
|
||||
project: foo-test-0
|
||||
region: europe-west8
|
||||
|
||||
counts:
|
||||
google_compute_forwarding_rule: 1
|
||||
google_compute_health_check: 1
|
||||
google_compute_region_backend_service: 1
|
||||
google_compute_region_target_http_proxy: 1
|
||||
google_compute_region_url_map: 1
|
||||
google_compute_service_attachment: 1
|
||||
modules: 0
|
||||
resources: 6
|
||||
@@ -1,4 +1,4 @@
|
||||
# Copyright 2023 Google LLC
|
||||
# Copyright 2026 Google LLC
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
@@ -16,6 +16,7 @@ module: modules/net-lb-app-int
|
||||
common_tfvars:
|
||||
- common.tfvars
|
||||
tests:
|
||||
context:
|
||||
defaults:
|
||||
groups:
|
||||
health-checks-custom:
|
||||
|
||||
Reference in New Issue
Block a user