diff --git a/fast/stages/1-resman/stage-2-networking.tf b/fast/stages/1-resman/stage-2-networking.tf
index 23c45a834..0abcf0e35 100644
--- a/fast/stages/1-resman/stage-2-networking.tf
+++ b/fast/stages/1-resman/stage-2-networking.tf
@@ -60,35 +60,25 @@ module "net-folder" {
# network security stage 2 service accounts
var.fast_stage_2.network_security.enabled != true ? {} : {
"roles/serviceusage.serviceUsageAdmin" = [
- try(module.nsec-sa-rw[0].iam_email, null)
+ module.nsec-sa-rw[0].iam_email
]
(var.custom_roles["network_firewall_policies_admin"]) = [
- try(module.nsec-sa-rw[0].iam_email, null)
+ module.nsec-sa-rw[0].iam_email
]
"roles/compute.orgFirewallPolicyUser" = [
- try(module.nsec-sa-ro[0].iam_email, null)
+ module.nsec-sa-ro[0].iam_email
]
"roles/serviceusage.serviceUsageConsumer" = [
- try(module.nsec-sa-ro[0].iam_email, null)
+ module.nsec-sa-ro[0].iam_email
]
},
# security stage 2 service accounts
var.fast_stage_2.security.enabled != true ? {} : {
"roles/serviceusage.serviceUsageAdmin" = [
- try(module.sec-sa-rw[0].iam_email, null)
+ module.sec-sa-rw[0].iam_email
]
"roles/serviceusage.serviceUsageConsumer" = [
- try(module.sec-sa-ro[0].iam_email, null)
- ]
- },
- try(var.custom_roles["network_firewall_policies_admin"], null) == null ? {} : {
- (var.custom_roles["network_firewall_policies_admin"]) = [
- try(module.sec-sa-rw[0].iam_email, null)
- ]
- },
- try(var.custom_roles["network_firewall_policies_viewer"], null) == null ? {} : {
- (var.custom_roles["network_firewall_policies_viewer"]) = [
- try(module.sec-sa-ro[0].iam_email, null)
+ module.sec-sa-ro[0].iam_email
]
},
# project factory service accounts
diff --git a/fast/stages/1-tenant-factory/README.md b/fast/stages/1-tenant-factory/README.md
index a3d628cbe..adb91c678 100644
--- a/fast/stages/1-tenant-factory/README.md
+++ b/fast/stages/1-tenant-factory/README.md
@@ -328,13 +328,13 @@ gcloud storage cp gs://{prefix}-{tenant-shortname}-prod-iac-core-0/tfvars/0-boot
|---|---|:---:|:---:|:---:|:---:|
| [automation](variables-fast.tf#L19) | Automation resources created by the bootstrap stage. | object({…}) | ✓ | | 0-bootstrap |
| [billing_account](variables-fast.tf#L42) | Billing account id. If billing account is not part of the same org set `is_org_level` to `false`. To disable handling of billing IAM roles set `no_iam` to `true`. | object({…}) | ✓ | | 0-bootstrap |
-| [logging](variables-fast.tf#L99) | Logging resources created by the bootstrap stage. | object({…}) | ✓ | | 0-bootstrap |
-| [org_policy_tags](variables-fast.tf#L118) | Organization policy tags. | object({…}) | ✓ | | 0-bootstrap |
-| [organization](variables-fast.tf#L108) | Organization details. | object({…}) | ✓ | | 0-bootstrap |
-| [prefix](variables-fast.tf#L135) | Prefix used for resources that need unique names. Use 9 characters or less. | string | ✓ | | 0-bootstrap |
-| [custom_roles](variables-fast.tf#L53) | Custom roles defined at the org level, in key => id format. | object({…}) | | null | 0-bootstrap |
-| [groups](variables-fast.tf#L71) | Group names or IAM-format principals to grant organization-level permissions. If just the name is provided, the 'group:' principal and organization domain are interpolated. | object({…}) | | {} | 0-bootstrap |
-| [locations](variables-fast.tf#L86) | Optional locations for GCS, BigQuery, and logging buckets created here. | object({…}) | | {} | 0-bootstrap |
+| [logging](variables-fast.tf#L97) | Logging resources created by the bootstrap stage. | object({…}) | ✓ | | 0-bootstrap |
+| [org_policy_tags](variables-fast.tf#L116) | Organization policy tags. | object({…}) | ✓ | | 0-bootstrap |
+| [organization](variables-fast.tf#L106) | Organization details. | object({…}) | ✓ | | 0-bootstrap |
+| [prefix](variables-fast.tf#L133) | Prefix used for resources that need unique names. Use 9 characters or less. | string | ✓ | | 0-bootstrap |
+| [custom_roles](variables-fast.tf#L53) | Custom roles defined at the org level, in key => id format. | object({…}) | | null | 0-bootstrap |
+| [groups](variables-fast.tf#L69) | Group names or IAM-format principals to grant organization-level permissions. If just the name is provided, the 'group:' principal and organization domain are interpolated. | object({…}) | | {} | 0-bootstrap |
+| [locations](variables-fast.tf#L84) | Optional locations for GCS, BigQuery, and logging buckets created here. | object({…}) | | {} | 0-bootstrap |
| [outputs_location](variables.tf#L17) | Path where providers and tfvars files for the following stages are written. Leave empty to disable. | string | | null | |
| [root_node](variables.tf#L23) | Root folder under which tenants are created, in folders/nnnn format. Defaults to the organization if null. | string | | null | |
| [tag_names](variables.tf#L36) | Customized names for resource management tags. | object({…}) | | {} | |
diff --git a/fast/stages/1-tenant-factory/variables-fast.tf b/fast/stages/1-tenant-factory/variables-fast.tf
index be76b320a..e8179a2bb 100644
--- a/fast/stages/1-tenant-factory/variables-fast.tf
+++ b/fast/stages/1-tenant-factory/variables-fast.tf
@@ -56,14 +56,12 @@ variable "custom_roles" {
type = object({
gcve_network_admin = string
network_firewall_policies_admin = string
- # TODO: remove after v34.0.0
- network_firewall_policies_viewer = optional(string)
- ngfw_enterprise_admin = optional(string)
- ngfw_enterprise_viewer = optional(string)
- organization_admin_viewer = string
- service_project_network_admin = string
- storage_viewer = string
- tenant_network_admin = string
+ ngfw_enterprise_admin = optional(string)
+ ngfw_enterprise_viewer = optional(string)
+ organization_admin_viewer = string
+ service_project_network_admin = string
+ storage_viewer = string
+ tenant_network_admin = string
})
default = null
}
diff --git a/tests/fast/stages/s1_resman/simple.tfvars b/tests/fast/stages/s1_resman/simple.tfvars
index 0f73afb84..ce8f7894f 100644
--- a/tests/fast/stages/s1_resman/simple.tfvars
+++ b/tests/fast/stages/s1_resman/simple.tfvars
@@ -53,17 +53,16 @@ automation = {
}
custom_roles = {
# organization_iam_admin = "organizations/123456789012/roles/organizationIamAdmin",
- billing_viewer = "organizations/123456789012/roles/billingViewer"
- gcve_network_admin = "organizations/123456789012/roles/gcveNetworkAdmin"
- gcve_network_viewer = "organizations/123456789012/roles/gcveNetworkViewer"
- network_firewall_policies_admin = "organizations/123456789012/roles/networkFirewallPoliciesAdmin"
- network_firewall_policies_viewer = "organizations/123456789012/roles/networkFirewallPoliciesViewer"
- ngfw_enterprise_admin = "organizations/123456789012/roles/ngfwEnterpriseAdmin"
- ngfw_enterprise_viewer = "organizations/123456789012/roles/ngfwEnterpriseViewer"
- organization_admin_viewer = "organizations/123456789012/roles/organizationAdminViewer"
- project_iam_viewer = "organizations/123456789012/roles/projectIamViewer"
- service_project_network_admin = "organizations/123456789012/roles/xpnServiceAdmin"
- storage_viewer = "organizations/123456789012/roles/storageViewer"
+ billing_viewer = "organizations/123456789012/roles/billingViewer"
+ gcve_network_admin = "organizations/123456789012/roles/gcveNetworkAdmin"
+ gcve_network_viewer = "organizations/123456789012/roles/gcveNetworkViewer"
+ network_firewall_policies_admin = "organizations/123456789012/roles/networkFirewallPoliciesAdmin"
+ ngfw_enterprise_admin = "organizations/123456789012/roles/ngfwEnterpriseAdmin"
+ ngfw_enterprise_viewer = "organizations/123456789012/roles/ngfwEnterpriseViewer"
+ organization_admin_viewer = "organizations/123456789012/roles/organizationAdminViewer"
+ project_iam_viewer = "organizations/123456789012/roles/projectIamViewer"
+ service_project_network_admin = "organizations/123456789012/roles/xpnServiceAdmin"
+ storage_viewer = "organizations/123456789012/roles/storageViewer"
}
environments = {
dev = {
@@ -103,6 +102,9 @@ fast_stage_2 = {
}
}
}
+ network_security = {
+ enabled = true
+ }
}
tags = {
context = {
diff --git a/tests/fast/stages/s1_resman/simple.yaml b/tests/fast/stages/s1_resman/simple.yaml
index ba844c38e..bab547be2 100644
--- a/tests/fast/stages/s1_resman/simple.yaml
+++ b/tests/fast/stages/s1_resman/simple.yaml
@@ -13,6 +13,81 @@
# limitations under the License.
values:
+ google_storage_bucket_object.providers["1-resman-folder-sandbox"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/1-resman-folder-sandbox-providers.tf
+ google_storage_bucket_object.providers["1-resman-folder-tenants"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/1-resman-folder-tenants-providers.tf
+ google_storage_bucket_object.providers["2-network-security"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/2-network-security-providers.tf
+ google_storage_bucket_object.providers["2-network-security-r"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/2-network-security-r-providers.tf
+ google_storage_bucket_object.providers["2-networking"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/2-networking-providers.tf
+ google_storage_bucket_object.providers["2-networking-r"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/2-networking-r-providers.tf
+ google_storage_bucket_object.providers["2-project-factory"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/2-project-factory-providers.tf
+ google_storage_bucket_object.providers["2-project-factory-r"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/2-project-factory-r-providers.tf
+ google_storage_bucket_object.providers["2-security"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/2-security-providers.tf
+ google_storage_bucket_object.providers["2-security-r"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/2-security-r-providers.tf
+ google_storage_bucket_object.providers["3-gcve-dev"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/3-gcve-dev-providers.tf
+ google_storage_bucket_object.providers["3-gcve-dev-r"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/3-gcve-dev-r-providers.tf
+ google_storage_bucket_object.providers["3-gcve-prod"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/3-gcve-prod-providers.tf
+ google_storage_bucket_object.providers["3-gcve-prod-r"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/3-gcve-prod-r-providers.tf
+ google_storage_bucket_object.providers["3-gke-dev"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/3-gke-dev-providers.tf
+ google_storage_bucket_object.providers["3-gke-dev-r"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/3-gke-dev-r-providers.tf
+ google_storage_bucket_object.providers["3-gke-prod"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/3-gke-prod-providers.tf
+ google_storage_bucket_object.providers["3-gke-prod-r"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/3-gke-prod-r-providers.tf
+ google_storage_bucket_object.providers["3-project-factory-dev"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/3-project-factory-dev-providers.tf
+ google_storage_bucket_object.providers["3-project-factory-dev-r"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/3-project-factory-dev-r-providers.tf
+ google_storage_bucket_object.providers["3-project-factory-prod"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/3-project-factory-prod-providers.tf
+ google_storage_bucket_object.providers["3-project-factory-prod-r"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: providers/3-project-factory-prod-r-providers.tf
+ google_storage_bucket_object.tfvars:
+ bucket: fast2-prod-iac-core-outputs
+ name: tfvars/1-resman.auto.tfvars.json
+ google_storage_bucket_object.workflows["networking"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: workflows/networking-workflow.yaml
+ google_storage_bucket_object.workflows["security"]:
+ bucket: fast2-prod-iac-core-outputs
+ name: workflows/security-workflow.yaml
module.cicd-sa-ro["networking"].google_project_iam_member.project-roles["fast2-prod-automation-roles/logging.logWriter"]:
condition: []
project: fast2-prod-automation
@@ -154,7 +229,7 @@ values:
? module.net-folder[0].google_folder_iam_binding.authoritative["organizations/123456789012/roles/networkFirewallPoliciesAdmin"]
: condition: []
members:
- - serviceAccount:fast2-prod-resman-sec-0@fast2-prod-automation.iam.gserviceaccount.com
+ - serviceAccount:fast2-resman-nsec-0@fast2-prod-automation.iam.gserviceaccount.com
role: organizations/123456789012/roles/networkFirewallPoliciesAdmin
module.net-folder[0].google_folder_iam_binding.authoritative["organizations/123456789012/roles/projectIamViewer"]:
condition: []
@@ -171,6 +246,11 @@ values:
members:
- serviceAccount:fast2-resman-pf-0r@fast2-prod-automation.iam.gserviceaccount.com
role: roles/compute.networkViewer
+ module.net-folder[0].google_folder_iam_binding.authoritative["roles/compute.orgFirewallPolicyUser"]:
+ condition: []
+ members:
+ - serviceAccount:fast2-resman-nsec-0r@fast2-prod-automation.iam.gserviceaccount.com
+ role: roles/compute.orgFirewallPolicyUser
module.net-folder[0].google_folder_iam_binding.authoritative["roles/compute.xpnAdmin"]:
condition: []
members:
@@ -356,6 +436,83 @@ values:
bucket: fast2-prod-iac-core-outputs
condition: []
role: roles/storage.objectAdmin
+ module.nsec-bucket[0].google_storage_bucket.bucket:
+ autoclass: []
+ cors: []
+ custom_placement_config: []
+ default_event_based_hold: null
+ effective_labels:
+ goog-terraform-provisioned: 'true'
+ enable_object_retention: null
+ encryption: []
+ force_destroy: false
+ labels: null
+ lifecycle_rule: []
+ location: EU
+ logging: []
+ name: fast2-resman-nsec-0
+ project: fast2-prod-automation
+ requester_pays: null
+ retention_policy: []
+ storage_class: STANDARD
+ terraform_labels:
+ goog-terraform-provisioned: 'true'
+ timeouts: null
+ uniform_bucket_level_access: true
+ versioning:
+ - enabled: true
+ module.nsec-bucket[0].google_storage_bucket_iam_binding.authoritative["roles/storage.objectAdmin"]:
+ bucket: fast2-resman-nsec-0
+ condition: []
+ members:
+ - serviceAccount:fast2-resman-nsec-0@fast2-prod-automation.iam.gserviceaccount.com
+ role: roles/storage.objectAdmin
+ module.nsec-bucket[0].google_storage_bucket_iam_binding.authoritative["roles/storage.objectViewer"]:
+ bucket: fast2-resman-nsec-0
+ condition: []
+ members:
+ - serviceAccount:fast2-resman-nsec-0r@fast2-prod-automation.iam.gserviceaccount.com
+ role: roles/storage.objectViewer
+ ? module.nsec-sa-ro[0].google_project_iam_member.project-roles["fast2-prod-automation-roles/serviceusage.serviceUsageConsumer"]
+ : condition: []
+ project: fast2-prod-automation
+ role: roles/serviceusage.serviceUsageConsumer
+ module.nsec-sa-ro[0].google_service_account.service_account[0]:
+ account_id: fast2-resman-nsec-0r
+ create_ignore_already_exists: null
+ description: null
+ disabled: false
+ display_name: Terraform resman network security main service account (read-only).
+ project: fast2-prod-automation
+ timeouts: null
+ module.nsec-sa-ro[0].google_service_account_iam_binding.authoritative["roles/iam.serviceAccountTokenCreator"]:
+ condition: []
+ members: null
+ role: roles/iam.serviceAccountTokenCreator
+ ? module.nsec-sa-ro[0].google_storage_bucket_iam_member.bucket-roles["fast2-prod-iac-core-outputs-organizations/123456789012/roles/storageViewer"]
+ : bucket: fast2-prod-iac-core-outputs
+ condition: []
+ role: organizations/123456789012/roles/storageViewer
+ ? module.nsec-sa-rw[0].google_project_iam_member.project-roles["fast2-prod-automation-roles/serviceusage.serviceUsageConsumer"]
+ : condition: []
+ project: fast2-prod-automation
+ role: roles/serviceusage.serviceUsageConsumer
+ module.nsec-sa-rw[0].google_service_account.service_account[0]:
+ account_id: fast2-resman-nsec-0
+ create_ignore_already_exists: null
+ description: null
+ disabled: false
+ display_name: Terraform resman network security main service account.
+ project: fast2-prod-automation
+ timeouts: null
+ module.nsec-sa-rw[0].google_service_account_iam_binding.authoritative["roles/iam.serviceAccountTokenCreator"]:
+ condition: []
+ members: null
+ role: roles/iam.serviceAccountTokenCreator
+ ? module.nsec-sa-rw[0].google_storage_bucket_iam_member.bucket-roles["fast2-prod-iac-core-outputs-roles/storage.objectAdmin"]
+ : bucket: fast2-prod-iac-core-outputs
+ condition: []
+ role: roles/storage.objectAdmin
module.organization[0].google_organization_iam_member.bindings["gcve-dev"]:
condition: []
member: serviceAccount:fast2-dev-resman-gcve-0@fast2-prod-automation.iam.gserviceaccount.com
@@ -396,11 +553,31 @@ values:
member: serviceAccount:fast2-prod-resman-net-0@fast2-prod-automation.iam.gserviceaccount.com
org_id: '123456789012'
role: roles/compute.orgFirewallPolicyAdmin
+ module.organization[0].google_organization_iam_member.bindings["sa_net_nsec_fw_policy_user"]:
+ condition: []
+ member: serviceAccount:fast2-resman-nsec-0@fast2-prod-automation.iam.gserviceaccount.com
+ org_id: '123456789012'
+ role: roles/compute.orgFirewallPolicyUser
+ module.organization[0].google_organization_iam_member.bindings["sa_net_nsec_ngfw_enterprise_admin"]:
+ condition: []
+ member: serviceAccount:fast2-resman-nsec-0@fast2-prod-automation.iam.gserviceaccount.com
+ org_id: '123456789012'
+ role: organizations/123456789012/roles/ngfwEnterpriseAdmin
+ module.organization[0].google_organization_iam_member.bindings["sa_net_nsec_ro_ngfw_enterprise_viewer"]:
+ condition: []
+ member: serviceAccount:fast2-resman-nsec-0r@fast2-prod-automation.iam.gserviceaccount.com
+ org_id: '123456789012'
+ role: organizations/123456789012/roles/ngfwEnterpriseViewer
module.organization[0].google_organization_iam_member.bindings["sa_net_xpn_admin"]:
condition: []
member: serviceAccount:fast2-prod-resman-net-0@fast2-prod-automation.iam.gserviceaccount.com
org_id: '123456789012'
role: roles/compute.xpnAdmin
+ module.organization[0].google_organization_iam_member.bindings["sa_nsec_fw_policy_admin"]:
+ condition: []
+ member: serviceAccount:fast2-resman-nsec-0@fast2-prod-automation.iam.gserviceaccount.com
+ org_id: '123456789012'
+ role: roles/compute.orgFirewallPolicyAdmin
module.organization[0].google_organization_iam_member.bindings["sa_pf_billing"]:
condition: []
member: serviceAccount:fast2-resman-pf-0@fast2-prod-automation.iam.gserviceaccount.com
@@ -462,6 +639,10 @@ values:
description: Managed by the Terraform organization module.
short_name: gke
timeouts: null
+ module.organization[0].google_tags_tag_value.default["context/network-security"]:
+ description: Managed by the Terraform organization module.
+ short_name: network-security
+ timeouts: null
module.organization[0].google_tags_tag_value.default["context/networking"]:
description: Managed by the Terraform organization module.
short_name: networking
@@ -1575,18 +1756,36 @@ values:
counts:
google_folder: 13
- google_folder_iam_binding: 74
- google_organization_iam_member: 15
- google_project_iam_member: 24
- google_service_account: 24
- google_service_account_iam_binding: 24
- google_storage_bucket: 11
- google_storage_bucket_iam_binding: 22
- google_storage_bucket_iam_member: 24
- google_storage_bucket_object: 23
+ google_folder_iam_binding: 75
+ google_organization_iam_member: 19
+ google_project_iam_member: 26
+ google_service_account: 26
+ google_service_account_iam_binding: 26
+ google_storage_bucket: 12
+ google_storage_bucket_iam_binding: 24
+ google_storage_bucket_iam_member: 26
+ google_storage_bucket_object: 25
google_tags_tag_binding: 13
google_tags_tag_key: 2
- google_tags_tag_value: 11
+ google_tags_tag_value: 12
google_tags_tag_value_iam_binding: 4
- modules: 49
- resources: 284
+ modules: 52
+ resources: 303
+
+outputs:
+ cicd_repositories:
+ networking:
+ provider: projects/1234567890/locations/global/workloadIdentityPools/ldj-bootstrap/providers/ldj-bootstrap-github-ludomagno
+ repository:
+ branch: main
+ name: test/00-networking
+ parent_id: null
+ type: github
+ security:
+ provider: projects/1234567890/locations/global/workloadIdentityPools/ldj-bootstrap/providers/ldj-bootstrap-gitlab-ludomagno
+ repository:
+ branch: null
+ name: test/00-security
+ type: gitlab
+ folder_ids: __missing__
+ tfvars: __missing__