Skip to content

Instantly share code, notes, and snippets.

@mvanholsteijn
Created November 30, 2025 02:26
Show Gist options
  • Select an option

  • Save mvanholsteijn/7d2afc35b0d8bcb40e66b5877f1039c5 to your computer and use it in GitHub Desktop.

Select an option

Save mvanholsteijn/7d2afc35b0d8bcb40e66b5877f1039c5 to your computer and use it in GitHub Desktop.
demonstrate policy-access-boundaries with terraform
variable domain {
type = string
}
variable billing_account {
type = string
}
data "google_organization" "current" {
domain = var.domain
}
locals {
domain_as_prefix = lower(join("-", reverse(split(".", var.domain))))
}
resource "google_folder" "business_unit_parent" {
parent = data.google_organization.current.name
display_name = "business-units"
}
resource "google_folder" "business_unit" {
for_each = local.business_units
parent = google_folder.business_unit_parent.name
display_name = each.value
deletion_protection = false
}
resource "google_project" "business_unit" {
for_each = local.business_units
name = each.key
project_id = "${local.domain_as_prefix}-${lower(each.key)}"
folder_id = google_folder.business_unit[each.key].name
billing_account = var.billing_account
deletion_policy = "DELETE"
}
resource "google_project_service" "business_unit" {
for_each = {
for m in setproduct(local.business_units, ["cloud.googleapis.com", "storage.googleapis.com"]) :
"${m[0]}/${m[1]}" => {
project = google_project.business_unit[m[0]].project_id
service = m[1]
}
}
project = each.value.project
service = each.value.service
disable_on_destroy = false
}
resource "google_service_account" "business_unit" {
for_each = local.business_units
account_id = "data-pipeline"
project = google_project.business_unit[each.key].project_id
}
resource google_service_account_iam_binding business_unit_token_creator {
for_each = local.business_units
service_account_id = google_service_account.business_unit[each.key].id
role = "roles/iam.serviceAccountTokenCreator"
members = [
format("user:%s", data.google_client_openid_userinfo.terraformer.email)
]
}
data "google_client_openid_userinfo" "terraformer" {
}
resource google_service_account_iam_binding business_unit_user {
for_each = local.business_units
service_account_id = google_service_account.business_unit[each.key].id
role = "roles/iam.serviceAccountUser"
members = [
format("user:%s", data.google_client_openid_userinfo.terraformer.email)
]
}
locals {
business_units = toset(["BU-001", "BU-002", "BU-003"])
data_sharing_contracts = {
"BU-001" = ["BU-001"]
"BU-002" = ["BU-001", "BU-002"],
"BU-003" = ["BU-001", "BU-002", "BU-003"],
}
}
resource "google_storage_bucket" "business_unit" {
for_each = local.business_units
name = "${local.domain_as_prefix}-${lower(each.key)}-data"
project = google_project.business_unit[each.key].project_id
location = "EU"
force_destroy = true
uniform_bucket_level_access = true
}
resource "google_storage_bucket_iam_binding" "business_unit" {
for_each = google_storage_bucket.business_unit
role = "roles/storage.objectAdmin"
members = [ for sa in google_service_account.business_unit : sa.member ]
bucket = each.value.name
}
resource "google_storage_bucket_object" "index" {
for_each = local.business_units
content_type = "application/html"
name = "index.html"
bucket = google_storage_bucket.business_unit[each.key].name
content = <<-EOF
<!DOCTYPE html>
<html>
<head>
<title>Hello from ${each.key}</title>
</head>
<body>
<h1>Hello World from ${each.key}!</h1>
</body>
</html>
EOF
}
resource "google_iam_principal_access_boundary_policy" "business_unit" {
for_each = local.business_units
organization = reverse(split("/", google_folder.business_unit_parent.parent))[0]
display_name = "data sharing contract enforcement for ${each.key}"
location = "global"
principal_access_boundary_policy_id = lower(each.key)
details {
rules {
effect = "ALLOW"
resources = [for business_unit in local.data_sharing_contracts[each.key] :
format("//cloudresourcemanager.googleapis.com/%s", google_folder.business_unit[business_unit].id)
]
}
}
}
resource "google_iam_folders_policy_binding" "business_unit" {
for_each = local.business_units
folder = google_folder.business_unit[each.key].folder_id
location = "global"
display_name = "data sharing contract enforcement for ${each.key}"
policy_kind = "PRINCIPAL_ACCESS_BOUNDARY"
policy_binding_id = lower(each.key)
policy = google_iam_principal_access_boundary_policy.business_unit[each.key].id
target {
principal_set = format("//cloudresourcemanager.googleapis.com/%s", google_folder.business_unit[each.key].id)
}
}
resource local_file config_gcloud {
filename = "config-gcloud.sh"
file_permission = "0700"
content = join("\n", [
for business_unit in local.business_units :
join("\n", [
"gcloud config configurations create ${lower(business_unit)} --no-activate --quiet",
"gcloud config set account $(gcloud config get account --quiet) --configuration ${lower(business_unit)}",
"gcloud config set core/project ${google_project.business_unit[business_unit].project_id} --configuration ${lower(business_unit)} --quiet",
"gcloud config set auth/impersonate_service_account ${google_service_account.business_unit[business_unit].email} --configuration ${lower(business_unit)} --quiet",
])
]
)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment