Created
April 1, 2022 00:23
-
-
Save olliefr/7a5c0d700d50fa120c38a0fbe4925b43 to your computer and use it in GitHub Desktop.
Making sense of Terraform Google provider's google_organization_policy and compute.vmExternalIpAccess constraint.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
terraform { | |
required_version = "~> 1.1.7" | |
required_providers { | |
google = "~>4.12.0" | |
} | |
experiments = [module_variable_optional_attrs] | |
} | |
variable "gcp_organisation" { | |
default = "1054101600813" | |
} | |
# "gcp.resourceLocations" = { | |
# list_policy = { | |
# allow = { | |
# values = [ | |
# "in:europe-locations" | |
# ] | |
# } | |
# } | |
# } | |
locals { | |
project_id = "pj-terraform-master-rsid" | |
zone = "europe-west2-c" | |
list_policy = { | |
# allow = { | |
# values = [ | |
# "projects/${project_id}/zones/${zone}/instances/instance-a", | |
# "in:europe-locations", | |
# ] | |
# all = true | |
# } | |
deny = { | |
# values = [ | |
# "projects/${local.project_id}/zones/${local.zone}/instances/instance-a", | |
## "in:europe-locations" | |
# ] | |
all = true | |
} | |
} | |
new_list_policy = { | |
for k,v in local.list_policy: (lookup(v, "all", false) ? "${k}_all" : k) => v | |
} | |
} | |
#output "result" { | |
# value = local.new_list_policy | |
#} | |
# This resource has been superseded by `google_org_policy_policy`. | |
# `google_org_policy_policy` uses Organization Policy API V2 instead of | |
# Cloud Resource Manager API V1 and it supports additional features such as tags and conditions. | |
# https://registry.terraform.io/providers/hashicorp/google/latest/docs/resources/google_organization_policy | |
# Google constraint documentation | |
# https://cloud.google.com/compute/docs/ip-addresses/reserve-static-external-ip-address#disableexternalip | |
resource "google_organization_policy" "compute_vm_external_ip_access" { | |
org_id = var.gcp_organisation | |
constraint = "compute.vmExternalIpAccess" | |
# WARNING! This is hackish but it suits the need right now. | |
dynamic "list_policy" { | |
for_each = local.new_list_policy[*] | |
content { | |
dynamic "allow" { | |
for_each = lookup(list_policy.value, "allow", null)[*] | |
content { | |
values = allow.value.values | |
} | |
} | |
dynamic "allow" { | |
for_each = lookup(list_policy.value, "allow_all", null)[*] | |
content { | |
all = true | |
} | |
} | |
dynamic "deny" { | |
for_each = lookup(list_policy.value, "deny", null)[*] | |
content { | |
values = deny.value.values | |
} | |
} | |
dynamic "deny" { | |
for_each = lookup(list_policy.value, "deny_all", null)[*] | |
content { | |
all = true | |
} | |
} | |
} | |
} | |
# list_policy { | |
# | |
## # Enable for 'all': plan OK, apply OK | |
## allow { | |
## all = true | |
## } | |
# | |
## # Enable for 'all': plan OK, apply ERROR | |
## deny { | |
## all = false | |
## } | |
# | |
## # Disable for 'all': plan OK, apply OK | |
## deny { | |
## all = true | |
## } | |
# | |
## # Disable for 'all': plan OK, apply ERROR | |
## allow { | |
## all = false | |
## } | |
# | |
# ## | |
# ## Conclusion: when `all` keyword is used, the only valid value is `true`. Pair with `allow` or `deny`. | |
# ## | |
# | |
## # Disable for 'all': plan OK, apply ERROR | |
## # This translates into `all = false` in the plan. | |
## allow { | |
## values = [] | |
## } | |
# | |
## # Enable for 'all': plan OK, apply ERROR | |
## # This translates into `all = false` in the plan. | |
## deny { | |
## values = [] | |
## } | |
# | |
# ## | |
# ## Conclusion: empty list of values plans OK but does not work | |
# ## | |
# } | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment