Remove firewall policy management from resource management modules (#1581)

* rename firewall policy module, fix outputs

* add TOC to firewall policy module

* don't depend policy on parent id

* remove firewall policy from resource management modules

* remove factory conditionals

* fast net a and b

* fast stages

* fast tfdoc

* fast tfdoc

* remove unused test

* fix shielded folder blueprint

* fix shielded folder blueprint
This commit is contained in:
Ludovico Magnocavallo 2023-08-09 13:23:07 +02:00 committed by GitHub
parent b7ff8f0933
commit 79373721df
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
58 changed files with 1040 additions and 1017 deletions

View File

@ -30,7 +30,7 @@ The current list of modules supports most of the core foundational and networkin
Currently available modules: Currently available modules:
- **foundational** - [billing budget](./modules/billing-budget), [Cloud Identity group](./modules/cloud-identity-group/), [folder](./modules/folder), [service accounts](./modules/iam-service-account), [logging bucket](./modules/logging-bucket), [organization](./modules/organization), [project](./modules/project), [projects-data-source](./modules/projects-data-source) - **foundational** - [billing budget](./modules/billing-budget), [Cloud Identity group](./modules/cloud-identity-group/), [folder](./modules/folder), [service accounts](./modules/iam-service-account), [logging bucket](./modules/logging-bucket), [organization](./modules/organization), [project](./modules/project), [projects-data-source](./modules/projects-data-source)
- **networking** - [DNS](./modules/dns), [DNS Response Policy](./modules/dns-response-policy/), [Cloud Endpoints](./modules/endpoints), [address reservation](./modules/net-address), [NAT](./modules/net-cloudnat), [VLAN Attachment](./modules/net-vlan-attachment/), [External Application LB](./modules/net-lb-app-ext/), [External Passthrough Network LB](./modules/net-lb-ext), [Internal Application LB](./modules/net-lb-app-int), [Internal Passthrough Network LB](./modules/net-lb-int), [Internal Proxy Network LB](./modules/net-lb-proxy-int), [IPSec over Interconnect](./modules/net-ipsec-over-interconnect), [VPC](./modules/net-vpc), [VPC firewall](./modules/net-vpc-firewall), [VPC firewall policy](./modules/net-vpc-firewall-policy), [VPC peering](./modules/net-vpc-peering), [VPN dynamic](./modules/net-vpn-dynamic), [HA VPN](./modules/net-vpn-ha), [VPN static](./modules/net-vpn-static), [Service Directory](./modules/service-directory), [Secure Web Proxy](./modules/net-swp) - **networking** - [DNS](./modules/dns), [DNS Response Policy](./modules/dns-response-policy/), [Cloud Endpoints](./modules/endpoints), [address reservation](./modules/net-address), [NAT](./modules/net-cloudnat), [VLAN Attachment](./modules/net-vlan-attachment/), [External Application LB](./modules/net-lb-app-ext/), [External Passthrough Network LB](./modules/net-lb-ext), [Firewall policy](./modules/net-firewall-policy), [Internal Application LB](./modules/net-lb-app-int), [Internal Passthrough Network LB](./modules/net-lb-int), [Internal Proxy Network LB](./modules/net-lb-proxy-int), [IPSec over Interconnect](./modules/net-ipsec-over-interconnect), [VPC](./modules/net-vpc), [VPC firewall](./modules/net-vpc-firewall), [VPC peering](./modules/net-vpc-peering), [VPN dynamic](./modules/net-vpn-dynamic), [HA VPN](./modules/net-vpn-ha), [VPN static](./modules/net-vpn-static), [Service Directory](./modules/service-directory), [Secure Web Proxy](./modules/net-swp)
- **compute** - [VM/VM group](./modules/compute-vm), [MIG](./modules/compute-mig), [COS container](./modules/cloud-config-container/cos-generic-metadata/) (coredns, mysql, onprem, squid), [GKE cluster](./modules/gke-cluster-standard), [GKE hub](./modules/gke-hub), [GKE nodepool](./modules/gke-nodepool) - **compute** - [VM/VM group](./modules/compute-vm), [MIG](./modules/compute-mig), [COS container](./modules/cloud-config-container/cos-generic-metadata/) (coredns, mysql, onprem, squid), [GKE cluster](./modules/gke-cluster-standard), [GKE hub](./modules/gke-hub), [GKE nodepool](./modules/gke-nodepool)
- **data** - [AlloyDB instance](./modules/alloydb-instance), [BigQuery dataset](./modules/bigquery-dataset), [Bigtable instance](./modules/bigtable-instance), [Dataplex](./modules/dataplex), [Dataplex DataScan](./modules/dataplex-datascan/), [Cloud SQL instance](./modules/cloudsql-instance), [Data Catalog Policy Tag](./modules/data-catalog-policy-tag), [Datafusion](./modules/datafusion), [Dataproc](./modules/dataproc), [GCS](./modules/gcs), [Pub/Sub](./modules/pubsub) - **data** - [AlloyDB instance](./modules/alloydb-instance), [BigQuery dataset](./modules/bigquery-dataset), [Bigtable instance](./modules/bigtable-instance), [Dataplex](./modules/dataplex), [Dataplex DataScan](./modules/dataplex-datascan/), [Cloud SQL instance](./modules/cloudsql-instance), [Data Catalog Policy Tag](./modules/data-catalog-policy-tag), [Datafusion](./modules/datafusion), [Dataproc](./modules/dataproc), [GCS](./modules/gcs), [Pub/Sub](./modules/pubsub)
- **development** - [API Gateway](./modules/api-gateway), [Apigee](./modules/apigee), [Artifact Registry](./modules/artifact-registry), [Container Registry](./modules/container-registry), [Cloud Source Repository](./modules/source-repository) - **development** - [API Gateway](./modules/api-gateway), [Apigee](./modules/apigee), [Artifact Registry](./modules/artifact-registry), [Container Registry](./modules/container-registry), [Cloud Source Repository](./modules/source-repository)

View File

@ -209,5 +209,5 @@ module "test" {
billing_account_id = "123456-123456-123456" billing_account_id = "123456-123456-123456"
} }
} }
# tftest modules=6 resources=38 inventory=simple.yaml # tftest modules=7 resources=38
``` ```

View File

@ -0,0 +1,37 @@
# skip boilerplate check
allow-admins:
description: Access from the admin subnet to all subnets
priority: 1000
match:
source_ranges:
- rfc1918
allow-healthchecks:
description: Enable HTTP and HTTPS healthchecks
priority: 1001
match:
source_ranges:
- healthchecks
layer4_configs:
- protocol: tcp
ports: ["80", "443"]
allow-ssh-from-iap:
description: Enable SSH from IAP
priority: 1002
match:
source_ranges:
- 35.235.240.0/20
layer4_configs:
- protocol: tcp
ports: ["22"]
allow-icmp:
description: Enable ICMP
priority: 1003
match:
source_ranges:
- 0.0.0.0/0
layer4_configs:
- protocol: icmp

View File

@ -1,50 +0,0 @@
# skip boilerplate check
allow-admins:
description: Access from the admin subnet to all subnets
direction: INGRESS
action: allow
priority: 1000
ranges:
- $rfc1918
ports:
all: []
target_resources: null
enable_logging: false
allow-healthchecks:
description: Enable HTTP and HTTPS healthchecks
direction: INGRESS
action: allow
priority: 1001
ranges:
- $healthchecks
ports:
tcp: ["80", "443"]
target_resources: null
enable_logging: false
allow-ssh-from-iap:
description: Enable SSH from IAP
direction: INGRESS
action: allow
priority: 1002
ranges:
- 35.235.240.0/20
ports:
tcp: ["22"]
target_resources: null
enable_logging: false
allow-icmp:
description: Enable ICMP
direction: INGRESS
action: allow
priority: 1003
ranges:
- 0.0.0.0/0
ports:
icmp: []
target_resources: null
enable_logging: false

View File

@ -78,11 +78,6 @@ module "folder" {
id = var.folder_config.folder_create != null ? null : var.folder_config.folder_id id = var.folder_config.folder_create != null ? null : var.folder_config.folder_id
group_iam = local.group_iam group_iam = local.group_iam
org_policies_data_path = var.data_dir != null ? "${var.data_dir}/org-policies" : null org_policies_data_path = var.data_dir != null ? "${var.data_dir}/org-policies" : null
firewall_policy_factory = var.data_dir != null ? {
cidr_file = "${var.data_dir}/firewall-policies/cidrs.yaml"
policy_name = "${var.prefix}-fw-policy"
rules_file = "${var.data_dir}/firewall-policies/hierarchical-policy-rules.yaml"
} : null
logging_sinks = var.enable_features.log_sink ? { logging_sinks = var.enable_features.log_sink ? {
for name, attrs in var.log_sinks : name => { for name, attrs in var.log_sinks : name => {
bq_partitioned_table = attrs.type == "bigquery" bq_partitioned_table = attrs.type == "bigquery"
@ -93,14 +88,24 @@ module "folder" {
} : null } : null
} }
module "firewall-policy" {
source = "../../../modules/net-firewall-policy"
name = "default"
parent_id = module.folder.id
rules_factory_config = var.data_dir == null ? {} : {
cidr_file_path = "${var.data_dir}/firewall-policies/cidrs.yaml"
ingress_rules_file_path = "${var.data_dir}/firewall-policies/hierarchical-ingress-rules.yaml"
}
}
module "folder-workload" { module "folder-workload" {
source = "../../../modules/folder" source = "../../../modules/folder"
parent = module.folder.id parent = module.folder.id
name = "${var.prefix}-workload" name = "${var.prefix}-workload"
} }
#TODO VPCSC: Access levels
#TODO VPCSC: Access levels
data "google_projects" "folder-projects" { data "google_projects" "folder-projects" {
filter = "parent.id:${split("/", module.folder.id)[1]}" filter = "parent.id:${split("/", module.folder.id)[1]}"

View File

@ -172,7 +172,7 @@ Static routes are defined in `vpc-*.tf` files, in the `routes` section of each `
**VPC firewall rules** ([`net-vpc-firewall`](../../../modules/net-vpc-firewall)) are defined per-vpc on each `vpc-*.tf` file and leverage a resource factory to massively create rules. **VPC firewall rules** ([`net-vpc-firewall`](../../../modules/net-vpc-firewall)) are defined per-vpc on each `vpc-*.tf` file and leverage a resource factory to massively create rules.
To add a new firewall rule, create a new file or edit an existing one in the `data_folder` directory defined in the module `net-vpc-firewall`, following the examples of the "[Rules factory](../../../modules/net-vpc-firewall#rules-factory)" section of the module documentation. Sample firewall rules are shipped in [data/firewall-rules/landing](./data/firewall-rules/landing) and can be easily customised. To add a new firewall rule, create a new file or edit an existing one in the `data_folder` directory defined in the module `net-vpc-firewall`, following the examples of the "[Rules factory](../../../modules/net-vpc-firewall#rules-factory)" section of the module documentation. Sample firewall rules are shipped in [data/firewall-rules/landing](./data/firewall-rules/landing) and can be easily customised.
**Hierarchical firewall policies** ([`folder`](../../../modules/folder)) are defined in `main.tf`, and managed through a policy factory implemented by the `folder` module, which applies the defined hierarchical to the `Networking` folder, which contains all the core networking infrastructure. Policies are defined in the `rules_file` file - to define a new one simply use the instructions found on "[Firewall policy factory](../../../modules/organization#firewall-policy-factory)". Sample hierarchical firewall policies are shipped in [data/hierarchical-policy-rules.yaml](./data/hierarchical-policy-rules.yaml) and can be easily customised. **Hierarchical firewall policies** ([`folder`](../../../modules/folder)) are defined in `main.tf` and managed through a policy factory implemented by the `net-firewall-policy` module, which is then applied to the `Networking` folder containing all the core networking infrastructure. Policies are defined in the `rules_file` file, to define a new one simply use the [firewall policy module documentation](../../../modules/net-firewall-policy/README.md#factory)". Sample hierarchical firewall rules are shipped in [data/hierarchical-ingress-rules.yaml](./data/hierarchical-ingress-rules.yaml) and can be easily customised.
### DNS architecture ### DNS architecture
@ -378,7 +378,7 @@ DNS configurations are centralised in the `dns-*.tf` files. Spokes delegate DNS
| [dns-landing.tf](./dns-landing.tf) | Landing DNS zones and peerings setup. | <code>dns</code> · <code>dns-response-policy</code> | | | [dns-landing.tf](./dns-landing.tf) | Landing DNS zones and peerings setup. | <code>dns</code> · <code>dns-response-policy</code> | |
| [dns-prod.tf](./dns-prod.tf) | Production spoke DNS zones and peerings setup. | <code>dns</code> | | | [dns-prod.tf](./dns-prod.tf) | Production spoke DNS zones and peerings setup. | <code>dns</code> | |
| [landing.tf](./landing.tf) | Landing VPC and related resources. | <code>net-cloudnat</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>project</code> | | | [landing.tf](./landing.tf) | Landing VPC and related resources. | <code>net-cloudnat</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>project</code> | |
| [main.tf](./main.tf) | Networking folder and hierarchical policy. | <code>folder</code> | | | [main.tf](./main.tf) | Networking folder and hierarchical policy. | <code>folder</code> · <code>net-firewall-policy</code> | |
| [monitoring-vpn-onprem.tf](./monitoring-vpn-onprem.tf) | VPN monitoring alerts. | | <code>google_monitoring_alert_policy</code> | | [monitoring-vpn-onprem.tf](./monitoring-vpn-onprem.tf) | VPN monitoring alerts. | | <code>google_monitoring_alert_policy</code> |
| [monitoring.tf](./monitoring.tf) | Network monitoring dashboards. | | <code>google_monitoring_dashboard</code> | | [monitoring.tf](./monitoring.tf) | Network monitoring dashboards. | | <code>google_monitoring_dashboard</code> |
| [outputs.tf](./outputs.tf) | Module outputs. | | <code>google_storage_bucket_object</code> · <code>local_file</code> | | [outputs.tf](./outputs.tf) | Module outputs. | | <code>google_storage_bucket_object</code> · <code>local_file</code> |

View File

@ -0,0 +1,37 @@
# skip boilerplate check
allow-admins:
description: Access from the admin subnet to all subnets
priority: 1000
match:
source_ranges:
- rfc1918
allow-healthchecks:
description: Enable HTTP and HTTPS healthchecks
priority: 1001
match:
source_ranges:
- healthchecks
layer4_configs:
- protocol: tcp
ports: ["80", "443"]
allow-ssh-from-iap:
description: Enable SSH from IAP
priority: 1002
match:
source_ranges:
- 35.235.240.0/20
layer4_configs:
- protocol: tcp
ports: ["22"]
allow-icmp:
description: Enable ICMP
priority: 1003
match:
source_ranges:
- 0.0.0.0/0
layer4_configs:
- protocol: icmp

View File

@ -1,49 +0,0 @@
# skip boilerplate check
allow-admins:
description: Access from the admin subnet to all subnets
direction: INGRESS
action: allow
priority: 1000
ranges:
- $rfc1918
ports:
all: []
target_resources: null
enable_logging: false
allow-healthchecks:
description: Enable HTTP and HTTPS healthchecks
direction: INGRESS
action: allow
priority: 1001
ranges:
- $healthchecks
ports:
tcp: ["80", "443"]
target_resources: null
enable_logging: false
allow-ssh-from-iap:
description: Enable SSH from IAP
direction: INGRESS
action: allow
priority: 1002
ranges:
- 35.235.240.0/20
ports:
tcp: ["22"]
target_resources: null
enable_logging: false
allow-icmp:
description: Enable ICMP
direction: INGRESS
action: allow
priority: 1003
ranges:
- 0.0.0.0/0
ports:
icmp: []
target_resources: null
enable_logging: false

View File

@ -45,13 +45,18 @@ module "folder" {
name = "Networking" name = "Networking"
folder_create = var.folder_ids.networking == null folder_create = var.folder_ids.networking == null
id = var.folder_ids.networking id = var.folder_ids.networking
firewall_policy_factory = { firewall_policy_associations = {
cidr_file = "${var.factories_config.data_dir}/cidrs.yaml" default = module.firewall-policy-default.id
policy_name = var.factories_config.firewall_policy_name }
rules_file = "${var.factories_config.data_dir}/hierarchical-policy-rules.yaml" }
}
firewall_policy_association = { module "firewall-policy-default" {
factory-policy = "factory" source = "../../../modules/net-firewall-policy"
name = "net-default"
parent_id = module.folder.id
rules_factory_config = {
cidr_file_path = "${var.factories_config.data_dir}/cidrs.yaml"
ingress_rules_file_path = "${var.factories_config.data_dir}/hierarchical-ingress-rules.yaml"
} }
} }

View File

@ -186,7 +186,7 @@ BGP sessions for landing-spoke are configured through variable `vpn_spoke_config
**VPC firewall rules** ([`net-vpc-firewall`](../../../modules/net-vpc-firewall)) are defined per-vpc on each `vpc-*.tf` file and leverage a resource factory to massively create rules. **VPC firewall rules** ([`net-vpc-firewall`](../../../modules/net-vpc-firewall)) are defined per-vpc on each `vpc-*.tf` file and leverage a resource factory to massively create rules.
To add a new firewall rule, create a new file or edit an existing one in the `data_folder` directory defined in the module `net-vpc-firewall`, following the examples of the "[Rules factory](../../../modules/net-vpc-firewall#rules-factory)" section of the module documentation. Sample firewall rules are shipped in [data/firewall-rules/landing](./data/firewall-rules/landing) and can be easily customised. To add a new firewall rule, create a new file or edit an existing one in the `data_folder` directory defined in the module `net-vpc-firewall`, following the examples of the "[Rules factory](../../../modules/net-vpc-firewall#rules-factory)" section of the module documentation. Sample firewall rules are shipped in [data/firewall-rules/landing](./data/firewall-rules/landing) and can be easily customised.
**Hierarchical firewall policies** ([`folder`](../../../modules/folder)) are defined in `main.tf`, and managed through a policy factory implemented by the `folder` module, which applies the defined hierarchical to the `Networking` folder, which contains all the core networking infrastructure. Policies are defined in the `rules_file` file - to define a new one simply use the instructions found on "[Firewall policy factory](../../../modules/organization#firewall-policy-factory)". Sample hierarchical firewall policies are shipped in [data/hierarchical-policy-rules.yaml](./data/hierarchical-policy-rules.yaml) and can be easily customised. **Hierarchical firewall policies** ([`folder`](../../../modules/folder)) are defined in `main.tf` and managed through a policy factory implemented by the `net-firewall-policy` module, which is then applied to the `Networking` folder containing all the core networking infrastructure. Policies are defined in the `rules_file` file, to define a new one simply use the [firewall policy module documentation](../../../modules/net-firewall-policy/README.md#factory)". Sample hierarchical firewall rules are shipped in [data/hierarchical-ingress-rules.yaml](./data/hierarchical-ingress-rules.yaml) and can be easily customised.
### DNS architecture ### DNS architecture
@ -393,7 +393,6 @@ DNS configurations are centralised in the `dns-*.tf` files. Spokes delegate DNS
<!-- TFDOC OPTS files:1 show_extra:1 --> <!-- TFDOC OPTS files:1 show_extra:1 -->
<!-- BEGIN TFDOC --> <!-- BEGIN TFDOC -->
## Files ## Files
| name | description | modules | resources | | name | description | modules | resources |
@ -402,7 +401,7 @@ DNS configurations are centralised in the `dns-*.tf` files. Spokes delegate DNS
| [dns-landing.tf](./dns-landing.tf) | Landing DNS zones and peerings setup. | <code>dns</code> · <code>dns-response-policy</code> | | | [dns-landing.tf](./dns-landing.tf) | Landing DNS zones and peerings setup. | <code>dns</code> · <code>dns-response-policy</code> | |
| [dns-prod.tf](./dns-prod.tf) | Production spoke DNS zones and peerings setup. | <code>dns</code> | | | [dns-prod.tf](./dns-prod.tf) | Production spoke DNS zones and peerings setup. | <code>dns</code> | |
| [landing.tf](./landing.tf) | Landing VPC and related resources. | <code>net-cloudnat</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>project</code> | | | [landing.tf](./landing.tf) | Landing VPC and related resources. | <code>net-cloudnat</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>project</code> | |
| [main.tf](./main.tf) | Networking folder and hierarchical policy. | <code>folder</code> | | | [main.tf](./main.tf) | Networking folder and hierarchical policy. | <code>folder</code> · <code>net-firewall-policy</code> | |
| [monitoring-vpn.tf](./monitoring-vpn.tf) | VPN monitoring alerts. | | <code>google_monitoring_alert_policy</code> | | [monitoring-vpn.tf](./monitoring-vpn.tf) | VPN monitoring alerts. | | <code>google_monitoring_alert_policy</code> |
| [monitoring.tf](./monitoring.tf) | Network monitoring dashboards. | | <code>google_monitoring_dashboard</code> | | [monitoring.tf](./monitoring.tf) | Network monitoring dashboards. | | <code>google_monitoring_dashboard</code> |
| [outputs.tf](./outputs.tf) | Module outputs. | | <code>google_storage_bucket_object</code> · <code>local_file</code> | | [outputs.tf](./outputs.tf) | Module outputs. | | <code>google_storage_bucket_object</code> · <code>local_file</code> |
@ -447,5 +446,4 @@ DNS configurations are centralised in the `dns-*.tf` files. Spokes delegate DNS
| [shared_vpc_self_links](outputs.tf#L78) | Shared VPC host projects. | | | | [shared_vpc_self_links](outputs.tf#L78) | Shared VPC host projects. | | |
| [tfvars](outputs.tf#L83) | Terraform variables file for the following stages. | ✓ | | | [tfvars](outputs.tf#L83) | Terraform variables file for the following stages. | ✓ | |
| [vpn_gateway_endpoints](outputs.tf#L89) | External IP Addresses for the GCP VPN gateways. | | | | [vpn_gateway_endpoints](outputs.tf#L89) | External IP Addresses for the GCP VPN gateways. | | |
<!-- END TFDOC --> <!-- END TFDOC -->

View File

@ -0,0 +1,37 @@
# skip boilerplate check
allow-admins:
description: Access from the admin subnet to all subnets
priority: 1000
match:
source_ranges:
- rfc1918
allow-healthchecks:
description: Enable HTTP and HTTPS healthchecks
priority: 1001
match:
source_ranges:
- healthchecks
layer4_configs:
- protocol: tcp
ports: ["80", "443"]
allow-ssh-from-iap:
description: Enable SSH from IAP
priority: 1002
match:
source_ranges:
- 35.235.240.0/20
layer4_configs:
- protocol: tcp
ports: ["22"]
allow-icmp:
description: Enable ICMP
priority: 1003
match:
source_ranges:
- 0.0.0.0/0
layer4_configs:
- protocol: icmp

View File

@ -1,49 +0,0 @@
# skip boilerplate check
allow-admins:
description: Access from the admin subnet to all subnets
direction: INGRESS
action: allow
priority: 1000
ranges:
- $rfc1918
ports:
all: []
target_resources: null
enable_logging: false
allow-healthchecks:
description: Enable HTTP and HTTPS healthchecks
direction: INGRESS
action: allow
priority: 1001
ranges:
- $healthchecks
ports:
tcp: ["80", "443"]
target_resources: null
enable_logging: false
allow-ssh-from-iap:
description: Enable SSH from IAP
direction: INGRESS
action: allow
priority: 1002
ranges:
- 35.235.240.0/20
ports:
tcp: ["22"]
target_resources: null
enable_logging: false
allow-icmp:
description: Enable ICMP
direction: INGRESS
action: allow
priority: 1003
ranges:
- 0.0.0.0/0
ports:
icmp: []
target_resources: null
enable_logging: false

View File

@ -45,13 +45,18 @@ module "folder" {
name = "Networking" name = "Networking"
folder_create = var.folder_ids.networking == null folder_create = var.folder_ids.networking == null
id = var.folder_ids.networking id = var.folder_ids.networking
firewall_policy_factory = { firewall_policy_associations = {
cidr_file = "${var.factories_config.data_dir}/cidrs.yaml" default = module.firewall-policy-default.id
policy_name = var.factories_config.firewall_policy_name }
rules_file = "${var.factories_config.data_dir}/hierarchical-policy-rules.yaml" }
}
firewall_policy_association = { module "firewall-policy-default" {
factory-policy = "factory" source = "../../../modules/net-firewall-policy"
name = "net-default"
parent_id = module.folder.id
rules_factory_config = {
cidr_file_path = "${var.factories_config.data_dir}/cidrs.yaml"
ingress_rules_file_path = "${var.factories_config.data_dir}/hierarchical-ingress-rules.yaml"
} }
} }

View File

@ -254,7 +254,7 @@ BGP sessions for trusted landing to on-premises are configured through the varia
**VPC firewall rules** ([`net-vpc-firewall`](../../../modules/net-vpc-firewall)) are defined per-vpc on each `vpc-*.tf` file and leverage a resource factory to massively create rules. **VPC firewall rules** ([`net-vpc-firewall`](../../../modules/net-vpc-firewall)) are defined per-vpc on each `vpc-*.tf` file and leverage a resource factory to massively create rules.
To add a new firewall rule, create a new file or edit an existing one in the `data_folder` directory defined in the module `net-vpc-firewall`, following the examples of the "[Rules factory](../../../modules/net-vpc-firewall#rules-factory)" section of the module documentation. Sample firewall rules are shipped in [data/firewall-rules/landing-untrusted](./data/firewall-rules/landing-untrusted) and in [data/firewall-rules/landing-trusted](./data/firewall-rules/landing-trusted), and can be easily customized. To add a new firewall rule, create a new file or edit an existing one in the `data_folder` directory defined in the module `net-vpc-firewall`, following the examples of the "[Rules factory](../../../modules/net-vpc-firewall#rules-factory)" section of the module documentation. Sample firewall rules are shipped in [data/firewall-rules/landing-untrusted](./data/firewall-rules/landing-untrusted) and in [data/firewall-rules/landing-trusted](./data/firewall-rules/landing-trusted), and can be easily customized.
**Hierarchical firewall policies** ([`folder`](../../../modules/folder)) are defined in `main.tf`, and managed through a policy factory implemented by the `folder` module, which applies the defined hierarchical to the `Networking` folder, which contains all the core networking infrastructure. Policies are defined in the `rules_file` file - to define a new one simply use the instructions found on "[Firewall policy factory](../../../modules/organization#firewall-policy-factory)". Sample hierarchical firewall policies are shipped in [data/hierarchical-policy-rules.yaml](./data/hierarchical-policy-rules.yaml) and can be easily customized. **Hierarchical firewall policies** ([`folder`](../../../modules/folder)) are defined in `main.tf` and managed through a policy factory implemented by the `net-firewall-policy` module, which is then applied to the `Networking` folder containing all the core networking infrastructure. Policies are defined in the `rules_file` file, to define a new one simply use the [firewall policy module documentation](../../../modules/net-firewall-policy/README.md#factory)". Sample hierarchical firewall rules are shipped in [data/hierarchical-ingress-rules.yaml](./data/hierarchical-ingress-rules.yaml) and can be easily customised.
### DNS architecture ### DNS architecture
@ -452,7 +452,6 @@ DNS configurations are centralised in the `dns-*.tf` files. Spokes delegate DNS
<!-- TFDOC OPTS files:1 show_extra:1 --> <!-- TFDOC OPTS files:1 show_extra:1 -->
<!-- BEGIN TFDOC --> <!-- BEGIN TFDOC -->
## Files ## Files
| name | description | modules | resources | | name | description | modules | resources |
@ -461,7 +460,7 @@ DNS configurations are centralised in the `dns-*.tf` files. Spokes delegate DNS
| [dns-landing.tf](./dns-landing.tf) | Landing DNS zones and peerings setup. | <code>dns</code> · <code>dns-response-policy</code> | | | [dns-landing.tf](./dns-landing.tf) | Landing DNS zones and peerings setup. | <code>dns</code> · <code>dns-response-policy</code> | |
| [dns-prod.tf](./dns-prod.tf) | Production spoke DNS zones and peerings setup. | <code>dns</code> | | | [dns-prod.tf](./dns-prod.tf) | Production spoke DNS zones and peerings setup. | <code>dns</code> | |
| [landing.tf](./landing.tf) | Landing VPC and related resources. | <code>net-cloudnat</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>project</code> | | | [landing.tf](./landing.tf) | Landing VPC and related resources. | <code>net-cloudnat</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>project</code> | |
| [main.tf](./main.tf) | Networking folder and hierarchical policy. | <code>folder</code> | | | [main.tf](./main.tf) | Networking folder and hierarchical policy. | <code>folder</code> · <code>net-firewall-policy</code> | |
| [monitoring-vpn-onprem.tf](./monitoring-vpn-onprem.tf) | VPN monitoring alerts. | | <code>google_monitoring_alert_policy</code> | | [monitoring-vpn-onprem.tf](./monitoring-vpn-onprem.tf) | VPN monitoring alerts. | | <code>google_monitoring_alert_policy</code> |
| [monitoring.tf](./monitoring.tf) | Network monitoring dashboards. | | <code>google_monitoring_dashboard</code> | | [monitoring.tf](./monitoring.tf) | Network monitoring dashboards. | | <code>google_monitoring_dashboard</code> |
| [nva.tf](./nva.tf) | None | <code>compute-mig</code> · <code>compute-vm</code> · <code>simple-nva</code> | | | [nva.tf](./nva.tf) | None | <code>compute-mig</code> · <code>compute-vm</code> · <code>simple-nva</code> | |
@ -504,5 +503,4 @@ DNS configurations are centralised in the `dns-*.tf` files. Spokes delegate DNS
| [shared_vpc_self_links](outputs.tf#L68) | Shared VPC host projects. | | | | [shared_vpc_self_links](outputs.tf#L68) | Shared VPC host projects. | | |
| [tfvars](outputs.tf#L73) | Terraform variables file for the following stages. | ✓ | | | [tfvars](outputs.tf#L73) | Terraform variables file for the following stages. | ✓ | |
| [vpn_gateway_endpoints](outputs.tf#L79) | External IP Addresses for the GCP VPN gateways. | | | | [vpn_gateway_endpoints](outputs.tf#L79) | External IP Addresses for the GCP VPN gateways. | | |
<!-- END TFDOC --> <!-- END TFDOC -->

View File

@ -0,0 +1,37 @@
# skip boilerplate check
allow-admins:
description: Access from the admin subnet to all subnets
priority: 1000
match:
source_ranges:
- rfc1918
allow-healthchecks:
description: Enable HTTP and HTTPS healthchecks
priority: 1001
match:
source_ranges:
- healthchecks
layer4_configs:
- protocol: tcp
ports: ["80", "443"]
allow-ssh-from-iap:
description: Enable SSH from IAP
priority: 1002
match:
source_ranges:
- 35.235.240.0/20
layer4_configs:
- protocol: tcp
ports: ["22"]
allow-icmp:
description: Enable ICMP
priority: 1003
match:
source_ranges:
- 0.0.0.0/0
layer4_configs:
- protocol: icmp

View File

@ -1,49 +0,0 @@
# skip boilerplate check
allow-admins:
description: Access from the admin subnet to all subnets
direction: INGRESS
action: allow
priority: 1000
ranges:
- $rfc1918
ports:
all: []
target_resources: null
enable_logging: false
allow-healthchecks:
description: Enable HTTP and HTTPS healthchecks
direction: INGRESS
action: allow
priority: 1001
ranges:
- $healthchecks
ports:
tcp: ["80", "443"]
target_resources: null
enable_logging: false
allow-ssh-from-iap:
description: Enable SSH from IAP
direction: INGRESS
action: allow
priority: 1002
ranges:
- 35.235.240.0/20
ports:
tcp: ["22"]
target_resources: null
enable_logging: false
allow-icmp:
description: Enable ICMP
direction: INGRESS
action: allow
priority: 1003
ranges:
- 0.0.0.0/0
ports:
icmp: []
target_resources: null
enable_logging: false

View File

@ -46,12 +46,17 @@ module "folder" {
name = "Networking" name = "Networking"
folder_create = var.folder_ids.networking == null folder_create = var.folder_ids.networking == null
id = var.folder_ids.networking id = var.folder_ids.networking
firewall_policy_factory = { firewall_policy_associations = {
cidr_file = "${var.factories_config.data_dir}/cidrs.yaml" default = module.firewall-policy-default.id
policy_name = var.factories_config.firewall_policy_name }
rules_file = "${var.factories_config.data_dir}/hierarchical-policy-rules.yaml" }
}
firewall_policy_association = { module "firewall-policy-default" {
factory-policy = var.factories_config.firewall_policy_name source = "../../../modules/net-firewall-policy"
name = "net-default"
parent_id = module.folder.id
rules_factory_config = {
cidr_file_path = "${var.factories_config.data_dir}/cidrs.yaml"
ingress_rules_file_path = "${var.factories_config.data_dir}/hierarchical-ingress-rules.yaml"
} }
} }

View File

@ -137,7 +137,7 @@ Static routes are defined in `net-*.tf` files, in the `routes` section of each `
**VPC firewall rules** ([`net-vpc-firewall`](../../../modules/net-vpc-firewall)) are defined per-vpc on each `net-*.tf` file and leverage a resource factory to massively create rules. **VPC firewall rules** ([`net-vpc-firewall`](../../../modules/net-vpc-firewall)) are defined per-vpc on each `net-*.tf` file and leverage a resource factory to massively create rules.
To add a new firewall rule, create a new file or edit an existing one in the `data_folder` directory defined in the module `net-vpc-firewall`, following the examples of the "[Rules factory](../../../modules/net-vpc-firewall#rules-factory)" section of the module documentation. Sample firewall rules are shipped in [data/firewall-rules/dev](./data/firewall-rules/dev) and can be easily customised. To add a new firewall rule, create a new file or edit an existing one in the `data_folder` directory defined in the module `net-vpc-firewall`, following the examples of the "[Rules factory](../../../modules/net-vpc-firewall#rules-factory)" section of the module documentation. Sample firewall rules are shipped in [data/firewall-rules/dev](./data/firewall-rules/dev) and can be easily customised.
**Hierarchical firewall policies** ([`folder`](../../../modules/folder)) are defined in `main.tf`, and managed through a policy factory implemented by the `folder` module, which applies the defined hierarchical to the `Networking` folder, which contains all the core networking infrastructure. Policies are defined in the `rules_file` file - to define a new one simply use the instructions found on "[Firewall policy factory](../../../modules/organization#firewall-policy-factory)". Sample hierarchical firewall policies are shipped in [data/hierarchical-policy-rules.yaml](./data/hierarchical-policy-rules.yaml) and can be easily customised. **Hierarchical firewall policies** ([`folder`](../../../modules/folder)) are defined in `main.tf` and managed through a policy factory implemented by the `net-firewall-policy` module, which is then applied to the `Networking` folder containing all the core networking infrastructure. Policies are defined in the `rules_file` file, to define a new one simply use the [firewall policy module documentation](../../../modules/net-firewall-policy/README.md#factory)". Sample hierarchical firewall rules are shipped in [data/hierarchical-ingress-rules.yaml](./data/hierarchical-ingress-rules.yaml) and can be easily customised.
### DNS architecture ### DNS architecture
@ -317,14 +317,13 @@ Regions are defined via the `regions` variable which sets up a mapping between t
<!-- TFDOC OPTS files:1 show_extra:1 --> <!-- TFDOC OPTS files:1 show_extra:1 -->
<!-- BEGIN TFDOC --> <!-- BEGIN TFDOC -->
## Files ## Files
| name | description | modules | resources | | name | description | modules | resources |
|---|---|---|---| |---|---|---|---|
| [dns-dev.tf](./dns-dev.tf) | Development spoke DNS zones and peerings setup. | <code>dns</code> · <code>dns-response-policy</code> | | | [dns-dev.tf](./dns-dev.tf) | Development spoke DNS zones and peerings setup. | <code>dns</code> · <code>dns-response-policy</code> | |
| [dns-prod.tf](./dns-prod.tf) | Production spoke DNS zones and peerings setup. | <code>dns</code> · <code>dns-response-policy</code> | | | [dns-prod.tf](./dns-prod.tf) | Production spoke DNS zones and peerings setup. | <code>dns</code> · <code>dns-response-policy</code> | |
| [main.tf](./main.tf) | Networking folder and hierarchical policy. | <code>folder</code> | | | [main.tf](./main.tf) | Networking folder and hierarchical policy. | <code>folder</code> · <code>net-firewall-policy</code> | |
| [monitoring-vpn-onprem.tf](./monitoring-vpn-onprem.tf) | VPN monitoring alerts. | | <code>google_monitoring_alert_policy</code> | | [monitoring-vpn-onprem.tf](./monitoring-vpn-onprem.tf) | VPN monitoring alerts. | | <code>google_monitoring_alert_policy</code> |
| [monitoring.tf](./monitoring.tf) | Network monitoring dashboards. | | <code>google_monitoring_dashboard</code> | | [monitoring.tf](./monitoring.tf) | Network monitoring dashboards. | | <code>google_monitoring_dashboard</code> |
| [outputs.tf](./outputs.tf) | Module outputs. | | <code>google_storage_bucket_object</code> · <code>local_file</code> | | [outputs.tf](./outputs.tf) | Module outputs. | | <code>google_storage_bucket_object</code> · <code>local_file</code> |
@ -366,5 +365,4 @@ Regions are defined via the `regions` variable which sets up a mapping between t
| [shared_vpc_self_links](outputs.tf#L79) | Shared VPC host projects. | | | | [shared_vpc_self_links](outputs.tf#L79) | Shared VPC host projects. | | |
| [tfvars](outputs.tf#L84) | Terraform variables file for the following stages. | ✓ | | | [tfvars](outputs.tf#L84) | Terraform variables file for the following stages. | ✓ | |
| [vpn_gateway_endpoints](outputs.tf#L90) | External IP Addresses for the GCP VPN gateways. | | | | [vpn_gateway_endpoints](outputs.tf#L90) | External IP Addresses for the GCP VPN gateways. | | |
<!-- END TFDOC --> <!-- END TFDOC -->

View File

@ -0,0 +1,37 @@
# skip boilerplate check
allow-admins:
description: Access from the admin subnet to all subnets
priority: 1000
match:
source_ranges:
- rfc1918
allow-healthchecks:
description: Enable HTTP and HTTPS healthchecks
priority: 1001
match:
source_ranges:
- healthchecks
layer4_configs:
- protocol: tcp
ports: ["80", "443"]
allow-ssh-from-iap:
description: Enable SSH from IAP
priority: 1002
match:
source_ranges:
- 35.235.240.0/20
layer4_configs:
- protocol: tcp
ports: ["22"]
allow-icmp:
description: Enable ICMP
priority: 1003
match:
source_ranges:
- 0.0.0.0/0
layer4_configs:
- protocol: icmp

View File

@ -1,49 +0,0 @@
# skip boilerplate check
allow-admins:
description: Access from the admin subnet to all subnets
direction: INGRESS
action: allow
priority: 1000
ranges:
- $rfc1918
ports:
all: []
target_resources: null
enable_logging: false
allow-healthchecks:
description: Enable HTTP and HTTPS healthchecks
direction: INGRESS
action: allow
priority: 1001
ranges:
- $healthchecks
ports:
tcp: ["80", "443"]
target_resources: null
enable_logging: false
allow-ssh-from-iap:
description: Enable SSH from IAP
direction: INGRESS
action: allow
priority: 1002
ranges:
- 35.235.240.0/20
ports:
tcp: ["22"]
target_resources: null
enable_logging: false
allow-icmp:
description: Enable ICMP
direction: INGRESS
action: allow
priority: 1003
ranges:
- 0.0.0.0/0
ports:
icmp: []
target_resources: null
enable_logging: false

View File

@ -41,13 +41,17 @@ module "folder" {
name = "Networking" name = "Networking"
folder_create = var.folder_ids.networking == null folder_create = var.folder_ids.networking == null
id = var.folder_ids.networking id = var.folder_ids.networking
firewall_policy_factory = { firewall_policy_associations = {
cidr_file = "${var.factories_config.data_dir}/cidrs.yaml" default = module.firewall-policy-default.id
policy_name = var.factories_config.firewall_policy_name
rules_file = "${var.factories_config.data_dir}/hierarchical-policy-rules.yaml"
}
firewall_policy_association = {
factory-policy = var.factories_config.firewall_policy_name
} }
} }
module "firewall-policy-default" {
source = "../../../modules/net-firewall-policy"
name = "net-default"
parent_id = module.folder.id
rules_factory_config = {
cidr_file_path = "${var.factories_config.data_dir}/cidrs.yaml"
ingress_rules_file_path = "${var.factories_config.data_dir}/hierarchical-ingress-rules.yaml"
}
}

View File

@ -276,7 +276,7 @@ BGP sessions for trusted landing to on-premises are configured through the varia
**VPC firewall rules** ([`net-vpc-firewall`](../../../modules/net-vpc-firewall)) are defined per-vpc on each `vpc-*.tf` file and leverage a resource factory to massively create rules. **VPC firewall rules** ([`net-vpc-firewall`](../../../modules/net-vpc-firewall)) are defined per-vpc on each `vpc-*.tf` file and leverage a resource factory to massively create rules.
To add a new firewall rule, create a new file or edit an existing one in the `data_folder` directory defined in the module `net-vpc-firewall`, following the examples of the "[Rules factory](../../../modules/net-vpc-firewall#rules-factory)" section of the module documentation. Sample firewall rules are shipped in [data/firewall-rules/landing-untrusted](./data/firewall-rules/landing-untrusted) and in [data/firewall-rules/landing-trusted](./data/firewall-rules/landing-trusted), and can be easily customized. To add a new firewall rule, create a new file or edit an existing one in the `data_folder` directory defined in the module `net-vpc-firewall`, following the examples of the "[Rules factory](../../../modules/net-vpc-firewall#rules-factory)" section of the module documentation. Sample firewall rules are shipped in [data/firewall-rules/landing-untrusted](./data/firewall-rules/landing-untrusted) and in [data/firewall-rules/landing-trusted](./data/firewall-rules/landing-trusted), and can be easily customized.
**Hierarchical firewall policies** ([`folder`](../../../modules/folder)) are defined in `main.tf`, and managed through a policy factory implemented by the `folder` module, which applies the defined hierarchical to the `Networking` folder, which contains all the core networking infrastructure. Policies are defined in the `rules_file` file - to define a new one simply use the instructions found on "[Firewall policy factory](../../../modules/organization#firewall-policy-factory)". Sample hierarchical firewall policies are shipped in [data/hierarchical-policy-rules.yaml](./data/hierarchical-policy-rules.yaml) and can be easily customized. **Hierarchical firewall policies** ([`folder`](../../../modules/folder)) are defined in `main.tf` and managed through a policy factory implemented by the `net-firewall-policy` module, which is then applied to the `Networking` folder containing all the core networking infrastructure. Policies are defined in the `rules_file` file, to define a new one simply use the [firewall policy module documentation](../../../modules/net-firewall-policy/README.md#factory)". Sample hierarchical firewall rules are shipped in [data/hierarchical-ingress-rules.yaml](./data/hierarchical-ingress-rules.yaml) and can be easily customised.
### DNS architecture ### DNS architecture
@ -476,7 +476,6 @@ DNS configurations are centralised in the `dns-*.tf` files. Spokes delegate DNS
<!-- TFDOC OPTS files:1 show_extra:1 --> <!-- TFDOC OPTS files:1 show_extra:1 -->
<!-- BEGIN TFDOC --> <!-- BEGIN TFDOC -->
## Files ## Files
| name | description | modules | resources | | name | description | modules | resources |
@ -485,7 +484,7 @@ DNS configurations are centralised in the `dns-*.tf` files. Spokes delegate DNS
| [dns-landing.tf](./dns-landing.tf) | Landing DNS zones and peerings setup. | <code>dns</code> · <code>dns-response-policy</code> | | | [dns-landing.tf](./dns-landing.tf) | Landing DNS zones and peerings setup. | <code>dns</code> · <code>dns-response-policy</code> | |
| [dns-prod.tf](./dns-prod.tf) | Production spoke DNS zones and peerings setup. | <code>dns</code> | | | [dns-prod.tf](./dns-prod.tf) | Production spoke DNS zones and peerings setup. | <code>dns</code> | |
| [landing.tf](./landing.tf) | Landing VPC and related resources. | <code>net-cloudnat</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>project</code> | | | [landing.tf](./landing.tf) | Landing VPC and related resources. | <code>net-cloudnat</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>project</code> | |
| [main.tf](./main.tf) | Networking folder and hierarchical policy. | <code>folder</code> | | | [main.tf](./main.tf) | Networking folder and hierarchical policy. | <code>folder</code> · <code>net-firewall-policy</code> | |
| [monitoring-vpn-onprem.tf](./monitoring-vpn-onprem.tf) | VPN monitoring alerts. | | <code>google_monitoring_alert_policy</code> | | [monitoring-vpn-onprem.tf](./monitoring-vpn-onprem.tf) | VPN monitoring alerts. | | <code>google_monitoring_alert_policy</code> |
| [monitoring.tf](./monitoring.tf) | Network monitoring dashboards. | | <code>google_monitoring_dashboard</code> | | [monitoring.tf](./monitoring.tf) | Network monitoring dashboards. | | <code>google_monitoring_dashboard</code> |
| [ncc.tf](./ncc.tf) | None | <code>ncc-spoke-ra</code> | | | [ncc.tf](./ncc.tf) | None | <code>ncc-spoke-ra</code> | |
@ -531,5 +530,4 @@ DNS configurations are centralised in the `dns-*.tf` files. Spokes delegate DNS
| [shared_vpc_self_links](outputs.tf#L68) | Shared VPC host projects. | | | | [shared_vpc_self_links](outputs.tf#L68) | Shared VPC host projects. | | |
| [tfvars](outputs.tf#L73) | Terraform variables file for the following stages. | ✓ | | | [tfvars](outputs.tf#L73) | Terraform variables file for the following stages. | ✓ | |
| [vpn_gateway_endpoints](outputs.tf#L79) | External IP Addresses for the GCP VPN gateways. | | | | [vpn_gateway_endpoints](outputs.tf#L79) | External IP Addresses for the GCP VPN gateways. | | |
<!-- END TFDOC --> <!-- END TFDOC -->

View File

@ -0,0 +1,37 @@
# skip boilerplate check
allow-admins:
description: Access from the admin subnet to all subnets
priority: 1000
match:
source_ranges:
- rfc1918
allow-healthchecks:
description: Enable HTTP and HTTPS healthchecks
priority: 1001
match:
source_ranges:
- healthchecks
layer4_configs:
- protocol: tcp
ports: ["80", "443"]
allow-ssh-from-iap:
description: Enable SSH from IAP
priority: 1002
match:
source_ranges:
- 35.235.240.0/20
layer4_configs:
- protocol: tcp
ports: ["22"]
allow-icmp:
description: Enable ICMP
priority: 1003
match:
source_ranges:
- 0.0.0.0/0
layer4_configs:
- protocol: icmp

View File

@ -1,49 +0,0 @@
# skip boilerplate check
allow-admins:
description: Access from the admin subnet to all subnets
direction: INGRESS
action: allow
priority: 1000
ranges:
- $rfc1918
ports:
all: []
target_resources: null
enable_logging: false
allow-healthchecks:
description: Enable HTTP and HTTPS healthchecks
direction: INGRESS
action: allow
priority: 1001
ranges:
- $healthchecks
ports:
tcp: ["80", "443"]
target_resources: null
enable_logging: false
allow-ssh-from-iap:
description: Enable SSH from IAP
direction: INGRESS
action: allow
priority: 1002
ranges:
- 35.235.240.0/20
ports:
tcp: ["22"]
target_resources: null
enable_logging: false
allow-icmp:
description: Enable ICMP
direction: INGRESS
action: allow
priority: 1003
ranges:
- 0.0.0.0/0
ports:
icmp: []
target_resources: null
enable_logging: false

View File

@ -46,12 +46,17 @@ module "folder" {
name = "Networking" name = "Networking"
folder_create = var.folder_ids.networking == null folder_create = var.folder_ids.networking == null
id = var.folder_ids.networking id = var.folder_ids.networking
firewall_policy_factory = { firewall_policy_associations = {
cidr_file = "${var.factories_config.data_dir}/cidrs.yaml" default = module.firewall-policy-default.id
policy_name = var.factories_config.firewall_policy_name }
rules_file = "${var.factories_config.data_dir}/hierarchical-policy-rules.yaml" }
}
firewall_policy_association = { module "firewall-policy-default" {
factory-policy = var.factories_config.firewall_policy_name source = "../../../modules/net-firewall-policy"
name = "net-default"
parent_id = module.folder.id
rules_factory_config = {
cidr_file_path = "${var.factories_config.data_dir}/cidrs.yaml"
ingress_rules_file_path = "${var.factories_config.data_dir}/hierarchical-ingress-rules.yaml"
} }
} }

View File

@ -45,6 +45,7 @@ These modules are used in the examples included in this repository. If you are u
- [Cloud Endpoints](./endpoints) - [Cloud Endpoints](./endpoints)
- [DNS](./dns) - [DNS](./dns)
- [DNS Response Policy](./dns-response-policy/) - [DNS Response Policy](./dns-response-policy/)
- [Firewall policy](./net-firewall-policy)
- [External Application Load Balancer](./net-lb-app-ext/) - [External Application Load Balancer](./net-lb-app-ext/)
- [External Passthrough Network Load Balancer](./net-lb-ext) - [External Passthrough Network Load Balancer](./net-lb-ext)
- [Internal Application Load Balancer](./net-lb-app-int) - [Internal Application Load Balancer](./net-lb-app-int)
@ -55,7 +56,6 @@ These modules are used in the examples included in this repository. If you are u
- [Service Directory](./service-directory) - [Service Directory](./service-directory)
- [VPC](./net-vpc) - [VPC](./net-vpc)
- [VPC firewall](./net-vpc-firewall) - [VPC firewall](./net-vpc-firewall)
- [VPC firewall policy](./net-vpc-firewall-policy)
- [VPN dynamic](./net-vpn-dynamic) - [VPN dynamic](./net-vpn-dynamic)
- [VPC peering](./net-vpc-peering) - [VPC peering](./net-vpc-peering)
- [VPN HA](./net-vpn-ha) - [VPN HA](./net-vpn-ha)

View File

@ -2,15 +2,12 @@
This module allows the creation and management of folders, including support for IAM bindings, organization policies, and hierarchical firewall rules. This module allows the creation and management of folders, including support for IAM bindings, organization policies, and hierarchical firewall rules.
<!-- BEGIN TOC --> <!-- BEGIN TOC -->
- [Basic example with IAM bindings](#basic-example-with-iam-bindings) - [Basic example with IAM bindings](#basic-example-with-iam-bindings)
- [IAM](#iam) - [IAM](#iam)
- [Organization policies](#organization-policies) - [Organization policies](#organization-policies)
- [Organization Policy Factory](#organization-policy-factory) - [Organization Policy Factory](#organization-policy-factory)
- [Hierarchical Firewall Policies](#hierarchical-firewall-policies) - [Hierarchical Firewall Policy Attachments](#hierarchical-firewall-policy-attachments)
- [Directly Defined Firewall Policies](#directly-defined-firewall-policies)
- [Firewall Policy Factory](#firewall-policy-factory)
- [Log Sinks](#log-sinks) - [Log Sinks](#log-sinks)
- [Data Access Logs](#data-access-logs) - [Data Access Logs](#data-access-logs)
- [Tags](#tags) - [Tags](#tags)
@ -121,128 +118,31 @@ module "folder" {
See the [organization policy factory in the project module](../project#organization-policy-factory). See the [organization policy factory in the project module](../project#organization-policy-factory).
## Hierarchical Firewall Policies ## Hierarchical Firewall Policy Attachments
Hierarchical firewall policies can be managed in two ways: Hierarchical firewall policies can be managed via the [`net-firewall-policy`](../net-firewall-policy/) module, including support for factories. Once a policy is available, attaching it to the organization can be done either in the firewall policy module itself, or here:
- via the `firewall_policies` variable, to directly define policies and rules in Terraform
- via the `firewall_policy_factory` variable, to leverage external YaML files via a simple "factory" embedded in the module ([see here](../../blueprints/factories) for more context on factories)
Once you have policies (either created via the module or externally), you can associate them using the `firewall_policy_association` variable.
### Directly Defined Firewall Policies
```hcl ```hcl
module "folder1" { module "firewall-policy" {
source = "./fabric/modules/folder" source = "./fabric/modules/net-firewall-policy"
parent = var.organization_id name = "test-1"
name = "policy-container" parent_id = module.folder.id
# attachment via the firewall policy module
firewall_policies = { # attachments = {
iap-policy = { # folder-1 = module.folder.id
allow-admins = { # }
description = "Access from the admin subnet to all subnets"
direction = "INGRESS"
action = "allow"
priority = 1000
ranges = ["10.0.0.0/8", "172.16.0.0/12", "192.168.0.0/16"]
ports = { all = [] }
target_service_accounts = null
target_resources = null
logging = false
}
allow-iap-ssh = {
description = "Always allow ssh from IAP"
direction = "INGRESS"
action = "allow"
priority = 100
ranges = ["35.235.240.0/20"]
ports = { tcp = ["22"] }
target_service_accounts = null
target_resources = null
logging = false
}
}
}
firewall_policy_association = {
iap-policy = "iap-policy"
}
} }
module "folder2" { module "folder" {
source = "./fabric/modules/folder" source = "./fabric/modules/folder"
parent = var.organization_id parent = "organizations/1234567890"
name = "hf2" name = "Folder name"
firewall_policy_association = { # attachment via the organization module
iap-policy = module.folder1.firewall_policy_id["iap-policy"] firewall_policy_associations = {
test-1 = module.firewall-policy.id
} }
} }
# tftest modules=2 resources=7 inventory=hfw.yaml # tftest modules=2 resources=3
```
### Firewall Policy Factory
The in-built factory allows you to define a single policy, using one file for rules, and an optional file for CIDR range substitution variables. Remember that non-absolute paths are relative to the root module (the folder where you run `terraform`).
```hcl
module "folder1" {
source = "./fabric/modules/folder"
parent = var.organization_id
name = "policy-container"
firewall_policy_factory = {
cidr_file = "configs/firewall-policies/cidrs.yaml"
policy_name = "iap-policy"
rules_file = "configs/firewall-policies/rules.yaml"
}
firewall_policy_association = {
iap-policy = "iap-policy"
}
}
module "folder2" {
source = "./fabric/modules/folder"
parent = var.organization_id
name = "hf2"
firewall_policy_association = {
iap-policy = module.folder1.firewall_policy_id["iap-policy"]
}
}
# tftest modules=2 resources=7 files=cidrs,rules inventory=hfw.yaml
```
```yaml
# tftest-file id=cidrs path=configs/firewall-policies/cidrs.yaml
rfc1918:
- 10.0.0.0/8
- 172.16.0.0/12
- 192.168.0.0/16
```
```yaml
# tftest-file id=rules path=configs/firewall-policies/rules.yaml
allow-admins:
description: Access from the admin subnet to all subnets
direction: INGRESS
action: allow
priority: 1000
ranges:
- $rfc1918
ports:
all: []
target_resources: null
logging: false
allow-iap-ssh:
description: "Always allow ssh from IAP"
direction: INGRESS
action: allow
priority: 100
ranges:
- 35.235.240.0/20
ports:
tcp: ["22"]
target_resources: null
logging: false
``` ```
## Log Sinks ## Log Sinks
@ -395,15 +295,13 @@ module "folder" {
<!-- TFDOC OPTS files:1 --> <!-- TFDOC OPTS files:1 -->
<!-- BEGIN TFDOC --> <!-- BEGIN TFDOC -->
## Files ## Files
| name | description | resources | | name | description | resources |
|---|---|---| |---|---|---|
| [firewall-policies.tf](./firewall-policies.tf) | None | <code>google_compute_firewall_policy</code> · <code>google_compute_firewall_policy_association</code> · <code>google_compute_firewall_policy_rule</code> |
| [iam.tf](./iam.tf) | IAM bindings, roles and audit logging resources. | <code>google_folder_iam_binding</code> · <code>google_folder_iam_member</code> · <code>google_folder_iam_policy</code> | | [iam.tf](./iam.tf) | IAM bindings, roles and audit logging resources. | <code>google_folder_iam_binding</code> · <code>google_folder_iam_member</code> · <code>google_folder_iam_policy</code> |
| [logging.tf](./logging.tf) | Log sinks and supporting resources. | <code>google_bigquery_dataset_iam_member</code> · <code>google_folder_iam_audit_config</code> · <code>google_logging_folder_exclusion</code> · <code>google_logging_folder_sink</code> · <code>google_project_iam_member</code> · <code>google_pubsub_topic_iam_member</code> · <code>google_storage_bucket_iam_member</code> | | [logging.tf](./logging.tf) | Log sinks and supporting resources. | <code>google_bigquery_dataset_iam_member</code> · <code>google_folder_iam_audit_config</code> · <code>google_logging_folder_exclusion</code> · <code>google_logging_folder_sink</code> · <code>google_project_iam_member</code> · <code>google_pubsub_topic_iam_member</code> · <code>google_storage_bucket_iam_member</code> |
| [main.tf](./main.tf) | Module-level locals and resources. | <code>google_essential_contacts_contact</code> · <code>google_folder</code> | | [main.tf](./main.tf) | Module-level locals and resources. | <code>google_compute_firewall_policy_association</code> · <code>google_essential_contacts_contact</code> · <code>google_folder</code> |
| [organization-policies.tf](./organization-policies.tf) | Folder-level organization policies. | <code>google_org_policy_policy</code> | | [organization-policies.tf](./organization-policies.tf) | Folder-level organization policies. | <code>google_org_policy_policy</code> |
| [outputs.tf](./outputs.tf) | Module outputs. | | | [outputs.tf](./outputs.tf) | Module outputs. | |
| [tags.tf](./tags.tf) | None | <code>google_tags_tag_binding</code> | | [tags.tf](./tags.tf) | None | <code>google_tags_tag_binding</code> |
@ -415,34 +313,29 @@ module "folder" {
| name | description | type | required | default | | name | description | type | required | default |
|---|---|:---:|:---:|:---:| |---|---|:---:|:---:|:---:|
| [contacts](variables.tf#L17) | List of essential contacts for this resource. Must be in the form EMAIL -> [NOTIFICATION_TYPES]. Valid notification types are ALL, SUSPENSION, SECURITY, TECHNICAL, BILLING, LEGAL, PRODUCT_UPDATES. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [contacts](variables.tf#L17) | List of essential contacts for this resource. Must be in the form EMAIL -> [NOTIFICATION_TYPES]. Valid notification types are ALL, SUSPENSION, SECURITY, TECHNICAL, BILLING, LEGAL, PRODUCT_UPDATES. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [firewall_policies](variables.tf#L24) | Hierarchical firewall policies created in this folder. | <code title="map&#40;map&#40;object&#40;&#123;&#10; action &#61; string&#10; description &#61; string&#10; direction &#61; string&#10; logging &#61; bool&#10; ports &#61; map&#40;list&#40;string&#41;&#41;&#10; priority &#61; number&#10; ranges &#61; list&#40;string&#41;&#10; target_resources &#61; list&#40;string&#41;&#10; target_service_accounts &#61; list&#40;string&#41;&#10;&#125;&#41;&#41;&#41;">map&#40;map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [firewall_policy_associations](variables.tf#L24) | Hierarchical firewall policies to associate to this folder, in association name => policy id format. | <code>map&#40;string&#41;</code> | | <code>&#123;&#125;</code> |
| [firewall_policy_association](variables.tf#L41) | The hierarchical firewall policy to associate to this folder. Must be either a key in the `firewall_policies` map or the id of a policy defined somewhere else. | <code>map&#40;string&#41;</code> | | <code>&#123;&#125;</code> | | [folder_create](variables.tf#L31) | Create folder. When set to false, uses id to reference an existing folder. | <code>bool</code> | | <code>true</code> |
| [firewall_policy_factory](variables.tf#L48) | Configuration for the firewall policy factory. | <code title="object&#40;&#123;&#10; cidr_file &#61; string&#10; policy_name &#61; string&#10; rules_file &#61; string&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>null</code> | | [group_iam](variables.tf#L37) | Authoritative IAM binding for organization groups, in {GROUP_EMAIL => [ROLES]} format. Group emails need to be static. Can be used in combination with the `iam` variable. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [folder_create](variables.tf#L58) | Create folder. When set to false, uses id to reference an existing folder. | <code>bool</code> | | <code>true</code> | | [iam](variables.tf#L44) | IAM bindings in {ROLE => [MEMBERS]} format. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [group_iam](variables.tf#L64) | Authoritative IAM binding for organization groups, in {GROUP_EMAIL => [ROLES]} format. Group emails need to be static. Can be used in combination with the `iam` variable. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [iam_additive](variables.tf#L51) | Non authoritative IAM bindings, in {ROLE => [MEMBERS]} format. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [iam](variables.tf#L71) | IAM bindings in {ROLE => [MEMBERS]} format. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [iam_additive_members](variables.tf#L58) | IAM additive bindings in {MEMBERS => [ROLE]} format. This might break if members are dynamic values. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [iam_additive](variables.tf#L78) | Non authoritative IAM bindings, in {ROLE => [MEMBERS]} format. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [iam_policy](variables.tf#L65) | IAM authoritative policy in {ROLE => [MEMBERS]} format. Roles and members not explicitly listed will be cleared, use with extreme caution. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>null</code> |
| [iam_additive_members](variables.tf#L85) | IAM additive bindings in {MEMBERS => [ROLE]} format. This might break if members are dynamic values. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [id](variables.tf#L71) | Folder ID in case you use folder_create=false. | <code>string</code> | | <code>null</code> |
| [iam_policy](variables.tf#L92) | IAM authoritative policy in {ROLE => [MEMBERS]} format. Roles and members not explicitly listed will be cleared, use with extreme caution. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>null</code> | | [logging_data_access](variables.tf#L77) | Control activation of data access logs. Format is service => { log type => [exempted members]}. The special 'allServices' key denotes configuration for all services. | <code>map&#40;map&#40;list&#40;string&#41;&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [id](variables.tf#L98) | Folder ID in case you use folder_create=false. | <code>string</code> | | <code>null</code> | | [logging_exclusions](variables.tf#L92) | Logging exclusions for this folder in the form {NAME -> FILTER}. | <code>map&#40;string&#41;</code> | | <code>&#123;&#125;</code> |
| [logging_data_access](variables.tf#L104) | Control activation of data access logs. Format is service => { log type => [exempted members]}. The special 'allServices' key denotes configuration for all services. | <code>map&#40;map&#40;list&#40;string&#41;&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [logging_sinks](variables.tf#L99) | Logging sinks to create for the organization. | <code title="map&#40;object&#40;&#123;&#10; bq_partitioned_table &#61; optional&#40;bool&#41;&#10; description &#61; optional&#40;string&#41;&#10; destination &#61; string&#10; disabled &#61; optional&#40;bool, false&#41;&#10; exclusions &#61; optional&#40;map&#40;string&#41;, &#123;&#125;&#41;&#10; filter &#61; string&#10; include_children &#61; optional&#40;bool, true&#41;&#10; type &#61; string&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [logging_exclusions](variables.tf#L119) | Logging exclusions for this folder in the form {NAME -> FILTER}. | <code>map&#40;string&#41;</code> | | <code>&#123;&#125;</code> | | [name](variables.tf#L129) | Folder name. | <code>string</code> | | <code>null</code> |
| [logging_sinks](variables.tf#L126) | Logging sinks to create for the organization. | <code title="map&#40;object&#40;&#123;&#10; bq_partitioned_table &#61; optional&#40;bool&#41;&#10; description &#61; optional&#40;string&#41;&#10; destination &#61; string&#10; disabled &#61; optional&#40;bool, false&#41;&#10; exclusions &#61; optional&#40;map&#40;string&#41;, &#123;&#125;&#41;&#10; filter &#61; string&#10; include_children &#61; optional&#40;bool, true&#41;&#10; type &#61; string&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [org_policies](variables.tf#L135) | Organization policies applied to this folder keyed by policy name. | <code title="map&#40;object&#40;&#123;&#10; inherit_from_parent &#61; optional&#40;bool&#41; &#35; for list policies only.&#10; reset &#61; optional&#40;bool&#41;&#10; rules &#61; optional&#40;list&#40;object&#40;&#123;&#10; allow &#61; optional&#40;object&#40;&#123;&#10; all &#61; optional&#40;bool&#41;&#10; values &#61; optional&#40;list&#40;string&#41;&#41;&#10; &#125;&#41;&#41;&#10; deny &#61; optional&#40;object&#40;&#123;&#10; all &#61; optional&#40;bool&#41;&#10; values &#61; optional&#40;list&#40;string&#41;&#41;&#10; &#125;&#41;&#41;&#10; enforce &#61; optional&#40;bool&#41; &#35; for boolean policies only.&#10; condition &#61; optional&#40;object&#40;&#123;&#10; description &#61; optional&#40;string&#41;&#10; expression &#61; optional&#40;string&#41;&#10; location &#61; optional&#40;string&#41;&#10; title &#61; optional&#40;string&#41;&#10; &#125;&#41;, &#123;&#125;&#41;&#10; &#125;&#41;&#41;, &#91;&#93;&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [name](variables.tf#L156) | Folder name. | <code>string</code> | | <code>null</code> | | [org_policies_data_path](variables.tf#L162) | Path containing org policies in YAML format. | <code>string</code> | | <code>null</code> |
| [org_policies](variables.tf#L162) | Organization policies applied to this folder keyed by policy name. | <code title="map&#40;object&#40;&#123;&#10; inherit_from_parent &#61; optional&#40;bool&#41; &#35; for list policies only.&#10; reset &#61; optional&#40;bool&#41;&#10; rules &#61; optional&#40;list&#40;object&#40;&#123;&#10; allow &#61; optional&#40;object&#40;&#123;&#10; all &#61; optional&#40;bool&#41;&#10; values &#61; optional&#40;list&#40;string&#41;&#41;&#10; &#125;&#41;&#41;&#10; deny &#61; optional&#40;object&#40;&#123;&#10; all &#61; optional&#40;bool&#41;&#10; values &#61; optional&#40;list&#40;string&#41;&#41;&#10; &#125;&#41;&#41;&#10; enforce &#61; optional&#40;bool&#41; &#35; for boolean policies only.&#10; condition &#61; optional&#40;object&#40;&#123;&#10; description &#61; optional&#40;string&#41;&#10; expression &#61; optional&#40;string&#41;&#10; location &#61; optional&#40;string&#41;&#10; title &#61; optional&#40;string&#41;&#10; &#125;&#41;, &#123;&#125;&#41;&#10; &#125;&#41;&#41;, &#91;&#93;&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [parent](variables.tf#L168) | Parent in folders/folder_id or organizations/org_id format. | <code>string</code> | | <code>null</code> |
| [org_policies_data_path](variables.tf#L189) | Path containing org policies in YAML format. | <code>string</code> | | <code>null</code> | | [tag_bindings](variables.tf#L178) | Tag bindings for this folder, in key => tag value id format. | <code>map&#40;string&#41;</code> | | <code>null</code> |
| [parent](variables.tf#L195) | Parent in folders/folder_id or organizations/org_id format. | <code>string</code> | | <code>null</code> |
| [tag_bindings](variables.tf#L205) | Tag bindings for this folder, in key => tag value id format. | <code>map&#40;string&#41;</code> | | <code>null</code> |
## Outputs ## Outputs
| name | description | sensitive | | name | description | sensitive |
|---|---|:---:| |---|---|:---:|
| [firewall_policies](outputs.tf#L16) | Map of firewall policy resources created in this folder. | | | [folder](outputs.tf#L17) | Folder resource. | |
| [firewall_policy_id](outputs.tf#L21) | Map of firewall policy ids created in this folder. | | | [id](outputs.tf#L22) | Fully qualified folder id. | |
| [folder](outputs.tf#L26) | Folder resource. | | | [name](outputs.tf#L32) | Folder name. | |
| [id](outputs.tf#L31) | Fully qualified folder id. | | | [sink_writer_identities](outputs.tf#L37) | Writer identities created for each sink. | |
| [name](outputs.tf#L41) | Folder name. | |
| [sink_writer_identities](outputs.tf#L46) | Writer identities created for each sink. | |
<!-- END TFDOC --> <!-- END TFDOC -->

View File

@ -1,93 +0,0 @@
/**
* Copyright 2022 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.
*/
locals {
_factory_cidrs = try(
yamldecode(file(var.firewall_policy_factory.cidr_file)), {}
)
_factory_name = (
try(var.firewall_policy_factory.policy_name, null) == null
? "factory"
: var.firewall_policy_factory.policy_name
)
_factory_rules = try(
yamldecode(file(var.firewall_policy_factory.rules_file)), {}
)
_factory_rules_parsed = {
for name, rule in local._factory_rules : name => merge(rule, {
ranges = flatten([
for r in(rule.ranges == null ? [] : rule.ranges) :
lookup(local._factory_cidrs, trimprefix(r, "$"), r)
])
})
}
_merged_rules = flatten([
for policy, rules in local.firewall_policies : [
for name, rule in rules : merge(rule, {
policy = policy
name = name
})
]
])
firewall_policies = merge(var.firewall_policies, (
length(local._factory_rules) == 0
? {}
: { (local._factory_name) = local._factory_rules_parsed }
))
firewall_rules = {
for r in local._merged_rules : "${r.policy}-${r.name}" => r
}
}
resource "google_compute_firewall_policy" "policy" {
for_each = local.firewall_policies
short_name = each.key
parent = local.folder.id
}
resource "google_compute_firewall_policy_rule" "rule" {
for_each = local.firewall_rules
firewall_policy = google_compute_firewall_policy.policy[each.value.policy].id
action = each.value.action
direction = each.value.direction
priority = try(each.value.priority, null)
target_resources = try(each.value.target_resources, null)
target_service_accounts = try(each.value.target_service_accounts, null)
enable_logging = try(each.value.logging, null)
# preview = each.value.preview
description = each.value.description
match {
src_ip_ranges = each.value.direction == "INGRESS" ? each.value.ranges : null
dest_ip_ranges = each.value.direction == "EGRESS" ? each.value.ranges : null
dynamic "layer4_configs" {
for_each = each.value.ports
iterator = port
content {
ip_protocol = port.key
ports = port.value
}
}
}
}
resource "google_compute_firewall_policy_association" "association" {
for_each = var.firewall_policy_association
name = replace(local.folder.id, "/", "-")
attachment_target = local.folder.id
firewall_policy = try(google_compute_firewall_policy.policy[each.value].id, each.value)
}

View File

@ -41,3 +41,10 @@ resource "google_essential_contacts_contact" "contact" {
language_tag = "en" language_tag = "en"
notification_category_subscriptions = each.value notification_category_subscriptions = each.value
} }
resource "google_compute_firewall_policy_association" "default" {
for_each = var.firewall_policy_associations
attachment_target = local.folder.id
name = each.key
firewall_policy = each.value
}

View File

@ -13,15 +13,6 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
output "firewall_policies" {
description = "Map of firewall policy resources created in this folder."
value = { for k, v in google_compute_firewall_policy.policy : k => v }
}
output "firewall_policy_id" {
description = "Map of firewall policy ids created in this folder."
value = { for k, v in google_compute_firewall_policy.policy : k => v.id }
}
output "folder" { output "folder" {
description = "Folder resource." description = "Folder resource."

View File

@ -21,40 +21,13 @@ variable "contacts" {
nullable = false nullable = false
} }
variable "firewall_policies" { variable "firewall_policy_associations" {
description = "Hierarchical firewall policies created in this folder." description = "Hierarchical firewall policies to associate to this folder, in association name => policy id format."
type = map(map(object({
action = string
description = string
direction = string
logging = bool
ports = map(list(string))
priority = number
ranges = list(string)
target_resources = list(string)
target_service_accounts = list(string)
})))
default = {}
nullable = false
}
variable "firewall_policy_association" {
description = "The hierarchical firewall policy to associate to this folder. Must be either a key in the `firewall_policies` map or the id of a policy defined somewhere else."
type = map(string) type = map(string)
default = {} default = {}
nullable = false nullable = false
} }
variable "firewall_policy_factory" {
description = "Configuration for the firewall policy factory."
type = object({
cidr_file = string
policy_name = string
rules_file = string
})
default = null
}
variable "folder_create" { variable "folder_create" {
description = "Create folder. When set to false, uses id to reference an existing folder." description = "Create folder. When set to false, uses id to reference an existing folder."
type = bool type = bool

View File

@ -9,13 +9,23 @@ The module also manages policy rules via code or a factory, and optional policy
The module also makes fewer assumptions about implicit defaults, only using one to set `match.layer4_configs` to `[{ protocol = "all" }]` if no explicit set of protocols and ports has been specified. The module also makes fewer assumptions about implicit defaults, only using one to set `match.layer4_configs` to `[{ protocol = "all" }]` if no explicit set of protocols and ports has been specified.
<!-- BEGIN TOC -->
- [Examples](#examples)
- [Hierarchical Policy](#hierarchical-policy)
- [Global Network policy](#global-network-policy)
- [Regional Network policy](#regional-network-policy)
- [Factory](#factory)
- [Variables](#variables)
- [Outputs](#outputs)
<!-- END TOC -->
## Examples ## Examples
### Hierarchical Policy ### Hierarchical Policy
```hcl ```hcl
module "firewall-policy" { module "firewall-policy" {
source = "./fabric/modules/net-vpc-firewall-policy" source = "./fabric/modules/net-firewall-policy"
name = "test-1" name = "test-1"
parent_id = "folders/1234567890" parent_id = "folders/1234567890"
attachments = { attachments = {
@ -67,9 +77,10 @@ module "vpc" {
} }
module "firewall-policy" { module "firewall-policy" {
source = "./fabric/modules/net-vpc-firewall-policy" source = "./fabric/modules/net-firewall-policy"
name = "test-1" name = "test-1"
parent_id = "my-project" parent_id = "my-project"
region = "global"
attachments = { attachments = {
my-vpc = module.vpc.self_link my-vpc = module.vpc.self_link
} }
@ -119,7 +130,7 @@ module "vpc" {
} }
module "firewall-policy" { module "firewall-policy" {
source = "./fabric/modules/net-vpc-firewall-policy" source = "./fabric/modules/net-firewall-policy"
name = "test-1" name = "test-1"
parent_id = "my-project" parent_id = "my-project"
region = "europe-west8" region = "europe-west8"
@ -164,7 +175,7 @@ This is an example of a simple factory:
```hcl ```hcl
module "firewall-policy" { module "firewall-policy" {
source = "./fabric/modules/net-vpc-firewall-policy" source = "./fabric/modules/net-firewall-policy"
name = "test-1" name = "test-1"
parent_id = "folders/1234567890" parent_id = "folders/1234567890"
attachments = { attachments = {
@ -219,7 +230,6 @@ icmp:
layer4_configs: layer4_configs:
- protocol: icmp - protocol: icmp
``` ```
<!-- BEGIN TFDOC --> <!-- BEGIN TFDOC -->
## Variables ## Variables
@ -231,7 +241,7 @@ icmp:
| [description](variables.tf#L24) | Policy description. | <code>string</code> | | <code>null</code> | | [description](variables.tf#L24) | Policy description. | <code>string</code> | | <code>null</code> |
| [egress_rules](variables.tf#L30) | List of egress rule definitions, action can be 'allow', 'deny', 'goto_next'. The match.layer4configs map is in protocol => optional [ports] format. | <code title="map&#40;object&#40;&#123;&#10; priority &#61; number&#10; action &#61; optional&#40;string, &#34;deny&#34;&#41;&#10; description &#61; optional&#40;string&#41;&#10; disabled &#61; optional&#40;bool, false&#41;&#10; enable_logging &#61; optional&#40;bool&#41;&#10; target_service_accounts &#61; optional&#40;list&#40;string&#41;&#41;&#10; target_tags &#61; optional&#40;list&#40;string&#41;&#41;&#10; match &#61; object&#40;&#123;&#10; address_groups &#61; optional&#40;list&#40;string&#41;&#41;&#10; fqdns &#61; optional&#40;list&#40;string&#41;&#41;&#10; region_codes &#61; optional&#40;list&#40;string&#41;&#41;&#10; threat_intelligences &#61; optional&#40;list&#40;string&#41;&#41;&#10; destination_ranges &#61; optional&#40;list&#40;string&#41;&#41;&#10; source_ranges &#61; optional&#40;list&#40;string&#41;&#41;&#10; source_tags &#61; optional&#40;list&#40;string&#41;&#41;&#10; layer4_configs &#61; optional&#40;list&#40;object&#40;&#123;&#10; protocol &#61; optional&#40;string, &#34;all&#34;&#41;&#10; ports &#61; optional&#40;list&#40;string&#41;&#41;&#10; &#125;&#41;&#41;, &#91;&#123;&#125;&#93;&#41;&#10; &#125;&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [egress_rules](variables.tf#L30) | List of egress rule definitions, action can be 'allow', 'deny', 'goto_next'. The match.layer4configs map is in protocol => optional [ports] format. | <code title="map&#40;object&#40;&#123;&#10; priority &#61; number&#10; action &#61; optional&#40;string, &#34;deny&#34;&#41;&#10; description &#61; optional&#40;string&#41;&#10; disabled &#61; optional&#40;bool, false&#41;&#10; enable_logging &#61; optional&#40;bool&#41;&#10; target_service_accounts &#61; optional&#40;list&#40;string&#41;&#41;&#10; target_tags &#61; optional&#40;list&#40;string&#41;&#41;&#10; match &#61; object&#40;&#123;&#10; address_groups &#61; optional&#40;list&#40;string&#41;&#41;&#10; fqdns &#61; optional&#40;list&#40;string&#41;&#41;&#10; region_codes &#61; optional&#40;list&#40;string&#41;&#41;&#10; threat_intelligences &#61; optional&#40;list&#40;string&#41;&#41;&#10; destination_ranges &#61; optional&#40;list&#40;string&#41;&#41;&#10; source_ranges &#61; optional&#40;list&#40;string&#41;&#41;&#10; source_tags &#61; optional&#40;list&#40;string&#41;&#41;&#10; layer4_configs &#61; optional&#40;list&#40;object&#40;&#123;&#10; protocol &#61; optional&#40;string, &#34;all&#34;&#41;&#10; ports &#61; optional&#40;list&#40;string&#41;&#41;&#10; &#125;&#41;&#41;, &#91;&#123;&#125;&#93;&#41;&#10; &#125;&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [ingress_rules](variables.tf#L71) | List of ingress rule definitions, action can be 'allow', 'deny', 'goto_next'. | <code title="map&#40;object&#40;&#123;&#10; priority &#61; number&#10; action &#61; optional&#40;string, &#34;allow&#34;&#41;&#10; description &#61; optional&#40;string&#41;&#10; disabled &#61; optional&#40;bool, false&#41;&#10; enable_logging &#61; optional&#40;bool&#41;&#10; target_service_accounts &#61; optional&#40;list&#40;string&#41;&#41;&#10; target_tags &#61; optional&#40;list&#40;string&#41;&#41;&#10; match &#61; object&#40;&#123;&#10; address_groups &#61; optional&#40;list&#40;string&#41;&#41;&#10; fqdns &#61; optional&#40;list&#40;string&#41;&#41;&#10; region_codes &#61; optional&#40;list&#40;string&#41;&#41;&#10; threat_intelligences &#61; optional&#40;list&#40;string&#41;&#41;&#10; destination_ranges &#61; optional&#40;list&#40;string&#41;&#41;&#10; source_ranges &#61; optional&#40;list&#40;string&#41;&#41;&#10; source_tags &#61; optional&#40;list&#40;string&#41;&#41;&#10; layer4_configs &#61; optional&#40;list&#40;object&#40;&#123;&#10; protocol &#61; optional&#40;string, &#34;all&#34;&#41;&#10; ports &#61; optional&#40;list&#40;string&#41;&#41;&#10; &#125;&#41;&#41;, &#91;&#123;&#125;&#93;&#41;&#10; &#125;&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [ingress_rules](variables.tf#L71) | List of ingress rule definitions, action can be 'allow', 'deny', 'goto_next'. | <code title="map&#40;object&#40;&#123;&#10; priority &#61; number&#10; action &#61; optional&#40;string, &#34;allow&#34;&#41;&#10; description &#61; optional&#40;string&#41;&#10; disabled &#61; optional&#40;bool, false&#41;&#10; enable_logging &#61; optional&#40;bool&#41;&#10; target_service_accounts &#61; optional&#40;list&#40;string&#41;&#41;&#10; target_tags &#61; optional&#40;list&#40;string&#41;&#41;&#10; match &#61; object&#40;&#123;&#10; address_groups &#61; optional&#40;list&#40;string&#41;&#41;&#10; fqdns &#61; optional&#40;list&#40;string&#41;&#41;&#10; region_codes &#61; optional&#40;list&#40;string&#41;&#41;&#10; threat_intelligences &#61; optional&#40;list&#40;string&#41;&#41;&#10; destination_ranges &#61; optional&#40;list&#40;string&#41;&#41;&#10; source_ranges &#61; optional&#40;list&#40;string&#41;&#41;&#10; source_tags &#61; optional&#40;list&#40;string&#41;&#41;&#10; layer4_configs &#61; optional&#40;list&#40;object&#40;&#123;&#10; protocol &#61; optional&#40;string, &#34;all&#34;&#41;&#10; ports &#61; optional&#40;list&#40;string&#41;&#41;&#10; &#125;&#41;&#41;, &#91;&#123;&#125;&#93;&#41;&#10; &#125;&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [region](variables.tf#L125) | Policy region. Leave null for hierarchical policy, or global network policy. | <code>string</code> | | <code>null</code> | | [region](variables.tf#L125) | Policy region. Leave null for hierarchical policy, set to 'global' for a global network policy. | <code>string</code> | | <code>null</code> |
| [rules_factory_config](variables.tf#L131) | Configuration for the optional rules factory. | <code title="object&#40;&#123;&#10; cidr_file_path &#61; optional&#40;string&#41;&#10; egress_rules_file_path &#61; optional&#40;string&#41;&#10; ingress_rules_file_path &#61; optional&#40;string&#41;&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>&#123;&#125;</code> | | [rules_factory_config](variables.tf#L131) | Configuration for the optional rules factory. | <code title="object&#40;&#123;&#10; cidr_file_path &#61; optional&#40;string&#41;&#10; egress_rules_file_path &#61; optional&#40;string&#41;&#10; ingress_rules_file_path &#61; optional&#40;string&#41;&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>&#123;&#125;</code> |
## Outputs ## Outputs

View File

@ -15,20 +15,14 @@
*/ */
locals { locals {
_factory_egress_rules = ( _factory_egress_rules = try(
var.rules_factory_config.egress_rules_file_path == null yamldecode(file(var.rules_factory_config.egress_rules_file_path)), {}
? {}
: yamldecode(file(var.rules_factory_config.egress_rules_file_path))
) )
_factory_ingress_rules = ( _factory_ingress_rules = try(
var.rules_factory_config.ingress_rules_file_path == null yamldecode(file(var.rules_factory_config.ingress_rules_file_path)), {}
? {}
: yamldecode(file(var.rules_factory_config.ingress_rules_file_path))
) )
factory_cidrs = ( factory_cidrs = try(
var.rules_factory_config.cidr_file_path == null yamldecode(file(var.rules_factory_config.cidr_file_path)), {}
? {}
: yamldecode(file(var.rules_factory_config.cidr_file_path))
) )
factory_egress_rules = { factory_egress_rules = {
for k, v in local._factory_egress_rules : "ingress/${k}" => { for k, v in local._factory_egress_rules : "ingress/${k}" => {

View File

@ -27,6 +27,7 @@ locals {
local.factory_egress_rules, local.factory_ingress_rules, local.factory_egress_rules, local.factory_ingress_rules,
local._rules_egress, local._rules_ingress local._rules_egress, local._rules_ingress
) )
use_hierarchical = strcontains(var.parent_id, "/") ? true : false # do not depend on the parent id as that might be dynamic and prevent count
use_regional = !local.use_hierarchical && var.region != null use_hierarchical = var.region == null
use_regional = !local.use_hierarchical && var.region != "global"
} }

View File

@ -16,9 +16,13 @@
output "id" { output "id" {
description = "Fully qualified firewall policy id." description = "Fully qualified firewall policy id."
value = coalesce([ value = (
try(google_compute_firewall_policy.hierarchical.0.id, null), local.use_hierarchical
try(google_compute_network_firewall_policy.net-global.0.id, null), ? google_compute_firewall_policy.hierarchical.0.id
try(google_compute_region_network_firewall_policy.net-regional.0.id, null) : (
]) local.use_regional
? google_compute_region_network_firewall_policy.net-regional.0.id
: google_compute_network_firewall_policy.net-global.0.id
)
)
} }

View File

@ -123,7 +123,7 @@ variable "parent_id" {
} }
variable "region" { variable "region" {
description = "Policy region. Leave null for hierarchical policy, or global network policy." description = "Policy region. Leave null for hierarchical policy, set to 'global' for a global network policy."
type = string type = string
default = null default = null
} }

View File

@ -11,6 +11,7 @@ This module allows managing several organization properties:
To manage organization policies, the `orgpolicy.googleapis.com` service should be enabled in the quota project. To manage organization policies, the `orgpolicy.googleapis.com` service should be enabled in the quota project.
## TOC ## TOC
<!-- BEGIN TOC --> <!-- BEGIN TOC -->
- [TOC](#toc) - [TOC](#toc)
- [Example](#example) - [Example](#example)
@ -19,9 +20,7 @@ To manage organization policies, the `orgpolicy.googleapis.com` service should b
- [Organization Policy Factory](#organization-policy-factory) - [Organization Policy Factory](#organization-policy-factory)
- [Organization Policy Custom Constraints](#organization-policy-custom-constraints) - [Organization Policy Custom Constraints](#organization-policy-custom-constraints)
- [Organization Policy Custom Constraints Factory](#organization-policy-custom-constraints-factory) - [Organization Policy Custom Constraints Factory](#organization-policy-custom-constraints-factory)
- [Hierarchical Firewall Policies](#hierarchical-firewall-policies) - [Hierarchical Firewall Policy Attachments](#hierarchical-firewall-policy-attachments)
- [Directly Defined Firewall Policies](#directly-defined-firewall-policies)
- [Firewall Policy Factory](#firewall-policy-factory)
- [Log Sinks](#log-sinks) - [Log Sinks](#log-sinks)
- [Data Access Logs](#data-access-logs) - [Data Access Logs](#data-access-logs)
- [Custom Roles](#custom-roles) - [Custom Roles](#custom-roles)
@ -226,109 +225,30 @@ custom.dataprocNoMoreThan10Workers:
description: Cluster cannot have more than 10 workers, including primary and secondary workers. description: Cluster cannot have more than 10 workers, including primary and secondary workers.
``` ```
## Hierarchical Firewall Policies ## Hierarchical Firewall Policy Attachments
Hierarchical firewall policies can be managed in two ways: Hierarchical firewall policies can be managed via the [`net-firewall-policy`](../net-firewall-policy/) module, including support for factories. Once a policy is available, attaching it to the organization can be done either in the firewall policy module itself, or here:
- via the `firewall_policies` variable, to directly define policies and rules in Terraform
- via the `firewall_policy_factory` variable, to leverage external YaML files via a simple "factory" embedded in the module ([see here](../../blueprints/factories) for more context on factories)
Once you have policies (either created via the module or externally), you can associate them using the `firewall_policy_association` variable.
### Directly Defined Firewall Policies
```hcl ```hcl
module "firewall-policy" {
source = "./fabric/modules/net-firewall-policy"
name = "test-1"
parent_id = var.organization_id
# attachment via the firewall policy module
# attachments = {
# org = var.organization_id
# }
}
module "org" { module "org" {
source = "./fabric/modules/organization" source = "./fabric/modules/organization"
organization_id = var.organization_id organization_id = var.organization_id
firewall_policies = { # attachment via the organization module
iap-policy = { firewall_policy_associations = {
allow-admins = { test-1 = module.firewall-policy.id
description = "Access from the admin subnet to all subnets"
direction = "INGRESS"
action = "allow"
priority = 1000
ranges = ["10.0.0.0/8", "172.16.0.0/12", "192.168.0.0/16"]
ports = { all = [] }
target_service_accounts = null
target_resources = null
logging = false
}
allow-iap-ssh = {
description = "Always allow ssh from IAP."
direction = "INGRESS"
action = "allow"
priority = 100
ranges = ["35.235.240.0/20"]
ports = {
tcp = ["22"]
}
target_service_accounts = null
target_resources = null
logging = false
}
}
}
firewall_policy_association = {
iap_policy = "iap-policy"
} }
} }
# tftest modules=1 resources=4 inventory=hfw.yaml # tftest modules=2 resources=2
```
### Firewall Policy Factory
The in-built factory allows you to define a single policy, using one file for rules, and an optional file for CIDR range substitution variables. Remember that non-absolute paths are relative to the root module (the folder where you run `terraform`).
```hcl
module "org" {
source = "./fabric/modules/organization"
organization_id = var.organization_id
firewall_policy_factory = {
cidr_file = "configs/firewall-policies/cidrs.yaml"
policy_name = "iap-policy"
rules_file = "configs/firewall-policies/rules.yaml"
}
firewall_policy_association = {
iap_policy = module.org.firewall_policy_id["iap-policy"]
}
}
# tftest modules=1 resources=4 files=cidrs,rules inventory=hfw.yaml
```
```yaml
# tftest-file id=cidrs path=configs/firewall-policies/cidrs.yaml
rfc1918:
- 10.0.0.0/8
- 172.16.0.0/12
- 192.168.0.0/16
```
```yaml
# tftest-file id=rules path=configs/firewall-policies/rules.yaml
allow-admins:
description: Access from the admin subnet to all subnets
direction: INGRESS
action: allow
priority: 1000
ranges:
- $rfc1918
ports:
all: []
target_resources: null
logging: false
allow-iap-ssh:
description: "Always allow ssh from IAP."
direction: INGRESS
action: allow
priority: 100
ranges:
- 35.235.240.0/20
ports:
tcp: ["22"]
target_resources: null
logging: false
``` ```
## Log Sinks ## Log Sinks
@ -530,18 +450,14 @@ module "org" {
``` ```
<!-- TFDOC OPTS files:1 --> <!-- TFDOC OPTS files:1 -->
<!-- BEGIN TFDOC --> <!-- BEGIN TFDOC -->
## Files ## Files
| name | description | resources | | name | description | resources |
|---|---|---| |---|---|---|
| [firewall-policies.tf](./firewall-policies.tf) | Hierarchical firewall policies. | <code>google_compute_firewall_policy</code> · <code>google_compute_firewall_policy_association</code> · <code>google_compute_firewall_policy_rule</code> |
| [iam.tf](./iam.tf) | IAM bindings, roles and audit logging resources. | <code>google_organization_iam_binding</code> · <code>google_organization_iam_custom_role</code> · <code>google_organization_iam_member</code> · <code>google_organization_iam_policy</code> | | [iam.tf](./iam.tf) | IAM bindings, roles and audit logging resources. | <code>google_organization_iam_binding</code> · <code>google_organization_iam_custom_role</code> · <code>google_organization_iam_member</code> · <code>google_organization_iam_policy</code> |
| [logging.tf](./logging.tf) | Log sinks and data access logs. | <code>google_bigquery_dataset_iam_member</code> · <code>google_logging_organization_exclusion</code> · <code>google_logging_organization_sink</code> · <code>google_organization_iam_audit_config</code> · <code>google_project_iam_member</code> · <code>google_pubsub_topic_iam_member</code> · <code>google_storage_bucket_iam_member</code> | | [logging.tf](./logging.tf) | Log sinks and data access logs. | <code>google_bigquery_dataset_iam_member</code> · <code>google_logging_organization_exclusion</code> · <code>google_logging_organization_sink</code> · <code>google_organization_iam_audit_config</code> · <code>google_project_iam_member</code> · <code>google_pubsub_topic_iam_member</code> · <code>google_storage_bucket_iam_member</code> |
| [main.tf](./main.tf) | Module-level locals and resources. | <code>google_essential_contacts_contact</code> | | [main.tf](./main.tf) | Module-level locals and resources. | <code>google_compute_firewall_policy_association</code> · <code>google_essential_contacts_contact</code> |
| [org-policy-custom-constraints.tf](./org-policy-custom-constraints.tf) | None | <code>google_org_policy_custom_constraint</code> | | [org-policy-custom-constraints.tf](./org-policy-custom-constraints.tf) | None | <code>google_org_policy_custom_constraint</code> |
| [organization-policies.tf](./organization-policies.tf) | Organization-level organization policies. | <code>google_org_policy_policy</code> | | [organization-policies.tf](./organization-policies.tf) | Organization-level organization policies. | <code>google_org_policy_policy</code> |
| [outputs.tf](./outputs.tf) | Module outputs. | | | [outputs.tf](./outputs.tf) | Module outputs. | |
@ -553,27 +469,25 @@ module "org" {
| name | description | type | required | default | | name | description | type | required | default |
|---|---|:---:|:---:|:---:| |---|---|:---:|:---:|:---:|
| [organization_id](variables.tf#L226) | Organization id in organizations/nnnnnn format. | <code>string</code> | ✓ | | | [organization_id](variables.tf#L199) | Organization id in organizations/nnnnnn format. | <code>string</code> | ✓ | |
| [contacts](variables.tf#L17) | List of essential contacts for this resource. Must be in the form EMAIL -> [NOTIFICATION_TYPES]. Valid notification types are ALL, SUSPENSION, SECURITY, TECHNICAL, BILLING, LEGAL, PRODUCT_UPDATES. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [contacts](variables.tf#L17) | List of essential contacts for this resource. Must be in the form EMAIL -> [NOTIFICATION_TYPES]. Valid notification types are ALL, SUSPENSION, SECURITY, TECHNICAL, BILLING, LEGAL, PRODUCT_UPDATES. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [custom_roles](variables.tf#L24) | Map of role name => list of permissions to create in this project. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [custom_roles](variables.tf#L24) | Map of role name => list of permissions to create in this project. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [firewall_policies](variables.tf#L31) | Hierarchical firewall policy rules created in the organization. | <code title="map&#40;map&#40;object&#40;&#123;&#10; action &#61; string&#10; description &#61; string&#10; direction &#61; string&#10; logging &#61; bool&#10; ports &#61; map&#40;list&#40;string&#41;&#41;&#10; priority &#61; number&#10; ranges &#61; list&#40;string&#41;&#10; target_resources &#61; list&#40;string&#41;&#10; target_service_accounts &#61; list&#40;string&#41;&#10;&#125;&#41;&#41;&#41;">map&#40;map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [firewall_policy_associations](variables.tf#L31) | Hierarchical firewall policies to associate to this folder, in association name => policy id format. | <code>map&#40;string&#41;</code> | | <code>&#123;&#125;</code> |
| [firewall_policy_association](variables.tf#L48) | The hierarchical firewall policy to associate to this folder. Must be either a key in the `firewall_policies` map or the id of a policy defined somewhere else. | <code>map&#40;string&#41;</code> | | <code>&#123;&#125;</code> | | [group_iam](variables.tf#L38) | Authoritative IAM binding for organization groups, in {GROUP_EMAIL => [ROLES]} format. Group emails need to be static. Can be used in combination with the `iam` variable. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [firewall_policy_factory](variables.tf#L55) | Configuration for the firewall policy factory. | <code title="object&#40;&#123;&#10; cidr_file &#61; string&#10; policy_name &#61; string&#10; rules_file &#61; string&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>null</code> | | [iam](variables.tf#L45) | IAM bindings, in {ROLE => [MEMBERS]} format. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [group_iam](variables.tf#L65) | Authoritative IAM binding for organization groups, in {GROUP_EMAIL => [ROLES]} format. Group emails need to be static. Can be used in combination with the `iam` variable. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [iam_additive](variables.tf#L52) | Non authoritative IAM bindings, in {ROLE => [MEMBERS]} format. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [iam](variables.tf#L72) | IAM bindings, in {ROLE => [MEMBERS]} format. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [iam_additive_members](variables.tf#L59) | IAM additive bindings in {MEMBERS => [ROLE]} format. This might break if members are dynamic values. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [iam_additive](variables.tf#L79) | Non authoritative IAM bindings, in {ROLE => [MEMBERS]} format. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [iam_policy](variables.tf#L66) | IAM authoritative policy in {ROLE => [MEMBERS]} format. Roles and members not explicitly listed will be cleared, use with extreme caution. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>null</code> |
| [iam_additive_members](variables.tf#L86) | IAM additive bindings in {MEMBERS => [ROLE]} format. This might break if members are dynamic values. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [logging_data_access](variables.tf#L72) | Control activation of data access logs. Format is service => { log type => [exempted members]}. The special 'allServices' key denotes configuration for all services. | <code>map&#40;map&#40;list&#40;string&#41;&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [iam_policy](variables.tf#L93) | IAM authoritative policy in {ROLE => [MEMBERS]} format. Roles and members not explicitly listed will be cleared, use with extreme caution. | <code>map&#40;list&#40;string&#41;&#41;</code> | | <code>null</code> | | [logging_exclusions](variables.tf#L87) | Logging exclusions for this organization in the form {NAME -> FILTER}. | <code>map&#40;string&#41;</code> | | <code>&#123;&#125;</code> |
| [logging_data_access](variables.tf#L99) | Control activation of data access logs. Format is service => { log type => [exempted members]}. The special 'allServices' key denotes configuration for all services. | <code>map&#40;map&#40;list&#40;string&#41;&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [logging_sinks](variables.tf#L94) | Logging sinks to create for the organization. | <code title="map&#40;object&#40;&#123;&#10; bq_partitioned_table &#61; optional&#40;bool&#41;&#10; description &#61; optional&#40;string&#41;&#10; destination &#61; string&#10; disabled &#61; optional&#40;bool, false&#41;&#10; exclusions &#61; optional&#40;map&#40;string&#41;, &#123;&#125;&#41;&#10; filter &#61; string&#10; include_children &#61; optional&#40;bool, true&#41;&#10; type &#61; string&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [logging_exclusions](variables.tf#L114) | Logging exclusions for this organization in the form {NAME -> FILTER}. | <code>map&#40;string&#41;</code> | | <code>&#123;&#125;</code> | | [network_tags](variables.tf#L124) | Network tags by key name. If `id` is provided, key creation is skipped. The `iam` attribute behaves like the similarly named one at module level. | <code title="map&#40;object&#40;&#123;&#10; description &#61; optional&#40;string, &#34;Managed by the Terraform organization module.&#34;&#41;&#10; iam &#61; optional&#40;map&#40;list&#40;string&#41;&#41;, &#123;&#125;&#41;&#10; id &#61; optional&#40;string&#41;&#10; network &#61; string &#35; project_id&#47;vpc_name&#10; values &#61; optional&#40;map&#40;object&#40;&#123;&#10; description &#61; optional&#40;string, &#34;Managed by the Terraform organization module.&#34;&#41;&#10; iam &#61; optional&#40;map&#40;list&#40;string&#41;&#41;, &#123;&#125;&#41;&#10; &#125;&#41;&#41;, &#123;&#125;&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [logging_sinks](variables.tf#L121) | Logging sinks to create for the organization. | <code title="map&#40;object&#40;&#123;&#10; bq_partitioned_table &#61; optional&#40;bool&#41;&#10; description &#61; optional&#40;string&#41;&#10; destination &#61; string&#10; disabled &#61; optional&#40;bool, false&#41;&#10; exclusions &#61; optional&#40;map&#40;string&#41;, &#123;&#125;&#41;&#10; filter &#61; string&#10; include_children &#61; optional&#40;bool, true&#41;&#10; type &#61; string&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [org_policies](variables.tf#L146) | Organization policies applied to this organization keyed by policy name. | <code title="map&#40;object&#40;&#123;&#10; inherit_from_parent &#61; optional&#40;bool&#41; &#35; for list policies only.&#10; reset &#61; optional&#40;bool&#41;&#10; rules &#61; optional&#40;list&#40;object&#40;&#123;&#10; allow &#61; optional&#40;object&#40;&#123;&#10; all &#61; optional&#40;bool&#41;&#10; values &#61; optional&#40;list&#40;string&#41;&#41;&#10; &#125;&#41;&#41;&#10; deny &#61; optional&#40;object&#40;&#123;&#10; all &#61; optional&#40;bool&#41;&#10; values &#61; optional&#40;list&#40;string&#41;&#41;&#10; &#125;&#41;&#41;&#10; enforce &#61; optional&#40;bool&#41; &#35; for boolean policies only.&#10; condition &#61; optional&#40;object&#40;&#123;&#10; description &#61; optional&#40;string&#41;&#10; expression &#61; optional&#40;string&#41;&#10; location &#61; optional&#40;string&#41;&#10; title &#61; optional&#40;string&#41;&#10; &#125;&#41;, &#123;&#125;&#41;&#10; &#125;&#41;&#41;, &#91;&#93;&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [network_tags](variables.tf#L151) | Network tags by key name. If `id` is provided, key creation is skipped. The `iam` attribute behaves like the similarly named one at module level. | <code title="map&#40;object&#40;&#123;&#10; description &#61; optional&#40;string, &#34;Managed by the Terraform organization module.&#34;&#41;&#10; iam &#61; optional&#40;map&#40;list&#40;string&#41;&#41;, &#123;&#125;&#41;&#10; id &#61; optional&#40;string&#41;&#10; network &#61; string &#35; project_id&#47;vpc_name&#10; values &#61; optional&#40;map&#40;object&#40;&#123;&#10; description &#61; optional&#40;string, &#34;Managed by the Terraform organization module.&#34;&#41;&#10; iam &#61; optional&#40;map&#40;list&#40;string&#41;&#41;, &#123;&#125;&#41;&#10; &#125;&#41;&#41;, &#123;&#125;&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [org_policies_data_path](variables.tf#L173) | Path containing org policies in YAML format. | <code>string</code> | | <code>null</code> |
| [org_policies](variables.tf#L173) | Organization policies applied to this organization keyed by policy name. | <code title="map&#40;object&#40;&#123;&#10; inherit_from_parent &#61; optional&#40;bool&#41; &#35; for list policies only.&#10; reset &#61; optional&#40;bool&#41;&#10; rules &#61; optional&#40;list&#40;object&#40;&#123;&#10; allow &#61; optional&#40;object&#40;&#123;&#10; all &#61; optional&#40;bool&#41;&#10; values &#61; optional&#40;list&#40;string&#41;&#41;&#10; &#125;&#41;&#41;&#10; deny &#61; optional&#40;object&#40;&#123;&#10; all &#61; optional&#40;bool&#41;&#10; values &#61; optional&#40;list&#40;string&#41;&#41;&#10; &#125;&#41;&#41;&#10; enforce &#61; optional&#40;bool&#41; &#35; for boolean policies only.&#10; condition &#61; optional&#40;object&#40;&#123;&#10; description &#61; optional&#40;string&#41;&#10; expression &#61; optional&#40;string&#41;&#10; location &#61; optional&#40;string&#41;&#10; title &#61; optional&#40;string&#41;&#10; &#125;&#41;, &#123;&#125;&#41;&#10; &#125;&#41;&#41;, &#91;&#93;&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [org_policy_custom_constraints](variables.tf#L179) | Organization policy custom constraints keyed by constraint name. | <code title="map&#40;object&#40;&#123;&#10; display_name &#61; optional&#40;string&#41;&#10; description &#61; optional&#40;string&#41;&#10; action_type &#61; string&#10; condition &#61; string&#10; method_types &#61; list&#40;string&#41;&#10; resource_types &#61; list&#40;string&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [org_policies_data_path](variables.tf#L200) | Path containing org policies in YAML format. | <code>string</code> | | <code>null</code> | | [org_policy_custom_constraints_data_path](variables.tf#L193) | Path containing org policy custom constraints in YAML format. | <code>string</code> | | <code>null</code> |
| [org_policy_custom_constraints](variables.tf#L206) | Organization policy custom constraints keyed by constraint name. | <code title="map&#40;object&#40;&#123;&#10; display_name &#61; optional&#40;string&#41;&#10; description &#61; optional&#40;string&#41;&#10; action_type &#61; string&#10; condition &#61; string&#10; method_types &#61; list&#40;string&#41;&#10; resource_types &#61; list&#40;string&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> | | [tag_bindings](variables.tf#L208) | Tag bindings for this organization, in key => tag value id format. | <code>map&#40;string&#41;</code> | | <code>null</code> |
| [org_policy_custom_constraints_data_path](variables.tf#L220) | Path containing org policy custom constraints in YAML format. | <code>string</code> | | <code>null</code> | | [tags](variables.tf#L214) | Tags by key name. If `id` is provided, key or value creation is skipped. The `iam` attribute behaves like the similarly named one at module level. | <code title="map&#40;object&#40;&#123;&#10; description &#61; optional&#40;string, &#34;Managed by the Terraform organization module.&#34;&#41;&#10; iam &#61; optional&#40;map&#40;list&#40;string&#41;&#41;, &#123;&#125;&#41;&#10; id &#61; optional&#40;string&#41;&#10; values &#61; optional&#40;map&#40;object&#40;&#123;&#10; description &#61; optional&#40;string, &#34;Managed by the Terraform organization module.&#34;&#41;&#10; iam &#61; optional&#40;map&#40;list&#40;string&#41;&#41;, &#123;&#125;&#41;&#10; id &#61; optional&#40;string&#41;&#10; &#125;&#41;&#41;, &#123;&#125;&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> |
| [tag_bindings](variables.tf#L235) | Tag bindings for this organization, in key => tag value id format. | <code>map&#40;string&#41;</code> | | <code>null</code> |
| [tags](variables.tf#L241) | Tags by key name. If `id` is provided, key or value creation is skipped. The `iam` attribute behaves like the similarly named one at module level. | <code title="map&#40;object&#40;&#123;&#10; description &#61; optional&#40;string, &#34;Managed by the Terraform organization module.&#34;&#41;&#10; iam &#61; optional&#40;map&#40;list&#40;string&#41;&#41;, &#123;&#125;&#41;&#10; id &#61; optional&#40;string&#41;&#10; values &#61; optional&#40;map&#40;object&#40;&#123;&#10; description &#61; optional&#40;string, &#34;Managed by the Terraform organization module.&#34;&#41;&#10; iam &#61; optional&#40;map&#40;list&#40;string&#41;&#41;, &#123;&#125;&#41;&#10; id &#61; optional&#40;string&#41;&#10; &#125;&#41;&#41;, &#123;&#125;&#41;&#10;&#125;&#41;&#41;">map&#40;object&#40;&#123;&#8230;&#125;&#41;&#41;</code> | | <code>&#123;&#125;</code> |
## Outputs ## Outputs
@ -582,13 +496,11 @@ module "org" {
| [custom_constraint_ids](outputs.tf#L17) | Map of CUSTOM_CONSTRAINTS => ID in the organization. | | | [custom_constraint_ids](outputs.tf#L17) | Map of CUSTOM_CONSTRAINTS => ID in the organization. | |
| [custom_role_id](outputs.tf#L22) | Map of custom role IDs created in the organization. | | | [custom_role_id](outputs.tf#L22) | Map of custom role IDs created in the organization. | |
| [custom_roles](outputs.tf#L35) | Map of custom roles resources created in the organization. | | | [custom_roles](outputs.tf#L35) | Map of custom roles resources created in the organization. | |
| [firewall_policies](outputs.tf#L40) | Map of firewall policy resources created in the organization. | | | [id](outputs.tf#L40) | Fully qualified organization id. | |
| [firewall_policy_id](outputs.tf#L45) | Map of firewall policy ids created in the organization. | | | [network_tag_keys](outputs.tf#L57) | Tag key resources. | |
| [id](outputs.tf#L50) | Fully qualified organization id. | | | [network_tag_values](outputs.tf#L66) | Tag value resources. | |
| [network_tag_keys](outputs.tf#L67) | Tag key resources. | | | [organization_id](outputs.tf#L76) | Organization id dependent on module resources. | |
| [network_tag_values](outputs.tf#L76) | Tag value resources. | | | [sink_writer_identities](outputs.tf#L93) | Writer identities created for each sink. | |
| [organization_id](outputs.tf#L86) | Organization id dependent on module resources. | | | [tag_keys](outputs.tf#L101) | Tag key resources. | |
| [sink_writer_identities](outputs.tf#L103) | Writer identities created for each sink. | | | [tag_values](outputs.tf#L110) | Tag value resources. | |
| [tag_keys](outputs.tf#L111) | Tag key resources. | |
| [tag_values](outputs.tf#L120) | Tag value resources. | |
<!-- END TFDOC --> <!-- END TFDOC -->

View File

@ -1,100 +0,0 @@
/**
* Copyright 2022 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.
*/
# tfdoc:file:description Hierarchical firewall policies.
locals {
_factory_cidrs = try(
yamldecode(file(var.firewall_policy_factory.cidr_file)), {}
)
_factory_name = (
try(var.firewall_policy_factory.policy_name, null) == null
? "factory"
: var.firewall_policy_factory.policy_name
)
_factory_rules = try(
yamldecode(file(var.firewall_policy_factory.rules_file)), {}
)
_factory_rules_parsed = {
for name, rule in local._factory_rules : name => merge(rule, {
ranges = flatten([
for r in(rule.ranges == null ? [] : rule.ranges) :
lookup(local._factory_cidrs, trimprefix(r, "$"), r)
])
})
}
_merged_rules = flatten([
for policy, rules in local.firewall_policies : [
for name, rule in rules : merge(rule, {
policy = policy
name = name
})
]
])
firewall_policies = merge(var.firewall_policies, (
length(local._factory_rules) == 0
? {}
: { (local._factory_name) = local._factory_rules_parsed }
))
firewall_rules = {
for r in local._merged_rules : "${r.policy}-${r.name}" => r
}
}
resource "google_compute_firewall_policy" "policy" {
for_each = local.firewall_policies
short_name = each.key
parent = var.organization_id
depends_on = [
google_organization_iam_binding.authoritative,
google_organization_iam_custom_role.roles,
google_organization_iam_member.additive,
google_organization_iam_policy.authoritative,
]
}
resource "google_compute_firewall_policy_rule" "rule" {
for_each = local.firewall_rules
firewall_policy = google_compute_firewall_policy.policy[each.value.policy].id
action = each.value.action
direction = each.value.direction
priority = try(each.value.priority, null)
target_resources = try(each.value.target_resources, null)
target_service_accounts = try(each.value.target_service_accounts, null)
enable_logging = try(each.value.logging, null)
# preview = each.value.preview
description = each.value.description
match {
src_ip_ranges = each.value.direction == "INGRESS" ? each.value.ranges : null
dest_ip_ranges = each.value.direction == "EGRESS" ? each.value.ranges : null
dynamic "layer4_configs" {
for_each = each.value.ports
iterator = port
content {
ip_protocol = port.key
ports = port.value
}
}
}
}
resource "google_compute_firewall_policy_association" "association" {
for_each = var.firewall_policy_association
name = replace(var.organization_id, "/", "-")
attachment_target = var.organization_id
firewall_policy = try(google_compute_firewall_policy.policy[each.value].id, each.value)
}

View File

@ -26,3 +26,10 @@ resource "google_essential_contacts_contact" "contact" {
language_tag = "en" language_tag = "en"
notification_category_subscriptions = each.value notification_category_subscriptions = each.value
} }
resource "google_compute_firewall_policy_association" "default" {
for_each = var.firewall_policy_associations
attachment_target = var.organization_id
name = each.key
firewall_policy = each.value
}

View File

@ -37,16 +37,6 @@ output "custom_roles" {
value = google_organization_iam_custom_role.roles value = google_organization_iam_custom_role.roles
} }
output "firewall_policies" {
description = "Map of firewall policy resources created in the organization."
value = { for k, v in google_compute_firewall_policy.policy : k => v }
}
output "firewall_policy_id" {
description = "Map of firewall policy ids created in the organization."
value = { for k, v in google_compute_firewall_policy.policy : k => v.id }
}
output "id" { output "id" {
description = "Fully qualified organization id." description = "Fully qualified organization id."
value = var.organization_id value = var.organization_id

View File

@ -28,40 +28,13 @@ variable "custom_roles" {
nullable = false nullable = false
} }
variable "firewall_policies" { variable "firewall_policy_associations" {
description = "Hierarchical firewall policy rules created in the organization." description = "Hierarchical firewall policies to associate to this folder, in association name => policy id format."
type = map(map(object({
action = string
description = string
direction = string
logging = bool
ports = map(list(string))
priority = number
ranges = list(string)
target_resources = list(string)
target_service_accounts = list(string)
# preview = bool
})))
default = {}
}
variable "firewall_policy_association" {
description = "The hierarchical firewall policy to associate to this folder. Must be either a key in the `firewall_policies` map or the id of a policy defined somewhere else."
type = map(string) type = map(string)
default = {} default = {}
nullable = false nullable = false
} }
variable "firewall_policy_factory" {
description = "Configuration for the firewall policy factory."
type = object({
cidr_file = string
policy_name = string
rules_file = string
})
default = null
}
variable "group_iam" { variable "group_iam" {
description = "Authoritative IAM binding for organization groups, in {GROUP_EMAIL => [ROLES]} format. Group emails need to be static. Can be used in combination with the `iam` variable." description = "Authoritative IAM binding for organization groups, in {GROUP_EMAIL => [ROLES]} format. Group emails need to be static. Can be used in combination with the `iam` variable."
type = map(list(string)) type = map(list(string))

View File

@ -13,21 +13,611 @@
# limitations under the License. # limitations under the License.
values: values:
module.test.module.folder.google_compute_firewall_policy.policy["prefix-fw-policy"]: module.test.module.firewall-policy.google_compute_firewall_policy.hierarchical[0]:
short_name: prefix-fw-policy description: null
short_name: default
timeouts: null
module.test.module.firewall-policy.google_compute_firewall_policy_rule.hierarchical["egress/allow-admins"]:
action: allow
description: Access from the admin subnet to all subnets
direction: INGRESS
disabled: false
enable_logging: null
match:
- dest_address_groups: null
dest_fqdns: null
dest_ip_ranges: null
dest_region_codes: null
dest_threat_intelligences: null
layer4_configs:
- ip_protocol: all
ports: null
src_address_groups: null
src_fqdns: null
src_ip_ranges:
- 10.0.0.0/8
- 172.16.0.0/12
- 192.168.0.0/16
src_region_codes: null
src_threat_intelligences: null
priority: 1000
target_resources: null
target_service_accounts: null
timeouts: null
module.test.module.firewall-policy.google_compute_firewall_policy_rule.hierarchical["egress/allow-healthchecks"]:
action: allow
description: Enable HTTP and HTTPS healthchecks
direction: INGRESS
disabled: false
enable_logging: null
match:
- dest_address_groups: null
dest_fqdns: null
dest_ip_ranges: null
dest_region_codes: null
dest_threat_intelligences: null
layer4_configs:
- ip_protocol: all
ports: null
src_address_groups: null
src_fqdns: null
src_ip_ranges:
- 35.191.0.0/16
- 130.211.0.0/22
- 209.85.152.0/22
- 209.85.204.0/22
src_region_codes: null
src_threat_intelligences: null
priority: 1001
target_resources: null
target_service_accounts: null
timeouts: null
module.test.module.firewall-policy.google_compute_firewall_policy_rule.hierarchical["egress/allow-icmp"]:
action: allow
description: Enable ICMP
direction: INGRESS
disabled: false
enable_logging: null
match:
- dest_address_groups: null
dest_fqdns: null
dest_ip_ranges: null
dest_region_codes: null
dest_threat_intelligences: null
layer4_configs:
- ip_protocol: all
ports: null
src_address_groups: null
src_fqdns: null
src_ip_ranges:
- 0.0.0.0/0
src_region_codes: null
src_threat_intelligences: null
priority: 1003
target_resources: null
target_service_accounts: null
timeouts: null
module.test.module.firewall-policy.google_compute_firewall_policy_rule.hierarchical["egress/allow-ssh-from-iap"]:
action: allow
description: Enable SSH from IAP
direction: INGRESS
disabled: false
enable_logging: null
match:
- dest_address_groups: null
dest_fqdns: null
dest_ip_ranges: null
dest_region_codes: null
dest_threat_intelligences: null
layer4_configs:
- ip_protocol: all
ports: null
src_address_groups: null
src_fqdns: null
src_ip_ranges:
- 35.235.240.0/20
src_region_codes: null
src_threat_intelligences: null
priority: 1002
target_resources: null
target_service_accounts: null
timeouts: null
module.test.module.folder-workload.google_folder.folder[0]:
display_name: prefix-workload
timeouts: null
module.test.module.folder.google_bigquery_dataset_iam_member.bq-sinks-binding["audit-logs"]:
condition: []
role: roles/bigquery.dataEditor
module.test.module.folder.google_bigquery_dataset_iam_member.bq-sinks-binding["vpc-sc"]:
condition: []
role: roles/bigquery.dataEditor
module.test.module.folder.google_folder.folder[0]: module.test.module.folder.google_folder.folder[0]:
display_name: ShieldedMVP display_name: ShieldedMVP
parent: organizations/1234567890123 parent: organizations/1234567890123
timeouts: null
module.test.module.folder.google_folder_iam_binding.authoritative["roles/editor"]:
condition: []
members:
- group:gcp-data-engineers@example.com
role: roles/editor
module.test.module.folder.google_folder_iam_binding.authoritative["roles/iam.serviceAccountTokenCreator"]:
condition: []
members:
- group:gcp-data-engineers@example.com
role: roles/iam.serviceAccountTokenCreator
module.test.module.folder.google_logging_folder_sink.sink["audit-logs"]:
description: audit-logs (Terraform-managed).
disabled: false
exclusions: []
filter: logName:"/logs/cloudaudit.googleapis.com%2Factivity" OR logName:"/logs/cloudaudit.googleapis.com%2Fsystem_event"
include_children: true
name: audit-logs
module.test.module.folder.google_logging_folder_sink.sink["vpc-sc"]:
description: vpc-sc (Terraform-managed).
disabled: false
exclusions: []
filter: protoPayload.metadata.@type="type.googleapis.com/google.cloud.audit.VpcServiceControlAuditMetadata"
include_children: true
name: vpc-sc
module.test.module.folder.google_org_policy_policy.default["compute.disableGuestAttributesAccess"]:
spec:
- inherit_from_parent: null
reset: null
rules:
- allow_all: null
condition: []
deny_all: null
enforce: 'TRUE'
values: []
timeouts: null
module.test.module.folder.google_org_policy_policy.default["compute.requireOsLogin"]:
spec:
- inherit_from_parent: null
reset: null
rules:
- allow_all: null
condition: []
deny_all: null
enforce: 'TRUE'
values: []
timeouts: null
module.test.module.folder.google_org_policy_policy.default["compute.restrictLoadBalancerCreationForTypes"]:
spec:
- inherit_from_parent: null
reset: null
rules:
- allow_all: null
condition: []
deny_all: null
enforce: null
values:
- allowed_values:
- in:INTERNAL
denied_values: null
timeouts: null
module.test.module.folder.google_org_policy_policy.default["compute.skipDefaultNetworkCreation"]:
spec:
- inherit_from_parent: null
reset: null
rules:
- allow_all: null
condition: []
deny_all: null
enforce: 'TRUE'
values: []
timeouts: null
module.test.module.folder.google_org_policy_policy.default["compute.vmExternalIpAccess"]:
spec:
- inherit_from_parent: null
reset: null
rules:
- allow_all: null
condition: []
deny_all: 'TRUE'
enforce: null
values: []
timeouts: null
module.test.module.folder.google_org_policy_policy.default["iam.automaticIamGrantsForDefaultServiceAccounts"]:
spec:
- inherit_from_parent: null
reset: null
rules:
- allow_all: null
condition: []
deny_all: null
enforce: 'TRUE'
values: []
timeouts: null
module.test.module.folder.google_org_policy_policy.default["iam.disableServiceAccountKeyCreation"]:
spec:
- inherit_from_parent: null
reset: null
rules:
- allow_all: null
condition: []
deny_all: null
enforce: 'TRUE'
values: []
timeouts: null
module.test.module.folder.google_org_policy_policy.default["iam.disableServiceAccountKeyUpload"]:
spec:
- inherit_from_parent: null
reset: null
rules:
- allow_all: null
condition: []
deny_all: null
enforce: 'TRUE'
values: []
timeouts: null
module.test.module.folder.google_org_policy_policy.default["run.allowedIngress"]:
spec:
- inherit_from_parent: null
reset: null
rules:
- allow_all: null
condition: []
deny_all: null
enforce: null
values:
- allowed_values:
- is:internal
denied_values: null
timeouts: null
module.test.module.folder.google_org_policy_policy.default["sql.restrictAuthorizedNetworks"]:
spec:
- inherit_from_parent: null
reset: null
rules:
- allow_all: null
condition: []
deny_all: null
enforce: 'TRUE'
values: []
timeouts: null
module.test.module.folder.google_org_policy_policy.default["sql.restrictPublicIp"]:
spec:
- inherit_from_parent: null
reset: null
rules:
- allow_all: null
condition: []
deny_all: null
enforce: 'TRUE'
values: []
timeouts: null
module.test.module.folder.google_org_policy_policy.default["storage.uniformBucketLevelAccess"]:
spec:
- inherit_from_parent: null
reset: null
rules:
- allow_all: null
condition: []
deny_all: null
enforce: 'TRUE'
values: []
timeouts: null
module.test.module.log-export-dataset[0].google_bigquery_dataset.default:
dataset_id: prefix_audit_export
default_encryption_configuration: []
default_partition_expiration_ms: null
default_table_expiration_ms: null
delete_contents_on_destroy: false
description: Terraform managed.
friendly_name: Audit logs export.
location: EU
max_time_travel_hours: '168'
project: prefix-audit-logs
timeouts: null
module.test.module.log-export-project[0].data.google_bigquery_default_service_account.bq_sa[0]:
project: prefix-audit-logs
module.test.module.log-export-project[0].data.google_storage_project_service_account.gcs_sa[0]:
project: prefix-audit-logs
user_project: null
module.test.module.log-export-project[0].google_project.project[0]: module.test.module.log-export-project[0].google_project.project[0]:
auto_create_network: false
billing_account: 123456-123456-123456 billing_account: 123456-123456-123456
labels: null
name: prefix-audit-logs
project_id: prefix-audit-logs project_id: prefix-audit-logs
skip_delete: false
timeouts: null
module.test.module.log-export-project[0].google_project_iam_binding.authoritative["roles/editor"]:
condition: []
members:
- group:gcp-data-security@example.com
project: prefix-audit-logs
role: roles/editor
module.test.module.log-export-project[0].google_project_service.project_services["bigquery.googleapis.com"]:
disable_dependent_services: false
disable_on_destroy: false
project: prefix-audit-logs
service: bigquery.googleapis.com
timeouts: null
module.test.module.log-export-project[0].google_project_service.project_services["pubsub.googleapis.com"]:
disable_dependent_services: false
disable_on_destroy: false
project: prefix-audit-logs
service: pubsub.googleapis.com
timeouts: null
module.test.module.log-export-project[0].google_project_service.project_services["stackdriver.googleapis.com"]:
disable_dependent_services: false
disable_on_destroy: false
project: prefix-audit-logs
service: stackdriver.googleapis.com
timeouts: null
module.test.module.log-export-project[0].google_project_service.project_services["storage.googleapis.com"]:
disable_dependent_services: false
disable_on_destroy: false
project: prefix-audit-logs
service: storage.googleapis.com
timeouts: null
module.test.module.log-export-project[0].google_project_service_identity.jit_si["pubsub.googleapis.com"]:
project: prefix-audit-logs
service: pubsub.googleapis.com
timeouts: null
module.test.module.vpc-sc[0].google_access_context_manager_access_policy.default[0]: module.test.module.vpc-sc[0].google_access_context_manager_access_policy.default[0]:
parent: organizations/1122334455 parent: organizations/1122334455
timeouts: null
title: shielded-folder title: shielded-folder
module.test.module.vpc-sc[0].google_access_context_manager_service_perimeter.regular["shielded"]: module.test.module.vpc-sc[0].google_access_context_manager_service_perimeter.regular["shielded"]:
description: null description: null
perimeter_type: PERIMETER_TYPE_REGULAR perimeter_type: PERIMETER_TYPE_REGULAR
spec:
- access_levels: []
egress_policies: []
ingress_policies:
- ingress_from:
- identity_type: null
sources:
- access_level: '*'
resource: null
ingress_to:
- operations:
- method_selectors: []
service_name: '*'
restricted_services:
- accessapproval.googleapis.com
- adsdatahub.googleapis.com
- aiplatform.googleapis.com
- alloydb.googleapis.com
- alpha-documentai.googleapis.com
- analyticshub.googleapis.com
- apigee.googleapis.com
- apigeeconnect.googleapis.com
- artifactregistry.googleapis.com
- assuredworkloads.googleapis.com
- automl.googleapis.com
- baremetalsolution.googleapis.com
- batch.googleapis.com
- beyondcorp.googleapis.com
- bigquery.googleapis.com
- bigquerydatapolicy.googleapis.com
- bigquerydatatransfer.googleapis.com
- bigquerymigration.googleapis.com
- bigqueryreservation.googleapis.com
- bigtable.googleapis.com
- binaryauthorization.googleapis.com
- cloudasset.googleapis.com
- cloudbuild.googleapis.com
- clouddebugger.googleapis.com
- clouderrorreporting.googleapis.com
- cloudfunctions.googleapis.com
- cloudkms.googleapis.com
- cloudprofiler.googleapis.com
- cloudresourcemanager.googleapis.com
- cloudsearch.googleapis.com
- cloudtrace.googleapis.com
- composer.googleapis.com
- compute.googleapis.com
- connectgateway.googleapis.com
- contactcenterinsights.googleapis.com
- container.googleapis.com
- containeranalysis.googleapis.com
- containerfilesystem.googleapis.com
- containerregistry.googleapis.com
- containerthreatdetection.googleapis.com
- contentwarehouse.googleapis.com
- datacatalog.googleapis.com
- dataflow.googleapis.com
- datafusion.googleapis.com
- datalineage.googleapis.com
- datamigration.googleapis.com
- datapipelines.googleapis.com
- dataplex.googleapis.com
- dataproc.googleapis.com
- datastream.googleapis.com
- dialogflow.googleapis.com
- dlp.googleapis.com
- dns.googleapis.com
- documentai.googleapis.com
- domains.googleapis.com
- essentialcontacts.googleapis.com
- eventarc.googleapis.com
- file.googleapis.com
- firebaseappcheck.googleapis.com
- firebaserules.googleapis.com
- firestore.googleapis.com
- gameservices.googleapis.com
- gkebackup.googleapis.com
- gkeconnect.googleapis.com
- gkehub.googleapis.com
- gkemulticloud.googleapis.com
- healthcare.googleapis.com
- iam.googleapis.com
- iamcredentials.googleapis.com
- iaptunnel.googleapis.com
- ids.googleapis.com
- integrations.googleapis.com
- language.googleapis.com
- lifesciences.googleapis.com
- logging.googleapis.com
- managedidentities.googleapis.com
- memcache.googleapis.com
- meshca.googleapis.com
- metastore.googleapis.com
- ml.googleapis.com
- monitoring.googleapis.com
- networkconnectivity.googleapis.com
- networkmanagement.googleapis.com
- networksecurity.googleapis.com
- networkservices.googleapis.com
- notebooks.googleapis.com
- opsconfigmonitoring.googleapis.com
- osconfig.googleapis.com
- oslogin.googleapis.com
- policytroubleshooter.googleapis.com
- privateca.googleapis.com
- pubsub.googleapis.com
- pubsublite.googleapis.com
- recaptchaenterprise.googleapis.com
- recommender.googleapis.com
- redis.googleapis.com
- retail.googleapis.com
- run.googleapis.com
- secretmanager.googleapis.com
- servicecontrol.googleapis.com
- servicedirectory.googleapis.com
- spanner.googleapis.com
- speakerid.googleapis.com
- speech.googleapis.com
- sqladmin.googleapis.com
- storage.googleapis.com
- storagetransfer.googleapis.com
- texttospeech.googleapis.com
- tpu.googleapis.com
- trafficdirector.googleapis.com
- transcoder.googleapis.com
- translate.googleapis.com
- videointelligence.googleapis.com
- vision.googleapis.com
- visionai.googleapis.com
- vpcaccess.googleapis.com
- workstations.googleapis.com
vpc_accessible_services:
- allowed_services:
- accessapproval.googleapis.com
- adsdatahub.googleapis.com
- aiplatform.googleapis.com
- alloydb.googleapis.com
- alpha-documentai.googleapis.com
- analyticshub.googleapis.com
- apigee.googleapis.com
- apigeeconnect.googleapis.com
- artifactregistry.googleapis.com
- assuredworkloads.googleapis.com
- automl.googleapis.com
- baremetalsolution.googleapis.com
- batch.googleapis.com
- beyondcorp.googleapis.com
- bigquery.googleapis.com
- bigquerydatapolicy.googleapis.com
- bigquerydatatransfer.googleapis.com
- bigquerymigration.googleapis.com
- bigqueryreservation.googleapis.com
- bigtable.googleapis.com
- binaryauthorization.googleapis.com
- cloudasset.googleapis.com
- cloudbuild.googleapis.com
- clouddebugger.googleapis.com
- clouderrorreporting.googleapis.com
- cloudfunctions.googleapis.com
- cloudkms.googleapis.com
- cloudprofiler.googleapis.com
- cloudresourcemanager.googleapis.com
- cloudsearch.googleapis.com
- cloudtrace.googleapis.com
- composer.googleapis.com
- compute.googleapis.com
- connectgateway.googleapis.com
- contactcenterinsights.googleapis.com
- container.googleapis.com
- containeranalysis.googleapis.com
- containerfilesystem.googleapis.com
- containerregistry.googleapis.com
- containerthreatdetection.googleapis.com
- contentwarehouse.googleapis.com
- datacatalog.googleapis.com
- dataflow.googleapis.com
- datafusion.googleapis.com
- datalineage.googleapis.com
- datamigration.googleapis.com
- datapipelines.googleapis.com
- dataplex.googleapis.com
- dataproc.googleapis.com
- datastream.googleapis.com
- dialogflow.googleapis.com
- dlp.googleapis.com
- dns.googleapis.com
- documentai.googleapis.com
- domains.googleapis.com
- essentialcontacts.googleapis.com
- eventarc.googleapis.com
- file.googleapis.com
- firebaseappcheck.googleapis.com
- firebaserules.googleapis.com
- firestore.googleapis.com
- gameservices.googleapis.com
- gkebackup.googleapis.com
- gkeconnect.googleapis.com
- gkehub.googleapis.com
- gkemulticloud.googleapis.com
- healthcare.googleapis.com
- iam.googleapis.com
- iamcredentials.googleapis.com
- iaptunnel.googleapis.com
- ids.googleapis.com
- integrations.googleapis.com
- language.googleapis.com
- lifesciences.googleapis.com
- logging.googleapis.com
- managedidentities.googleapis.com
- memcache.googleapis.com
- meshca.googleapis.com
- metastore.googleapis.com
- ml.googleapis.com
- monitoring.googleapis.com
- networkconnectivity.googleapis.com
- networkmanagement.googleapis.com
- networksecurity.googleapis.com
- networkservices.googleapis.com
- notebooks.googleapis.com
- opsconfigmonitoring.googleapis.com
- osconfig.googleapis.com
- oslogin.googleapis.com
- policytroubleshooter.googleapis.com
- privateca.googleapis.com
- pubsub.googleapis.com
- pubsublite.googleapis.com
- recaptchaenterprise.googleapis.com
- recommender.googleapis.com
- redis.googleapis.com
- retail.googleapis.com
- run.googleapis.com
- secretmanager.googleapis.com
- servicecontrol.googleapis.com
- servicedirectory.googleapis.com
- spanner.googleapis.com
- speakerid.googleapis.com
- speech.googleapis.com
- sqladmin.googleapis.com
- storage.googleapis.com
- storagetransfer.googleapis.com
- texttospeech.googleapis.com
- tpu.googleapis.com
- trafficdirector.googleapis.com
- transcoder.googleapis.com
- translate.googleapis.com
- videointelligence.googleapis.com
- vision.googleapis.com
- visionai.googleapis.com
- vpcaccess.googleapis.com
- workstations.googleapis.com
enable_restriction: true
status: []
timeouts: null
title: shielded title: shielded
use_explicit_dry_run_spec: true
counts: counts:
google_access_context_manager_access_policy: 1 google_access_context_manager_access_policy: 1
@ -47,5 +637,7 @@ counts:
google_project_service_identity: 1 google_project_service_identity: 1
google_projects: 1 google_projects: 1
google_storage_project_service_account: 1 google_storage_project_service_account: 1
modules: 6 modules: 7
resources: 38 resources: 38
outputs: {}

View File

@ -13,5 +13,5 @@
# limitations under the License. # limitations under the License.
counts: counts:
modules: 27 modules: 28
resources: 151 resources: 151

View File

@ -13,5 +13,5 @@
# limitations under the License. # limitations under the License.
counts: counts:
modules: 29 modules: 30
resources: 188 resources: 188

View File

@ -13,5 +13,5 @@
# limitations under the License. # limitations under the License.
counts: counts:
modules: 41 modules: 42
resources: 197 resources: 197

View File

@ -13,5 +13,5 @@
# limitations under the License. # limitations under the License.
counts: counts:
modules: 20 modules: 21
resources: 168 resources: 168

View File

@ -13,5 +13,5 @@
# limitations under the License. # limitations under the License.
counts: counts:
modules: 35 modules: 36
resources: 210 resources: 210

View File

@ -1,51 +0,0 @@
firewall_policies = {
policy1 = {
allow-ingress = {
description = ""
direction = "INGRESS"
action = "allow"
priority = 100
ranges = ["10.0.0.0/8"]
ports = {
tcp = ["22"]
}
target_service_accounts = null
target_resources = null
logging = false
}
deny-egress = {
description = ""
direction = "EGRESS"
action = "deny"
priority = 200
ranges = ["192.168.0.0/24"]
ports = {
tcp = ["443"]
}
target_service_accounts = null
target_resources = null
logging = false
}
}
policy2 = {
allow-ingress = {
description = ""
direction = "INGRESS"
action = "allow"
priority = 100
ranges = ["10.0.0.0/8"]
ports = {
tcp = ["22"]
}
target_service_accounts = null
target_resources = null
logging = false
}
}
}
firewall_policy_factory = {
cidr_file = "../../tests/modules/organization/data/firewall-cidrs.yaml"
policy_name = "factory-1"
rules_file = "../../tests/modules/organization/data/firewall-rules.yaml"
}

View File

@ -1,27 +0,0 @@
# Copyright 2022 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_firewall_policy.policy["factory-1"]: {}
google_compute_firewall_policy.policy["policy1"]: {}
google_compute_firewall_policy.policy["policy2"]: {}
google_compute_firewall_policy_rule.rule["factory-1-allow-admins"]: {}
google_compute_firewall_policy_rule.rule["factory-1-allow-ssh-from-iap"]: {}
google_compute_firewall_policy_rule.rule["policy1-allow-ingress"]: {}
google_compute_firewall_policy_rule.rule["policy1-deny-egress"]: {}
google_compute_firewall_policy_rule.rule["policy2-allow-ingress"]: {}
counts:
google_compute_firewall_policy: 3
google_compute_firewall_policy_rule: 5

View File

@ -21,5 +21,4 @@ tests:
org_policies_list: org_policies_list:
org_policies_boolean: org_policies_boolean:
org_policies_custom_constraints: org_policies_custom_constraints:
firewall_policies_factory_combined:
tags: tags: