diff --git a/0-bootstrap/README-GitHub.md b/0-bootstrap/README-GitHub.md index 6aba496d4..8c98ea3cf 100644 --- a/0-bootstrap/README-GitHub.md +++ b/0-bootstrap/README-GitHub.md @@ -565,15 +565,15 @@ or go to [Deploying step 3-networks-hub-and-spoke](#deploying-step-3-networks-hu chmod 755 ./tf-wrapper.sh ``` -1. Rename `common.auto.example.tfvars` to `common.auto.tfvars`, rename `shared.auto.example.tfvars` to `shared.auto.tfvars` and rename `access_context.auto.example.tfvars` to `access_context.auto.tfvars`. +1. Rename `common.auto.example.tfvars` to `common.auto.tfvars`, rename `production.auto.example.tfvars` to `production.auto.tfvars` and rename `access_context.auto.example.tfvars` to `access_context.auto.tfvars`. ```bash mv common.auto.example.tfvars common.auto.tfvars - mv shared.auto.example.tfvars shared.auto.tfvars + mv production.auto.example.tfvars production.auto.tfvars mv access_context.auto.example.tfvars access_context.auto.tfvars ``` -1. Update the file `shared.auto.tfvars` with the values for the `target_name_server_addresses`. +1. Update the file `production.auto.tfvars` with the values for the `target_name_server_addresses`. 1. Update the file `access_context.auto.tfvars` with the organization's `access_context_manager_policy_id`. ```bash diff --git a/0-bootstrap/README-GitLab.md b/0-bootstrap/README-GitLab.md index b0ab4a312..1a27609a7 100644 --- a/0-bootstrap/README-GitLab.md +++ b/0-bootstrap/README-GitLab.md @@ -568,15 +568,15 @@ or go to [Deploying step 3-networks-hub-and-spoke](#deploying-step-3-networks-hu chmod 755 ./*.sh ``` -1. Rename `common.auto.example.tfvars` to `common.auto.tfvars`, rename `shared.auto.example.tfvars` to `shared.auto.tfvars` and rename `access_context.auto.example.tfvars` to `access_context.auto.tfvars`. +1. Rename `common.auto.example.tfvars` to `common.auto.tfvars`, rename `production.auto.example.tfvars` to `production.auto.tfvars` and rename `access_context.auto.example.tfvars` to `access_context.auto.tfvars`. ```bash mv common.auto.example.tfvars common.auto.tfvars - mv shared.auto.example.tfvars shared.auto.tfvars + mv production.auto.example.tfvars production.auto.tfvars mv access_context.auto.example.tfvars access_context.auto.tfvars ``` -1. Update the file `shared.auto.tfvars` with the values for the `target_name_server_addresses`. +1. Update the file `production.auto.tfvars` with the values for the `target_name_server_addresses`. 1. Update the file `access_context.auto.tfvars` with the organization's `access_context_manager_policy_id`. ```bash diff --git a/0-bootstrap/README-Jenkins.md b/0-bootstrap/README-Jenkins.md index ac536a6c4..5ece83a8f 100644 --- a/0-bootstrap/README-Jenkins.md +++ b/0-bootstrap/README-Jenkins.md @@ -599,16 +599,16 @@ Here you will configure a VPN Network tunnel to enable connectivity between the sed -i'' -e "s/CICD_PROJECT_ID/${CICD_PROJECT_ID}/" ./Jenkinsfile ``` -1. Rename `common.auto.example.tfvars` to `common.auto.tfvars`, rename `shared.auto.example.tfvars` to `shared.auto.tfvars` and rename `access_context.auto.example.tfvars` to `access_context.auto.tfvars`. +1. Rename `common.auto.example.tfvars` to `common.auto.tfvars`, rename `production.auto.example.tfvars` to `production.auto.tfvars` and rename `access_context.auto.example.tfvars` to `access_context.auto.tfvars`. ```bash mv common.auto.example.tfvars common.auto.tfvars - mv shared.auto.example.tfvars shared.auto.tfvars + mv production.auto.example.tfvars production.auto.tfvars mv access_context.auto.example.tfvars access_context.auto.tfvars ``` 1. Update `common.auto.tfvars` file with values from your environment and bootstrap. See any of the envs folder [README.md](../3-networks-dual-svpc/envs/production/README.md) files for additional information on the values in the `common.auto.tfvars` file. -1. Update `shared.auto.tfvars` file with the `target_name_server_addresses`. +1. Update `production.auto.tfvars` file with the `target_name_server_addresses`. 1. Update `access_context.auto.tfvars` file with the `access_context_manager_policy_id`. 1. Use `terraform output` to get the backend bucket and networks step Terraform Service Account values from gcp-bootstrap output. diff --git a/0-bootstrap/README-Terraform-Cloud.md b/0-bootstrap/README-Terraform-Cloud.md index c13a88bb4..f68977a4f 100644 --- a/0-bootstrap/README-Terraform-Cloud.md +++ b/0-bootstrap/README-Terraform-Cloud.md @@ -476,15 +476,15 @@ or go to [Deploying step 3-networks-hub-and-spoke](#deploying-step-3-networks-hu chmod 755 ./tf-wrapper.sh ``` -1. Rename `common.auto.example.tfvars` to `common.auto.tfvars`, rename `shared.auto.example.tfvars` to `shared.auto.tfvars` and rename `access_context.auto.example.tfvars` to `access_context.auto.tfvars`. +1. Rename `common.auto.example.tfvars` to `common.auto.tfvars`, rename `production.auto.example.tfvars` to `production.auto.tfvars` and rename `access_context.auto.example.tfvars` to `access_context.auto.tfvars`. ```bash mv common.auto.example.tfvars common.auto.tfvars - mv shared.auto.example.tfvars shared.auto.tfvars + mv production.auto.example.tfvars production.auto.tfvars mv access_context.auto.example.tfvars access_context.auto.tfvars ``` -1. Update the file `shared.auto.tfvars` with the values for the `target_name_server_addresses`. +1. Update the file `production.auto.tfvars` with the values for the `target_name_server_addresses`. 1. Update the file `access_context.auto.tfvars` with the organization's `access_context_manager_policy_id`. ```bash diff --git a/1-org/envs/shared/README.md b/1-org/envs/shared/README.md index e12dc5bcf..9233b2bba 100644 --- a/1-org/envs/shared/README.md +++ b/1-org/envs/shared/README.md @@ -18,7 +18,7 @@ | log\_export\_storage\_location | The location of the storage bucket used to export logs. | `string` | `null` | no | | log\_export\_storage\_retention\_policy | Configuration of the bucket's data retention policy for how long objects in the bucket should be retained. |
object({
is_locked = bool
retention_period_days = number
})
| `null` | no | | log\_export\_storage\_versioning | (Optional) Toggles bucket versioning, ability to retain a non-current object version when the live object version gets replaced or deleted. | `bool` | `false` | no | -| project\_budget | Budget configuration for projects.
budget\_amount: The amount to use as the budget.
alert\_spent\_percents: A list of percentages of the budget to alert on when threshold is exceeded.
alert\_pubsub\_topic: The name of the Cloud Pub/Sub topic where budget related messages will be published, in the form of `projects/{project_id}/topics/{topic_id}`.
alert\_spend\_basis: The type of basis used to determine if spend has passed the threshold. Possible choices are `CURRENT_SPEND` or `FORECASTED_SPEND` (default). |
object({
dns_hub_budget_amount = optional(number, 1000)
dns_hub_alert_spent_percents = optional(list(number), [1.2])
dns_hub_alert_pubsub_topic = optional(string, null)
dns_hub_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
base_net_hub_budget_amount = optional(number, 1000)
base_net_hub_alert_spent_percents = optional(list(number), [1.2])
base_net_hub_alert_pubsub_topic = optional(string, null)
base_net_hub_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
base_network_budget_amount = optional(number, 1000)
base_network_alert_spent_percents = optional(list(number), [1.2])
base_network_alert_pubsub_topic = optional(string, null)
base_network_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
restricted_net_hub_budget_amount = optional(number, 1000)
restricted_net_hub_alert_spent_percents = optional(list(number), [1.2])
restricted_net_hub_alert_pubsub_topic = optional(string, null)
restricted_net_hub_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
restricted_network_budget_amount = optional(number, 1000)
restricted_network_alert_spent_percents = optional(list(number), [1.2])
restricted_network_alert_pubsub_topic = optional(string, null)
restricted_network_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
interconnect_budget_amount = optional(number, 1000)
interconnect_alert_spent_percents = optional(list(number), [1.2])
interconnect_alert_pubsub_topic = optional(string, null)
interconnect_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
org_secrets_budget_amount = optional(number, 1000)
org_secrets_alert_spent_percents = optional(list(number), [1.2])
org_secrets_alert_pubsub_topic = optional(string, null)
org_secrets_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
org_billing_export_budget_amount = optional(number, 1000)
org_billing_export_alert_spent_percents = optional(list(number), [1.2])
org_billing_export_alert_pubsub_topic = optional(string, null)
org_billing_export_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
org_audit_logs_budget_amount = optional(number, 1000)
org_audit_logs_alert_spent_percents = optional(list(number), [1.2])
org_audit_logs_alert_pubsub_topic = optional(string, null)
org_audit_logs_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
common_kms_budget_amount = optional(number, 1000)
common_kms_alert_spent_percents = optional(list(number), [1.2])
common_kms_alert_pubsub_topic = optional(string, null)
common_kms_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
scc_notifications_budget_amount = optional(number, 1000)
scc_notifications_alert_spent_percents = optional(list(number), [1.2])
scc_notifications_alert_pubsub_topic = optional(string, null)
scc_notifications_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
})
| `{}` | no | +| project\_budget | Budget configuration for projects.
budget\_amount: The amount to use as the budget.
alert\_spent\_percents: A list of percentages of the budget to alert on when threshold is exceeded.
alert\_pubsub\_topic: The name of the Cloud Pub/Sub topic where budget related messages will be published, in the form of `projects/{project_id}/topics/{topic_id}`.
alert\_spend\_basis: The type of basis used to determine if spend has passed the threshold. Possible choices are `CURRENT_SPEND` or `FORECASTED_SPEND` (default). |
object({
base_net_hub_budget_amount = optional(number, 1000)
base_net_hub_alert_spent_percents = optional(list(number), [1.2])
base_net_hub_alert_pubsub_topic = optional(string, null)
base_net_hub_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
base_network_budget_amount = optional(number, 1000)
base_network_alert_spent_percents = optional(list(number), [1.2])
base_network_alert_pubsub_topic = optional(string, null)
base_network_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
restricted_net_hub_budget_amount = optional(number, 1000)
restricted_net_hub_alert_spent_percents = optional(list(number), [1.2])
restricted_net_hub_alert_pubsub_topic = optional(string, null)
restricted_net_hub_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
restricted_network_budget_amount = optional(number, 1000)
restricted_network_alert_spent_percents = optional(list(number), [1.2])
restricted_network_alert_pubsub_topic = optional(string, null)
restricted_network_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
interconnect_budget_amount = optional(number, 1000)
interconnect_alert_spent_percents = optional(list(number), [1.2])
interconnect_alert_pubsub_topic = optional(string, null)
interconnect_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
org_secrets_budget_amount = optional(number, 1000)
org_secrets_alert_spent_percents = optional(list(number), [1.2])
org_secrets_alert_pubsub_topic = optional(string, null)
org_secrets_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
org_billing_export_budget_amount = optional(number, 1000)
org_billing_export_alert_spent_percents = optional(list(number), [1.2])
org_billing_export_alert_pubsub_topic = optional(string, null)
org_billing_export_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
org_audit_logs_budget_amount = optional(number, 1000)
org_audit_logs_alert_spent_percents = optional(list(number), [1.2])
org_audit_logs_alert_pubsub_topic = optional(string, null)
org_audit_logs_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
common_kms_budget_amount = optional(number, 1000)
common_kms_alert_spent_percents = optional(list(number), [1.2])
common_kms_alert_pubsub_topic = optional(string, null)
common_kms_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
scc_notifications_budget_amount = optional(number, 1000)
scc_notifications_alert_spent_percents = optional(list(number), [1.2])
scc_notifications_alert_pubsub_topic = optional(string, null)
scc_notifications_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND")
})
| `{}` | no | | project\_deletion\_policy | The deletion policy for the project created. | `string` | `"PREVENT"` | no | | remote\_state\_bucket | Backend bucket to load Terraform Remote State Data from previous steps. | `string` | n/a | yes | | scc\_notification\_filter | Filter used to create the Security Command Center Notification, you can see more details on how to create filters in https://cloud.google.com/security-command-center/docs/how-to-api-filter-notifications#create-filter | `string` | `"state = \"ACTIVE\""` | no | @@ -37,7 +37,6 @@ | cai\_monitoring\_topic | CAI Monitoring Cloud Function Pub/Sub Topic name. | | common\_folder\_name | The common folder name | | common\_kms\_project\_id | The org Cloud Key Management Service (KMS) project ID | -| dns\_hub\_project\_id | The DNS hub project ID | | domains\_to\_allow | The list of domains to allow users from in IAM. | | interconnect\_project\_id | The Dedicated Interconnect project ID | | interconnect\_project\_number | The Dedicated Interconnect project number | diff --git a/1-org/envs/shared/outputs.tf b/1-org/envs/shared/outputs.tf index b1cc75605..5d7d1c986 100644 --- a/1-org/envs/shared/outputs.tf +++ b/1-org/envs/shared/outputs.tf @@ -79,11 +79,6 @@ output "scc_notifications_project_id" { description = "The SCC notifications project ID" } -output "dns_hub_project_id" { - value = module.dns_hub.project_id - description = "The DNS hub project ID" -} - output "base_net_hub_project_id" { value = try(module.base_network_hub[0].project_id, null) description = "The Base Network hub project ID" diff --git a/1-org/envs/shared/projects.tf b/1-org/envs/shared/projects.tf index be2ee3f1f..5ae87ac57 100644 --- a/1-org/envs/shared/projects.tf +++ b/1-org/envs/shared/projects.tf @@ -233,48 +233,6 @@ module "scc_notifications" { budget_alert_spend_basis = var.project_budget.scc_notifications_budget_alert_spend_basis } -/****************************************** - Project for DNS Hub -*****************************************/ - -module "dns_hub" { - source = "terraform-google-modules/project-factory/google" - version = "~> 18.0" - - random_project_id = true - random_project_id_length = 4 - default_service_account = "deprivilege" - name = "${local.project_prefix}-net-dns" - org_id = local.org_id - billing_account = local.billing_account - folder_id = google_folder.network.id - deletion_policy = var.project_deletion_policy - - activate_apis = [ - "compute.googleapis.com", - "dns.googleapis.com", - "servicenetworking.googleapis.com", - "logging.googleapis.com", - "cloudresourcemanager.googleapis.com", - "billingbudgets.googleapis.com" - ] - - labels = { - environment = "network" - application_name = "org-dns-hub" - billing_code = "1234" - primary_contact = "example1" - secondary_contact = "example2" - business_code = "shared" - env_code = "net" - vpc = "none" - } - budget_alert_pubsub_topic = var.project_budget.dns_hub_alert_pubsub_topic - budget_alert_spent_percents = var.project_budget.dns_hub_alert_spent_percents - budget_amount = var.project_budget.dns_hub_budget_amount - budget_alert_spend_basis = var.project_budget.dns_hub_budget_alert_spend_basis -} - /****************************************** Project for Base Network Hub *****************************************/ diff --git a/1-org/envs/shared/variables.tf b/1-org/envs/shared/variables.tf index b39073d7d..929d213df 100644 --- a/1-org/envs/shared/variables.tf +++ b/1-org/envs/shared/variables.tf @@ -97,10 +97,6 @@ variable "project_budget" { alert_spend_basis: The type of basis used to determine if spend has passed the threshold. Possible choices are `CURRENT_SPEND` or `FORECASTED_SPEND` (default). EOT type = object({ - dns_hub_budget_amount = optional(number, 1000) - dns_hub_alert_spent_percents = optional(list(number), [1.2]) - dns_hub_alert_pubsub_topic = optional(string, null) - dns_hub_budget_alert_spend_basis = optional(string, "FORECASTED_SPEND") base_net_hub_budget_amount = optional(number, 1000) base_net_hub_alert_spent_percents = optional(list(number), [1.2]) base_net_hub_alert_pubsub_topic = optional(string, null) diff --git a/3-networks-dual-svpc/README.md b/3-networks-dual-svpc/README.md index 61ade0323..f545f1c4e 100644 --- a/3-networks-dual-svpc/README.md +++ b/3-networks-dual-svpc/README.md @@ -163,16 +163,16 @@ Run `terraform output cloudbuild_project_id` in the `0-bootstrap` folder to get chmod 755 ./tf-wrapper.sh ``` -1. Rename `common.auto.example.tfvars` to `common.auto.tfvars`, rename `shared.auto.example.tfvars` to `shared.auto.tfvars` and rename `access_context.auto.example.tfvars` to `access_context.auto.tfvars`. +1. Rename `common.auto.example.tfvars` to `common.auto.tfvars`, rename `production.auto.example.tfvars` to `production.auto.tfvars` and rename `access_context.auto.example.tfvars` to `access_context.auto.tfvars`. ```bash mv common.auto.example.tfvars common.auto.tfvars - mv shared.auto.example.tfvars shared.auto.tfvars + mv production.auto.example.tfvars production.auto.tfvars mv access_context.auto.example.tfvars access_context.auto.tfvars ``` 1. Update `common.auto.tfvars` file with values from your environment and bootstrap. See any of the envs folder [README.md](./envs/production/README.md) files for additional information on the values in the `common.auto.tfvars` file. - Update `shared.auto.tfvars` file with the `target_name_server_addresses`. + Update `production.auto.tfvars` file with the `target_name_server_addresses`. Update `access_context.auto.tfvars` file with the `access_context_manager_policy_id`. Use `terraform output` to get the backend bucket value from 0-bootstrap output. @@ -229,23 +229,43 @@ Run `terraform output cloudbuild_project_id` in the `0-bootstrap` folder to get ./tf-wrapper.sh apply shared ``` -1. Push your plan branch to trigger a plan for all environments. Because the - _plan_ branch is not a [named environment branch](../docs/FAQ.md#what-is-a-named-branch), pushing your _plan_ - branch triggers _terraform plan_ but not _terraform apply_. Review the plan output in your Cloud Build project https://console.cloud.google.com/cloud-build/builds;region=DEFAULT_REGION?project=YOUR_CLOUD_BUILD_PROJECT_ID +1. You must manually plan and apply the `production` environment since the `development`, `nonproduction` and `plan` environments depend on it. ```bash - git push --set-upstream origin plan + git checkout -b production + ``` + +1. Run `init` and `plan` and review output for environment production. + + ```bash + ./tf-wrapper.sh init production + ./tf-wrapper.sh plan production + ``` + +1. Run `apply` production. + + ```bash + ./tf-wrapper.sh apply production ``` -1. Merge changes to production. Because this is a [named environment branch](../docs/FAQ.md#what-is-a-named-branch), + 1. Push your production branch since development and nonproduction depends it. Because this is a [named environment branch](../docs/FAQ.md#what-is-a-named-branch), pushing to this branch triggers both _terraform plan_ and _terraform apply_. Review the apply output in your Cloud Build project https://console.cloud.google.com/cloud-build/builds;region=DEFAULT_REGION?project=YOUR_CLOUD_BUILD_PROJECT_ID +*Note:** The Production envrionment must be the first branch to be pushed as it includes the DNS Hub communication that will be used by other environments. + ```bash - git checkout -b production - git push origin production + git push --set-upstream origin production + ``` + +1. Push your plan branch to trigger a plan for all environments. Because the + _plan_ branch is not a [named environment branch](../docs/FAQ.md#what-is-a-named-branch), pushing your _plan_ + branch triggers _terraform plan_ but not _terraform apply_. Review the plan output in your Cloud Build project https://console.cloud.google.com/cloud-build/builds;region=DEFAULT_REGION?project=YOUR_CLOUD_BUILD_PROJECT_ID + + ```bash + git push --set-upstream origin plan ``` -1. After production has been applied, apply development. +1. After plan has been applied, apply development. 1. Merge changes to development. Because this is a [named environment branch](../docs/FAQ.md#what-is-a-named-branch), pushing to this branch triggers both _terraform plan_ and _terraform apply_. Review the apply output in your Cloud Build project https://console.cloud.google.com/cloud-build/builds;region=DEFAULT_REGION?project=YOUR_CLOUD_BUILD_PROJECT_ID @@ -298,21 +318,21 @@ See `0-bootstrap` [README-GitHub.md](../0-bootstrap/README-GitHub.md#deploying-s git init git commit -m "initialize empty directory" --allow-empty git checkout -b shared + git checkout -b production git checkout -b development git checkout -b nonproduction - git checkout -b production ``` -1. Rename `common.auto.example.tfvars` to `common.auto.tfvars`, rename `shared.auto.example.tfvars` to `shared.auto.tfvars` and rename `access_context.auto.example.tfvars` to `access_context.auto.tfvars`. +1. Rename `common.auto.example.tfvars` to `common.auto.tfvars`, rename `production.auto.example.tfvars` to `production.auto.tfvars` and rename `access_context.auto.example.tfvars` to `access_context.auto.tfvars`. ```bash mv common.auto.example.tfvars common.auto.tfvars - mv shared.auto.example.tfvars shared.auto.tfvars + mv production.auto.example.tfvars production.auto.tfvars mv access_context.auto.example.tfvars access_context.auto.tfvars ``` 1. Update `common.auto.tfvars` file with values from your environment and bootstrap. See any of the envs folder [README.md](./envs/production/README.md) files for additional information on the values in the `common.auto.tfvars` file. -1. Update `shared.auto.tfvars` file with the `target_name_server_addresses`. +1. Update `production.auto.tfvars` file with the `target_name_server_addresses`. 1. Update `access_context.auto.tfvars` file with the `access_context_manager_policy_id`. 1. Use `terraform output` to get the backend bucket value from gcp-bootstrap output. @@ -361,6 +381,36 @@ To use the `validate` option of the `tf-wrapper.sh` script, please follow the [i ```bash ./tf-wrapper.sh apply shared + ``` + +1. Checkout shared `production`. Run `init` and `plan` and review output for environment production. + + ```bash + git checkout production + git merge shared + ./tf-wrapper.sh init production + ./tf-wrapper.sh plan production + ``` + +1. Run `validate` and check for violations. + + ```bash + ./tf-wrapper.sh validate production $(pwd)/../gcp-policies ${SEED_PROJECT_ID} + ``` + +1. Run `apply` production. + + ```bash + ./tf-wrapper.sh apply production + git add . + git commit -m "Initial production commit." + cd ../ + ``` + +1. Run `git commit` shared. + + ```bash + git checkout shared git add . git commit -m "Initial shared commit." ``` @@ -411,30 +461,6 @@ To use the `validate` option of the `tf-wrapper.sh` script, please follow the [i git commit -m "Initial nonproduction commit." ``` -1. Checkout shared `production`. Run `init` and `plan` and review output for environment development. - - ```bash - git checkout production - git merge nonproduction - ./tf-wrapper.sh init production - ./tf-wrapper.sh plan production - ``` - -1. Run `validate` and check for violations. - - ```bash - ./tf-wrapper.sh validate production $(pwd)/../gcp-policies ${SEED_PROJECT_ID} - ``` - -1. Run `apply` production. - - ```bash - ./tf-wrapper.sh apply production - git add . - git commit -m "Initial production commit." - cd ../ - ``` - If you received any errors or made any changes to the Terraform config or any `.tfvars`, you must re-run `./tf-wrapper.sh plan ` before run `./tf-wrapper.sh apply `. Before executing the next stages, unset the `GOOGLE_IMPERSONATE_SERVICE_ACCOUNT` environment variable. diff --git a/3-networks-dual-svpc/envs/production/README.md b/3-networks-dual-svpc/envs/production/README.md index a92f78e34..4cedf43a6 100644 --- a/3-networks-dual-svpc/envs/production/README.md +++ b/3-networks-dual-svpc/envs/production/README.md @@ -1,6 +1,6 @@ # 3-networks-dual-svpc/production -The purpose of this step is to set up base and restricted shared VPCs with default DNS, NAT (optional), Private Service networking, VPC service controls, onprem Dedicated Interconnect, onprem VPN and baseline firewall rules for environment production. +The purpose of this step is to set up base and restricted shared VPCs with default DNS, NAT (optional), Private Service networking, VPC service controls, onprem Dedicated Interconnect, onprem VPN and baseline firewall rules for environment production and the global [DNS Hub](https://cloud.google.com/blog/products/networking/cloud-forwarding-peering-and-zones) that will be used by all environments. ## Prerequisites @@ -24,6 +24,7 @@ The purpose of this step is to set up base and restricted shared VPCs with defau | perimeter\_additional\_members | The list of additional members to be added to the enforced perimeter access level members list. To be able to see the resources protected by the VPC Service Controls in the restricted perimeter, add your user in this list. Entries must be in the standard GCP form: `user:email@example.com` or `serviceAccount:my-service-account@example.com`. | `list(string)` | `[]` | no | | perimeter\_additional\_members\_dry\_run | The list of additional members to be added to the dry-run perimeter access level members list. To be able to see the resources protected by the VPC Service Controls in the restricted perimeter, add your user in this list. Entries must be in the standard GCP form: `user:email@example.com` or `serviceAccount:my-service-account@example.com`. | `list(string)` | `[]` | no | | remote\_state\_bucket | Backend bucket to load Terraform Remote State Data from previous steps. | `string` | n/a | yes | +| target\_name\_server\_addresses | List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones. | `list(map(any))` | `[]` | no | | tfc\_org\_name | Name of the TFC organization | `string` | `""` | no | ## Outputs diff --git a/3-networks-dual-svpc/envs/production/main.tf b/3-networks-dual-svpc/envs/production/main.tf index d2ea8490e..e68a0454e 100644 --- a/3-networks-dual-svpc/envs/production/main.tf +++ b/3-networks-dual-svpc/envs/production/main.tf @@ -89,10 +89,11 @@ module "base_env" { base_subnet_secondary_ranges = local.base_subnet_secondary_ranges base_private_service_connect_ip = "10.17.0.4" restricted_private_service_cidr = local.restricted_private_service_cidr - restricted_subnet_primary_ranges = local.restricted_subnet_primary_ranges restricted_subnet_proxy_ranges = local.restricted_subnet_proxy_ranges + restricted_subnet_primary_ranges = local.restricted_subnet_primary_ranges restricted_subnet_secondary_ranges = local.restricted_subnet_secondary_ranges restricted_private_service_connect_ip = "10.17.0.8" remote_state_bucket = var.remote_state_bucket tfc_org_name = var.tfc_org_name + target_name_server_addresses = var.target_name_server_addresses } diff --git a/3-networks-dual-svpc/envs/production/production.auto.tfvars b/3-networks-dual-svpc/envs/production/production.auto.tfvars new file mode 120000 index 000000000..be31a2edd --- /dev/null +++ b/3-networks-dual-svpc/envs/production/production.auto.tfvars @@ -0,0 +1 @@ +../../production.auto.tfvars \ No newline at end of file diff --git a/3-networks-dual-svpc/envs/production/variables.tf b/3-networks-dual-svpc/envs/production/variables.tf index 02448e5a9..588a9e69d 100644 --- a/3-networks-dual-svpc/envs/production/variables.tf +++ b/3-networks-dual-svpc/envs/production/variables.tf @@ -14,6 +14,12 @@ * limitations under the License. */ +variable "target_name_server_addresses" { + description = "List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones." + type = list(map(any)) + default = [] +} + variable "remote_state_bucket" { description = "Backend bucket to load Terraform Remote State Data from previous steps." type = string diff --git a/3-networks-dual-svpc/envs/shared/README.md b/3-networks-dual-svpc/envs/shared/README.md index 27ab3647c..37d6649d7 100644 --- a/3-networks-dual-svpc/envs/shared/README.md +++ b/3-networks-dual-svpc/envs/shared/README.md @@ -1,7 +1,5 @@ # 3-networks-dual-svpc/shared -The purpose of this step is to set up the global [DNS Hub](https://cloud.google.com/blog/products/networking/cloud-forwarding-peering-and-zones) that will be used by all environments. - ## Prerequisites 1. 0-bootstrap executed successfully. @@ -15,18 +13,13 @@ The purpose of this step is to set up the global [DNS Hub](https://cloud.google. | bgp\_asn\_dns | BGP Autonomous System Number (ASN). | `number` | `64667` | no | | dns\_enable\_logging | Toggle DNS logging for VPC DNS. | `bool` | `true` | no | | domain | The DNS name of forwarding managed zone, for instance 'example.com'. Must end with a period. | `string` | n/a | yes | -| enable\_partner\_interconnect | Enable Partner Interconnect in the environment. | `bool` | `false` | no | | firewall\_policies\_enable\_logging | Toggle hierarchical firewall logging. | `bool` | `true` | no | -| preactivate\_partner\_interconnect | Preactivate Partner Interconnect VLAN attachment in the environment. | `bool` | `false` | no | | remote\_state\_bucket | Backend bucket to load Terraform Remote State Data from previous steps. | `string` | n/a | yes | -| target\_name\_server\_addresses | List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones. | `list(map(any))` | n/a | yes | | tfc\_org\_name | Name of the TFC organization | `string` | `""` | no | | vpc\_flow\_logs | enable\_logging: set to true to enable VPC flow logging for the subnetworks.
aggregation\_interval: Toggles the aggregation interval for collecting flow logs. Increasing the interval time will reduce the amount of generated flow logs for long lasting connections. Possible values are: INTERVAL\_5\_SEC, INTERVAL\_30\_SEC, INTERVAL\_1\_MIN, INTERVAL\_5\_MIN, INTERVAL\_10\_MIN, INTERVAL\_15\_MIN.
flow\_sampling: Set the sampling rate of VPC flow logs within the subnetwork where 1.0 means all collected logs are reported and 0.0 means no logs are reported. The value of the field must be in [0, 1].
metadata: Configures whether metadata fields should be added to the reported VPC flow logs. Possible values are: EXCLUDE\_ALL\_METADATA, INCLUDE\_ALL\_METADATA, CUSTOM\_METADATA.
metadata\_fields: ist of metadata fields that should be added to reported logs. Can only be specified if VPC flow logs for this subnetwork is enabled and "metadata" is set to CUSTOM\_METADATA.
filter\_expr: Export filter used to define which VPC flow logs should be logged, as as CEL expression. See https://cloud.google.com/vpc/docs/flow-logs#filtering for details on how to format this field. |
object({
enable_logging = optional(string, "true")
aggregation_interval = optional(string, "INTERVAL_5_SEC")
flow_sampling = optional(string, "0.5")
metadata = optional(string, "INCLUDE_ALL_METADATA")
metadata_fields = optional(list(string), [])
filter_expr = optional(string, "true")
})
| `{}` | no | ## Outputs -| Name | Description | -|------|-------------| -| dns\_hub\_project\_id | The DNS hub project ID | +No outputs. diff --git a/3-networks-dual-svpc/envs/shared/dns-hub.tf b/3-networks-dual-svpc/envs/shared/dns-hub.tf deleted file mode 100644 index 4c1a5f0d2..000000000 --- a/3-networks-dual-svpc/envs/shared/dns-hub.tf +++ /dev/null @@ -1,156 +0,0 @@ -/** - * Copyright 2021 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. - */ - -/****************************************** - DNS Hub VPC -*****************************************/ - -module "dns_hub_vpc" { - source = "terraform-google-modules/network/google" - version = "~> 10.0" - - project_id = local.dns_hub_project_id - network_name = "vpc-net-dns" - shared_vpc_host = "false" - delete_default_internet_gateway_routes = "true" - - subnets = [{ - subnet_name = "sb-net-dns-${local.default_region1}" - subnet_ip = "172.16.0.0/25" - subnet_region = local.default_region1 - subnet_private_access = "true" - subnet_flow_logs = var.vpc_flow_logs.enable_logging - subnet_flow_logs_interval = var.vpc_flow_logs.aggregation_interval - subnet_flow_logs_sampling = var.vpc_flow_logs.flow_sampling - subnet_flow_logs_metadata = var.vpc_flow_logs.metadata - subnet_flow_logs_metadata_fields = var.vpc_flow_logs.metadata_fields - subnet_flow_logs_filter = var.vpc_flow_logs.filter_expr - description = "DNS hub subnet for region 1." - }, { - subnet_name = "sb-net-dns-${local.default_region2}" - subnet_ip = "172.16.0.128/25" - subnet_region = local.default_region2 - subnet_private_access = "true" - subnet_flow_logs = var.vpc_flow_logs.enable_logging - subnet_flow_logs_interval = var.vpc_flow_logs.aggregation_interval - subnet_flow_logs_sampling = var.vpc_flow_logs.flow_sampling - subnet_flow_logs_metadata = var.vpc_flow_logs.metadata - subnet_flow_logs_metadata_fields = var.vpc_flow_logs.metadata_fields - subnet_flow_logs_filter = var.vpc_flow_logs.filter_expr - description = "DNS hub subnet for region 2." - }] - - routes = [{ - name = "rt-net-dns-1000-all-default-private-api" - description = "Route through IGW to allow private google api access." - destination_range = "199.36.153.8/30" - next_hop_internet = "true" - priority = "1000" - }] -} - -/****************************************** - Default DNS Policy - *****************************************/ - -resource "google_dns_policy" "default_policy" { - project = local.dns_hub_project_id - name = "dp-dns-hub-default-policy" - enable_inbound_forwarding = true - enable_logging = var.dns_enable_logging - networks { - network_url = module.dns_hub_vpc.network_self_link - } -} - -/****************************************** - DNS Forwarding -*****************************************/ - -module "dns-forwarding-zone" { - source = "terraform-google-modules/cloud-dns/google" - version = "~> 5.0" - - project_id = local.dns_hub_project_id - type = "forwarding" - name = "fz-dns-hub" - domain = var.domain - - private_visibility_config_networks = [ - module.dns_hub_vpc.network_self_link - ] - target_name_server_addresses = var.target_name_server_addresses -} - -/********************************************************* - Routers to advertise DNS proxy range "35.199.192.0/19" -*********************************************************/ - -module "dns_hub_region1_router1" { - source = "terraform-google-modules/cloud-router/google" - version = "~> 6.0" - - name = "cr-net-dns-${local.default_region1}-cr1" - project = local.dns_hub_project_id - network = module.dns_hub_vpc.network_name - region = local.default_region1 - bgp = { - asn = local.dns_bgp_asn_number - advertised_ip_ranges = [{ range = "35.199.192.0/19" }] - } -} - -module "dns_hub_region1_router2" { - source = "terraform-google-modules/cloud-router/google" - version = "~> 6.0" - - name = "cr-net-dns-${local.default_region1}-cr2" - project = local.dns_hub_project_id - network = module.dns_hub_vpc.network_name - region = local.default_region1 - bgp = { - asn = local.dns_bgp_asn_number - advertised_ip_ranges = [{ range = "35.199.192.0/19" }] - } -} - -module "dns_hub_region2_router1" { - source = "terraform-google-modules/cloud-router/google" - version = "~> 6.0" - - name = "cr-net-dns-${local.default_region2}-cr3" - project = local.dns_hub_project_id - network = module.dns_hub_vpc.network_name - region = local.default_region2 - bgp = { - asn = local.dns_bgp_asn_number - advertised_ip_ranges = [{ range = "35.199.192.0/19" }] - } -} - -module "dns_hub_region2_router2" { - source = "terraform-google-modules/cloud-router/google" - version = "~> 6.0" - - name = "cr-net-dns-${local.default_region2}-cr4" - project = local.dns_hub_project_id - network = module.dns_hub_vpc.network_name - region = local.default_region2 - bgp = { - asn = local.dns_bgp_asn_number - advertised_ip_ranges = [{ range = "35.199.192.0/19" }] - } -} diff --git a/3-networks-dual-svpc/envs/shared/interconnect.tf.example b/3-networks-dual-svpc/envs/shared/interconnect.tf.example deleted file mode 100644 index 239e406df..000000000 --- a/3-networks-dual-svpc/envs/shared/interconnect.tf.example +++ /dev/null @@ -1,60 +0,0 @@ -/** - * Copyright 2021 Google LLC - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -module "dns_hub_interconnect" { - source = "../../modules/dedicated_interconnect" - - vpc_name = "net-dns" - interconnect_project_id = local.dns_hub_project_id - - region1 = local.default_region1 - region1_router1_name = module.dns_hub_region1_router1.router.name - region1_interconnect1_candidate_subnets = ["169.254.0.0/29"] - region1_interconnect1_vlan_tag8021q = "3931" - region1_interconnect1 = "https://www.googleapis.com/compute/v1/projects/${local.interconnect_project_id}/global/interconnects/example-interconnect-1" - region1_interconnect1_location = "las-zone1-770" - region1_interconnect1_onprem_dc = "onprem-dc1" - region1_router2_name = module.dns_hub_region1_router2.router.name - region1_interconnect2_candidate_subnets = ["169.254.0.8/29"] - region1_interconnect2_vlan_tag8021q = "3932" - region1_interconnect2 = "https://www.googleapis.com/compute/v1/projects/${local.interconnect_project_id}/global/interconnects/example-interconnect-2" - region1_interconnect2_location = "las-zone1-770" - region1_interconnect2_onprem_dc = "onprem-dc2" - - region2 = local.default_region2 - region2_router1_name = module.dns_hub_region2_router1.router.name - region2_interconnect1_candidate_subnets = ["169.254.0.16/29"] - region2_interconnect1_vlan_tag8021q = "3933" - region2_interconnect1 = "https://www.googleapis.com/compute/v1/projects/${local.interconnect_project_id}/global/interconnects/example-interconnect-3" - region2_interconnect1_location = "lax-zone2-19" - region2_interconnect1_onprem_dc = "onprem-dc3" - region2_router2_name = module.dns_hub_region2_router2.router.name - region2_interconnect2_candidate_subnets = ["169.254.0.24/29"] - region2_interconnect2_vlan_tag8021q = "3934" - region2_interconnect2 = "https://www.googleapis.com/compute/v1/projects/${local.interconnect_project_id}/global/interconnects/example-interconnect-4" - region2_interconnect2_location = "lax-zone1-403" - region2_interconnect2_onprem_dc = "onprem-dc4" - - peer_asn = "64515" - peer_name = "interconnect-peer" - - cloud_router_labels = { - vlan_1 = "cr1", - vlan_2 = "cr2", - vlan_3 = "cr3", - vlan_4 = "cr4" - } -} diff --git a/3-networks-dual-svpc/envs/shared/outputs.tf b/3-networks-dual-svpc/envs/shared/outputs.tf index f7aca2374..9d277cce1 100644 --- a/3-networks-dual-svpc/envs/shared/outputs.tf +++ b/3-networks-dual-svpc/envs/shared/outputs.tf @@ -14,7 +14,3 @@ * limitations under the License. */ -output "dns_hub_project_id" { - value = local.dns_hub_project_id - description = "The DNS hub project ID" -} diff --git a/3-networks-dual-svpc/envs/shared/partner_interconnect.auto.tfvars.example b/3-networks-dual-svpc/envs/shared/partner_interconnect.auto.tfvars.example deleted file mode 100644 index aae4c298e..000000000 --- a/3-networks-dual-svpc/envs/shared/partner_interconnect.auto.tfvars.example +++ /dev/null @@ -1,18 +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. - */ - -enable_partner_interconnect = true -preactivate_partner_interconnect = true diff --git a/3-networks-dual-svpc/envs/shared/partner_interconnect.tf.example b/3-networks-dual-svpc/envs/shared/partner_interconnect.tf.example deleted file mode 100644 index d78a7454f..000000000 --- a/3-networks-dual-svpc/envs/shared/partner_interconnect.tf.example +++ /dev/null @@ -1,46 +0,0 @@ -/** - * Copyright 2021 Google LLC - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -module "dns_hub_interconnect" { - source = "../../modules/partner_interconnect" - - vpc_name = "net-dns" - attachment_project_id = local.dns_hub_project_id - preactivate = var.preactivate_partner_interconnect - - region1 = local.default_region1 - region1_router1_name = module.dns_hub_region1_router1.router.name - region1_interconnect1_location = "las-zone1-770" - region1_interconnect1_onprem_dc = "onprem-dc1" - region1_router2_name = module.dns_hub_region1_router2.router.name - region1_interconnect2_location = "las-zone1-770" - region1_interconnect2_onprem_dc = "onprem-dc2" - - region2 = local.default_region2 - region2_router1_name = module.dns_hub_region2_router1.router.name - region2_interconnect1_location = "lax-zone2-19" - region2_interconnect1_onprem_dc = "onprem-dc3" - region2_router2_name = module.dns_hub_region2_router2.router.name - region2_interconnect2_location = "lax-zone1-403" - region2_interconnect2_onprem_dc = "onprem-dc4" - - cloud_router_labels = { - vlan_1 = "cr1", - vlan_2 = "cr2", - vlan_3 = "cr3", - vlan_4 = "cr4" - } -} diff --git a/3-networks-dual-svpc/envs/shared/remote.tf b/3-networks-dual-svpc/envs/shared/remote.tf index 8bb1ddc51..d4ce9027d 100644 --- a/3-networks-dual-svpc/envs/shared/remote.tf +++ b/3-networks-dual-svpc/envs/shared/remote.tf @@ -17,12 +17,9 @@ locals { env = "common" environment_code = "c" - dns_bgp_asn_number = var.enable_partner_interconnect ? "16550" : var.bgp_asn_dns default_region1 = data.terraform_remote_state.bootstrap.outputs.common_config.default_region default_region2 = data.terraform_remote_state.bootstrap.outputs.common_config.default_region_2 folder_prefix = data.terraform_remote_state.bootstrap.outputs.common_config.folder_prefix - dns_hub_project_id = data.terraform_remote_state.org.outputs.dns_hub_project_id - interconnect_project_id = data.terraform_remote_state.org.outputs.interconnect_project_id parent_id = data.terraform_remote_state.bootstrap.outputs.common_config.parent_id bootstrap_folder_name = data.terraform_remote_state.bootstrap.outputs.common_config.bootstrap_folder_name common_folder_name = data.terraform_remote_state.org.outputs.common_folder_name diff --git a/3-networks-dual-svpc/envs/shared/remote.tf.cloud.example b/3-networks-dual-svpc/envs/shared/remote.tf.cloud.example index f12825173..78a4d2d7b 100644 --- a/3-networks-dual-svpc/envs/shared/remote.tf.cloud.example +++ b/3-networks-dual-svpc/envs/shared/remote.tf.cloud.example @@ -17,18 +17,15 @@ locals { env = "common" environment_code = "c" - dns_bgp_asn_number = var.enable_partner_interconnect ? "16550" : var.bgp_asn_dns default_region1 = data.tfe_outputs.bootstrap.outputs.common_config.default_region default_region2 = data.tfe_outputs.bootstrap.outputs.common_config.default_region_2 folder_prefix = data.tfe_outputs.bootstrap.nonsensitive_values.common_config.folder_prefix - dns_hub_project_id = data.tfe_outputs.org.nonsensitive_values.dns_hub_project_id - interconnect_project_id = data.tfe_outputs.org.nonsensitive_values.interconnect_project_id parent_id = data.tfe_outputs.bootstrap.nonsensitive_values.common_config.parent_id bootstrap_folder_name = data.tfe_outputs.bootstrap.nonsensitive_values.common_config.bootstrap_folder_name common_folder_name = data.tfe_outputs.org.nonsensitive_values.common_folder_name network_folder_name = data.tfe_outputs.org.nonsensitive_values.network_folder_name development_folder_name = data.tfe_outputs.env_development.nonsensitive_values.env_folder - nonproduction_folder_name = data.tfe_outputs.env_nonproduction.nonsensitive_values.env_folder + nonproduction_folder_name = data.tfe_outputs.env_nonproduction.nonsensitive_values.env_folder production_folder_name = data.tfe_outputs.env_production.nonsensitive_values.env_folder } diff --git a/3-networks-dual-svpc/envs/shared/shared.auto.tfvars b/3-networks-dual-svpc/envs/shared/shared.auto.tfvars deleted file mode 120000 index b7f8387a8..000000000 --- a/3-networks-dual-svpc/envs/shared/shared.auto.tfvars +++ /dev/null @@ -1 +0,0 @@ -../../shared.auto.tfvars \ No newline at end of file diff --git a/3-networks-dual-svpc/envs/shared/variables.tf b/3-networks-dual-svpc/envs/shared/variables.tf index 193ea63b3..ef776e33e 100644 --- a/3-networks-dual-svpc/envs/shared/variables.tf +++ b/3-networks-dual-svpc/envs/shared/variables.tf @@ -56,29 +56,12 @@ variable "bgp_asn_dns" { default = 64667 } -variable "target_name_server_addresses" { - description = "List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones." - type = list(map(any)) -} - variable "firewall_policies_enable_logging" { type = bool description = "Toggle hierarchical firewall logging." default = true } -variable "enable_partner_interconnect" { - description = "Enable Partner Interconnect in the environment." - type = bool - default = false -} - -variable "preactivate_partner_interconnect" { - description = "Preactivate Partner Interconnect VLAN attachment in the environment." - type = bool - default = false -} - variable "tfc_org_name" { description = "Name of the TFC organization" type = string diff --git a/3-networks-dual-svpc/modules/base_env/README.md b/3-networks-dual-svpc/modules/base_env/README.md index d543340d4..39744b3ba 100644 --- a/3-networks-dual-svpc/modules/base_env/README.md +++ b/3-networks-dual-svpc/modules/base_env/README.md @@ -32,6 +32,7 @@ | restricted\_subnet\_proxy\_ranges | The base proxy-only subnet primary IPTs ranges to the Restricted Shared Vpc. | `map(string)` | n/a | yes | | restricted\_subnet\_secondary\_ranges | The base subnet secondary IPTs ranges to the Restricted Shared Vpc | `map(list(map(string)))` | n/a | yes | | restricted\_vpc\_flow\_logs | aggregation\_interval: Toggles the aggregation interval for collecting flow logs. Increasing the interval time will reduce the amount of generated flow logs for long lasting connections. Possible values are: INTERVAL\_5\_SEC, INTERVAL\_30\_SEC, INTERVAL\_1\_MIN, INTERVAL\_5\_MIN, INTERVAL\_10\_MIN, INTERVAL\_15\_MIN.
flow\_sampling: Set the sampling rate of VPC flow logs within the subnetwork where 1.0 means all collected logs are reported and 0.0 means no logs are reported. The value of the field must be in [0, 1].
metadata: Configures whether metadata fields should be added to the reported VPC flow logs. Possible values are: EXCLUDE\_ALL\_METADATA, INCLUDE\_ALL\_METADATA, CUSTOM\_METADATA.
metadata\_fields: ist of metadata fields that should be added to reported logs. Can only be specified if VPC flow logs for this subnetwork is enabled and "metadata" is set to CUSTOM\_METADATA.
filter\_expr: Export filter used to define which VPC flow logs should be logged, as as CEL expression. See https://cloud.google.com/vpc/docs/flow-logs#filtering for details on how to format this field. |
object({
aggregation_interval = optional(string, "INTERVAL_5_SEC")
flow_sampling = optional(string, "0.5")
metadata = optional(string, "INCLUDE_ALL_METADATA")
metadata_fields = optional(list(string), [])
filter_expr = optional(string, "true")
})
| `{}` | no | +| target\_name\_server\_addresses | List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones. | `list(map(any))` | `[]` | no | | tfc\_org\_name | Name of the TFC organization | `string` | n/a | yes | ## Outputs @@ -40,6 +41,7 @@ |------|-------------| | access\_level\_name | Access context manager access level name for the enforced perimeter | | access\_level\_name\_dry\_run | Access context manager access level name for the dry-run perimeter | +| base\_dns\_project\_id | The base DNS project ID | | base\_host\_project\_id | The base host project ID | | base\_network\_name | The name of the VPC being created | | base\_network\_self\_link | The URI of the VPC being created | @@ -48,6 +50,7 @@ | base\_subnets\_secondary\_ranges | The secondary ranges associated with these subnets | | base\_subnets\_self\_links | The self-links of subnets being created | | enforce\_vpcsc | Enable the enforced mode for VPC Service Controls. It is not recommended to enable VPC-SC on the first run deploying your foundation. Review [best practices for enabling VPC Service Controls](https://cloud.google.com/vpc-service-controls/docs/enable), then only enforce the perimeter after you have analyzed the access patterns in your dry-run perimeter and created the necessary exceptions for your use cases. | +| restricted\_dns\_project\_id | The restricted DNS project ID | | restricted\_host\_project\_id | The restricted host project ID | | restricted\_network\_name | The name of the VPC being created | | restricted\_network\_self\_link | The URI of the VPC being created | @@ -56,5 +59,6 @@ | restricted\_subnets\_names | The names of the subnets being created | | restricted\_subnets\_secondary\_ranges | The secondary ranges associated with these subnets | | restricted\_subnets\_self\_links | The self-links of subnets being created | +| target\_name\_server\_addresses | List of IPv4 addresses of the target name servers for the forwarding zone configuration. These IP addresses should point to the name server responsible for replying to DNS queries. | diff --git a/3-networks-dual-svpc/modules/base_env/main.tf b/3-networks-dual-svpc/modules/base_env/main.tf index cfd4958a5..ffd7a9c32 100644 --- a/3-networks-dual-svpc/modules/base_env/main.tf +++ b/3-networks-dual-svpc/modules/base_env/main.tf @@ -170,8 +170,8 @@ module "restricted_shared_vpc" { source = "../restricted_shared_vpc" project_id = local.restricted_project_id - dns_hub_project_id = local.dns_hub_project_id project_number = local.restricted_project_number + restricted_dns_project_id = local.restricted_dns_project_id environment_code = var.environment_code access_context_manager_policy_id = var.access_context_manager_policy_id restricted_services = local.restricted_services @@ -202,6 +202,8 @@ module "restricted_shared_vpc" { local.dedicated_interconnect_egress_policy, var.egress_policies_dry_run )) + target_name_server_addresses = var.target_name_server_addresses + subnets = [ @@ -262,15 +264,16 @@ module "restricted_shared_vpc" { module "base_shared_vpc" { source = "../base_shared_vpc" - project_id = local.base_project_id - dns_hub_project_id = local.dns_hub_project_id - environment_code = var.environment_code - private_service_cidr = var.base_private_service_cidr - private_service_connect_ip = var.base_private_service_connect_ip - default_region1 = var.default_region1 - default_region2 = var.default_region2 - domain = var.domain - bgp_asn_subnet = local.bgp_asn_number + project_id = local.base_project_id + base_dns_project_id = local.base_dns_project_id + environment_code = var.environment_code + private_service_cidr = var.base_private_service_cidr + private_service_connect_ip = var.base_private_service_connect_ip + default_region1 = var.default_region1 + default_region2 = var.default_region2 + domain = var.domain + bgp_asn_subnet = local.bgp_asn_number + target_name_server_addresses = var.target_name_server_addresses subnets = [ { @@ -323,3 +326,4 @@ module "base_shared_vpc" { "sb-${var.environment_code}-shared-base-${var.default_region1}" = var.base_subnet_secondary_ranges[var.default_region1] } } + diff --git a/3-networks-dual-svpc/modules/base_env/outputs.tf b/3-networks-dual-svpc/modules/base_env/outputs.tf index 05dfc0107..2b8044a12 100644 --- a/3-networks-dual-svpc/modules/base_env/outputs.tf +++ b/3-networks-dual-svpc/modules/base_env/outputs.tf @@ -14,10 +14,21 @@ * limitations under the License. */ +output "target_name_server_addresses" { + value = var.target_name_server_addresses + description = "List of IPv4 addresses of the target name servers for the forwarding zone configuration. These IP addresses should point to the name server responsible for replying to DNS queries." +} + + /********************* Restricted Outputs *********************/ +output "restricted_dns_project_id" { + value = local.restricted_dns_project_id + description = "The restricted DNS project ID" +} + output "restricted_host_project_id" { value = local.restricted_project_id description = "The restricted host project ID" @@ -79,6 +90,11 @@ output "restricted_service_perimeter_name" { Private Outputs *****************************************/ +output "base_dns_project_id" { + value = local.base_dns_project_id + description = "The base DNS project ID" +} + output "base_host_project_id" { value = local.base_project_id description = "The base host project ID" @@ -113,3 +129,4 @@ output "base_subnets_secondary_ranges" { value = module.base_shared_vpc.subnets_secondary_ranges description = "The secondary ranges associated with these subnets" } + diff --git a/3-networks-dual-svpc/modules/base_env/remote.tf b/3-networks-dual-svpc/modules/base_env/remote.tf index 8bad47f0d..8c8f853ec 100644 --- a/3-networks-dual-svpc/modules/base_env/remote.tf +++ b/3-networks-dual-svpc/modules/base_env/remote.tf @@ -16,13 +16,14 @@ locals { restricted_project_id = data.terraform_remote_state.org.outputs.shared_vpc_projects[var.env].restricted_shared_vpc_project_id - restricted_project_number = data.terraform_remote_state.org.outputs.shared_vpc_projects[var.env].restricted_shared_vpc_project_number base_project_id = data.terraform_remote_state.org.outputs.shared_vpc_projects[var.env].base_shared_vpc_project_id + restricted_project_number = data.terraform_remote_state.org.outputs.shared_vpc_projects[var.env].restricted_shared_vpc_project_number interconnect_project_number = data.terraform_remote_state.org.outputs.interconnect_project_number - dns_hub_project_id = data.terraform_remote_state.org.outputs.dns_hub_project_id organization_service_account = data.terraform_remote_state.bootstrap.outputs.organization_step_terraform_service_account_email networks_service_account = data.terraform_remote_state.bootstrap.outputs.networks_step_terraform_service_account_email projects_service_account = data.terraform_remote_state.bootstrap.outputs.projects_step_terraform_service_account_email + restricted_dns_project_id = data.terraform_remote_state.org.outputs.shared_vpc_projects["production"].restricted_shared_vpc_project_id + base_dns_project_id = data.terraform_remote_state.org.outputs.shared_vpc_projects["production"].base_shared_vpc_project_id } data "terraform_remote_state" "bootstrap" { @@ -42,3 +43,4 @@ data "terraform_remote_state" "org" { prefix = "terraform/org/state" } } + diff --git a/3-networks-dual-svpc/modules/base_env/remote.tf.cloud.example b/3-networks-dual-svpc/modules/base_env/remote.tf.cloud.example index 6ba8d057d..df60f9e1c 100644 --- a/3-networks-dual-svpc/modules/base_env/remote.tf.cloud.example +++ b/3-networks-dual-svpc/modules/base_env/remote.tf.cloud.example @@ -19,7 +19,6 @@ locals { restricted_project_number = data.tfe_outputs.org.nonsensitive_values.shared_vpc_projects[var.env].restricted_shared_vpc_project_number base_project_id = data.tfe_outputs.org.nonsensitive_values.shared_vpc_projects[var.env].base_shared_vpc_project_id interconnect_project_number = data.tfe_outputs.org.nonsensitive_values.interconnect_project_number - dns_hub_project_id = data.tfe_outputs.org.nonsensitive_values.dns_hub_project_id organization_service_account = data.tfe_outputs.bootstrap.nonsensitive_values.organization_step_terraform_service_account_email networks_service_account = data.tfe_outputs.bootstrap.nonsensitive_values.networks_step_terraform_service_account_email projects_service_account = data.tfe_outputs.bootstrap.nonsensitive_values.projects_step_terraform_service_account_email diff --git a/3-networks-dual-svpc/modules/base_env/variables.tf b/3-networks-dual-svpc/modules/base_env/variables.tf index 963eae139..4bb88ca6c 100644 --- a/3-networks-dual-svpc/modules/base_env/variables.tf +++ b/3-networks-dual-svpc/modules/base_env/variables.tf @@ -14,6 +14,12 @@ * limitations under the License. */ +variable "target_name_server_addresses" { + description = "List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones." + type = list(map(any)) + default = [] +} + variable "remote_state_bucket" { description = "Backend bucket to load Terraform Remote State Data from previous steps." type = string @@ -212,3 +218,4 @@ variable "tfc_org_name" { description = "Name of the TFC organization" type = string } + diff --git a/3-networks-dual-svpc/modules/base_shared_vpc/README.md b/3-networks-dual-svpc/modules/base_shared_vpc/README.md index 10b8c0e1c..6636bf604 100644 --- a/3-networks-dual-svpc/modules/base_shared_vpc/README.md +++ b/3-networks-dual-svpc/modules/base_shared_vpc/README.md @@ -3,12 +3,13 @@ | Name | Description | Type | Default | Required | |------|-------------|------|---------|:--------:| +| base\_dns\_project\_id | Project ID for DNS Base Shared. | `string` | `""` | no | +| base\_network\_name | The name of the VPC being created | `string` | `""` | no | | bgp\_asn\_subnet | BGP ASN for Subnets cloud routers. | `number` | n/a | yes | | default\_region1 | Default region 1 for subnets and Cloud Routers | `string` | n/a | yes | | default\_region2 | Default region 2 for subnets and Cloud Routers | `string` | n/a | yes | | dns\_enable\_inbound\_forwarding | Toggle inbound query forwarding for VPC DNS. | `bool` | `true` | no | | dns\_enable\_logging | Toggle DNS logging for VPC DNS. | `bool` | `true` | no | -| dns\_hub\_project\_id | The DNS hub project ID | `string` | n/a | yes | | domain | The DNS name of peering managed zone, for instance 'example.com.' | `string` | n/a | yes | | enable\_all\_vpc\_internal\_traffic | Enable firewall policy rule to allow internal traffic (ingress and egress). | `bool` | `false` | no | | environment\_code | A short form of the folder level resources (environment) within the Google Cloud organization. | `string` | n/a | yes | @@ -22,6 +23,7 @@ | project\_id | Project ID for Private Shared VPC. | `string` | n/a | yes | | secondary\_ranges | Secondary ranges that will be used in some of the subnets | `map(list(object({ range_name = string, ip_cidr_range = string })))` | `{}` | no | | subnets | The list of subnets being created |
list(object({
subnet_name = string
subnet_ip = string
subnet_region = string
subnet_private_access = optional(string, "false")
subnet_private_ipv6_access = optional(string)
subnet_flow_logs = optional(string, "false")
subnet_flow_logs_interval = optional(string, "INTERVAL_5_SEC")
subnet_flow_logs_sampling = optional(string, "0.5")
subnet_flow_logs_metadata = optional(string, "INCLUDE_ALL_METADATA")
subnet_flow_logs_filter = optional(string, "true")
subnet_flow_logs_metadata_fields = optional(list(string), [])
description = optional(string)
purpose = optional(string)
role = optional(string)
stack_type = optional(string)
ipv6_access_type = optional(string)
}))
| `[]` | no | +| target\_name\_server\_addresses | List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones. | `list(map(any))` | n/a | yes | | windows\_activation\_enabled | Enable Windows license activation for Windows workloads. | `bool` | `false` | no | ## Outputs diff --git a/3-networks-dual-svpc/modules/base_shared_vpc/dns.tf b/3-networks-dual-svpc/modules/base_shared_vpc/dns.tf index 3b11a05eb..dd065135e 100644 --- a/3-networks-dual-svpc/modules/base_shared_vpc/dns.tf +++ b/3-networks-dual-svpc/modules/base_shared_vpc/dns.tf @@ -32,14 +32,19 @@ resource "google_dns_policy" "default_policy" { Creates DNS Peering to DNS HUB *****************************************/ data "google_compute_network" "vpc_dns_hub" { - name = "vpc-net-dns" - project = var.dns_hub_project_id + + count = var.environment_code != "p" ? 1 : 0 + + name = "vpc-p-shared-base" + project = var.base_dns_project_id } module "peering_zone" { source = "terraform-google-modules/cloud-dns/google" version = "~> 5.0" + count = var.environment_code != "p" ? 1 : 0 + project_id = var.project_id type = "peering" name = "dz-${var.environment_code}-shared-base-to-dns-hub" @@ -49,5 +54,25 @@ module "peering_zone" { private_visibility_config_networks = [ module.main.network_self_link ] - target_network = data.google_compute_network.vpc_dns_hub.self_link + target_network = data.google_compute_network.vpc_dns_hub[0].self_link +} + +/****************************************** + DNS Forwarding +*****************************************/ +module "dns_forwarding_zone" { + source = "terraform-google-modules/cloud-dns/google" + version = "~> 5.0" + + count = var.environment_code == "p" ? 1 : 0 + + project_id = var.project_id + type = "forwarding" + name = "fz-dns-hub" + domain = var.domain + + private_visibility_config_networks = [ + module.main.network_self_link + ] + target_name_server_addresses = var.target_name_server_addresses } diff --git a/3-networks-dual-svpc/modules/base_shared_vpc/main.tf b/3-networks-dual-svpc/modules/base_shared_vpc/main.tf index 31e3d7763..d5ad2522c 100644 --- a/3-networks-dual-svpc/modules/base_shared_vpc/main.tf +++ b/3-networks-dual-svpc/modules/base_shared_vpc/main.tf @@ -15,9 +15,12 @@ */ locals { - vpc_name = "${var.environment_code}-shared-base" - network_name = "vpc-${local.vpc_name}" - private_googleapis_cidr = module.private_service_connect.private_service_connect_ip + vpc_name = "${var.environment_code}-shared-base" + network_name = "vpc-${local.vpc_name}" + private_googleapis_cidr = module.private_service_connect.private_service_connect_ip + google_forward_source_range = "35.199.192.0/19" + advertised_ip = var.environment_code == "p" ? [{ range = local.google_forward_source_range }, { range = local.private_googleapis_cidr }] : [{ range = local.private_googleapis_cidr }] + } /****************************************** @@ -62,6 +65,7 @@ module "main" { ) } + /*************************************************************** Configure Service Networking for Cloud SQL & future services. **************************************************************/ @@ -101,7 +105,7 @@ module "region1_router1" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.private_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } @@ -116,7 +120,7 @@ module "region1_router2" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.private_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } @@ -131,7 +135,7 @@ module "region2_router1" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.private_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } @@ -146,6 +150,7 @@ module "region2_router2" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.private_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } + diff --git a/3-networks-dual-svpc/modules/base_shared_vpc/outputs.tf b/3-networks-dual-svpc/modules/base_shared_vpc/outputs.tf index 226e21343..f2e9e6eeb 100644 --- a/3-networks-dual-svpc/modules/base_shared_vpc/outputs.tf +++ b/3-networks-dual-svpc/modules/base_shared_vpc/outputs.tf @@ -14,6 +14,7 @@ * limitations under the License. */ + output "network_name" { value = module.main.network_name description = "The name of the VPC being created" @@ -78,3 +79,4 @@ output "region2_router2" { value = module.region2_router2 description = "Router 2 for Region 2" } + diff --git a/3-networks-dual-svpc/modules/base_shared_vpc/variables.tf b/3-networks-dual-svpc/modules/base_shared_vpc/variables.tf index 4b2fca26b..d1cab59d4 100644 --- a/3-networks-dual-svpc/modules/base_shared_vpc/variables.tf +++ b/3-networks-dual-svpc/modules/base_shared_vpc/variables.tf @@ -14,16 +14,29 @@ * limitations under the License. */ -variable "project_id" { +variable "base_dns_project_id" { + description = "Project ID for DNS Base Shared." type = string - description = "Project ID for Private Shared VPC." + default = "" +} + +variable "target_name_server_addresses" { + description = "List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones." + type = list(map(any)) } -variable "dns_hub_project_id" { +variable "base_network_name" { type = string - description = "The DNS hub project ID" + description = "The name of the VPC being created" + default = "" } +variable "project_id" { + type = string + description = "Project ID for Private Shared VPC." +} + + variable "environment_code" { type = string description = "A short form of the folder level resources (environment) within the Google Cloud organization." @@ -142,3 +155,4 @@ variable "enable_all_vpc_internal_traffic" { description = "Enable firewall policy rule to allow internal traffic (ingress and egress)." default = false } + diff --git a/3-networks-dual-svpc/modules/restricted_shared_vpc/README.md b/3-networks-dual-svpc/modules/restricted_shared_vpc/README.md index 1ce44d877..3ad3b457d 100644 --- a/3-networks-dual-svpc/modules/restricted_shared_vpc/README.md +++ b/3-networks-dual-svpc/modules/restricted_shared_vpc/README.md @@ -9,7 +9,6 @@ | default\_region2 | Second subnet region. The shared vpc modules only configures two regions. | `string` | n/a | yes | | dns\_enable\_inbound\_forwarding | Toggle inbound query forwarding for VPC DNS. | `bool` | `true` | no | | dns\_enable\_logging | Toggle DNS logging for VPC DNS. | `bool` | `true` | no | -| dns\_hub\_project\_id | The DNS hub project ID | `string` | n/a | yes | | domain | The DNS name of peering managed zone, for instance 'example.com.' | `string` | n/a | yes | | egress\_policies | A list of all [egress policies](https://cloud.google.com/vpc-service-controls/docs/ingress-egress-rules#egress-rules-reference) to use in an enforced perimeter. Each list object has a `from` and `to` value that describes egress\_from and egress\_to.

Example: `[{ from={ identities=[], identity_type="ID_TYPE" }, to={ resources=[], operations={ "SRV_NAME"={ OP_TYPE=[] }}}}]`

Valid Values:
`ID_TYPE` = `null` or `IDENTITY_TYPE_UNSPECIFIED` (only allow indentities from list); `ANY_IDENTITY`; `ANY_USER_ACCOUNT`; `ANY_SERVICE_ACCOUNT`
`SRV_NAME` = "`*`" (allow all services) or [Specific Services](https://cloud.google.com/vpc-service-controls/docs/supported-products#supported_products)
`OP_TYPE` = [methods](https://cloud.google.com/vpc-service-controls/docs/supported-method-restrictions) or [permissions](https://cloud.google.com/vpc-service-controls/docs/supported-method-restrictions) |
list(object({
from = any
to = any
}))
| `[]` | no | | egress\_policies\_dry\_run | A list of all [egress policies](https://cloud.google.com/vpc-service-controls/docs/ingress-egress-rules#egress-rules-reference) to use in a dry-run perimeter. Each list object has a `from` and `to` value that describes egress\_from and egress\_to.

Example: `[{ from={ identities=[], identity_type="ID_TYPE" }, to={ resources=[], operations={ "SRV_NAME"={ OP_TYPE=[] }}}}]`

Valid Values:
`ID_TYPE` = `null` or `IDENTITY_TYPE_UNSPECIFIED` (only allow indentities from list); `ANY_IDENTITY`; `ANY_USER_ACCOUNT`; `ANY_SERVICE_ACCOUNT`
`SRV_NAME` = "`*`" (allow all services) or [Specific Services](https://cloud.google.com/vpc-service-controls/docs/supported-products#supported_products)
`OP_TYPE` = [methods](https://cloud.google.com/vpc-service-controls/docs/supported-method-restrictions) or [permissions](https://cloud.google.com/vpc-service-controls/docs/supported-method-restrictions) |
list(object({
from = any
to = any
}))
| `[]` | no | @@ -29,10 +28,12 @@ | private\_service\_connect\_ip | Internal IP to be used as the private service connect endpoint. | `string` | n/a | yes | | project\_id | Project ID for Restricted Shared VPC. | `string` | n/a | yes | | project\_number | Project number for Restricted Shared VPC. It is the project INSIDE the regular service perimeter. | `number` | n/a | yes | +| restricted\_dns\_project\_id | Project ID for DNS Restricted Shared. | `string` | `""` | no | | restricted\_services | List of services to restrict in an enforced perimeter. | `list(string)` | n/a | yes | | restricted\_services\_dry\_run | List of services to restrict in a dry-run perimeter. | `list(string)` | n/a | yes | | secondary\_ranges | Secondary ranges that will be used in some of the subnets | `map(list(object({ range_name = string, ip_cidr_range = string })))` | `{}` | no | | subnets | The list of subnets being created |
list(object({
subnet_name = string
subnet_ip = string
subnet_region = string
subnet_private_access = optional(string, "false")
subnet_private_ipv6_access = optional(string)
subnet_flow_logs = optional(string, "false")
subnet_flow_logs_interval = optional(string, "INTERVAL_5_SEC")
subnet_flow_logs_sampling = optional(string, "0.5")
subnet_flow_logs_metadata = optional(string, "INCLUDE_ALL_METADATA")
subnet_flow_logs_filter = optional(string, "true")
subnet_flow_logs_metadata_fields = optional(list(string), [])
description = optional(string)
purpose = optional(string)
role = optional(string)
stack_type = optional(string)
ipv6_access_type = optional(string)
}))
| `[]` | no | +| target\_name\_server\_addresses | List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones. | `list(map(any))` | n/a | yes | | windows\_activation\_enabled | Enable Windows license activation for Windows workloads. | `bool` | `false` | no | ## Outputs diff --git a/3-networks-dual-svpc/modules/restricted_shared_vpc/dns.tf b/3-networks-dual-svpc/modules/restricted_shared_vpc/dns.tf index 138ad4505..85b190d82 100644 --- a/3-networks-dual-svpc/modules/restricted_shared_vpc/dns.tf +++ b/3-networks-dual-svpc/modules/restricted_shared_vpc/dns.tf @@ -32,14 +32,19 @@ resource "google_dns_policy" "default_policy" { Creates DNS Peering to DNS HUB *****************************************/ data "google_compute_network" "vpc_dns_hub" { - name = "vpc-net-dns" - project = var.dns_hub_project_id + + count = var.environment_code != "p" ? 1 : 0 + + name = "vpc-p-shared-restricted" + project = var.restricted_dns_project_id } module "peering_zone" { source = "terraform-google-modules/cloud-dns/google" version = "~> 5.0" + count = var.environment_code != "p" ? 1 : 0 + project_id = var.project_id type = "peering" name = "dz-${var.environment_code}-shared-restricted-to-dns-hub" @@ -49,5 +54,26 @@ module "peering_zone" { private_visibility_config_networks = [ module.main.network_self_link ] - target_network = data.google_compute_network.vpc_dns_hub.self_link + target_network = data.google_compute_network.vpc_dns_hub[0].self_link +} + +/****************************************** + DNS Forwarding +*****************************************/ +module "dns_forwarding_zone" { + source = "terraform-google-modules/cloud-dns/google" + version = "~> 5.0" + + count = var.environment_code == "p" ? 1 : 0 + + project_id = var.project_id + type = "forwarding" + name = "fz-dns-hub" + domain = var.domain + + private_visibility_config_networks = [ + module.main.network_self_link + ] + target_name_server_addresses = var.target_name_server_addresses } + diff --git a/3-networks-dual-svpc/modules/restricted_shared_vpc/main.tf b/3-networks-dual-svpc/modules/restricted_shared_vpc/main.tf index 54c2f648d..75792e367 100644 --- a/3-networks-dual-svpc/modules/restricted_shared_vpc/main.tf +++ b/3-networks-dual-svpc/modules/restricted_shared_vpc/main.tf @@ -15,9 +15,11 @@ */ locals { - vpc_name = "${var.environment_code}-shared-restricted" - network_name = "vpc-${local.vpc_name}" - restricted_googleapis_cidr = module.private_service_connect.private_service_connect_ip + vpc_name = "${var.environment_code}-shared-restricted" + network_name = "vpc-${local.vpc_name}" + restricted_googleapis_cidr = module.private_service_connect.private_service_connect_ip + google_forward_source_range = "35.199.192.0/19" + advertised_ip = var.environment_code == "p" ? [{ range = local.google_forward_source_range }, { range = local.restricted_googleapis_cidr }] : [{ range = local.restricted_googleapis_cidr }] } /****************************************** @@ -63,6 +65,7 @@ module "main" { ) } + /*************************************************************** Configure Service Networking for Cloud SQL & future services. **************************************************************/ @@ -105,7 +108,7 @@ module "region1_router1" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.restricted_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } @@ -120,7 +123,7 @@ module "region1_router2" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.restricted_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } @@ -135,7 +138,7 @@ module "region2_router1" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.restricted_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } @@ -150,6 +153,7 @@ module "region2_router2" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.restricted_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } + diff --git a/3-networks-dual-svpc/modules/restricted_shared_vpc/outputs.tf b/3-networks-dual-svpc/modules/restricted_shared_vpc/outputs.tf index af80f106d..748ec4ca3 100644 --- a/3-networks-dual-svpc/modules/restricted_shared_vpc/outputs.tf +++ b/3-networks-dual-svpc/modules/restricted_shared_vpc/outputs.tf @@ -88,3 +88,4 @@ output "service_perimeter_name" { value = local.perimeter_name description = "Access context manager service perimeter name for the enforced perimeter" } + diff --git a/3-networks-dual-svpc/modules/restricted_shared_vpc/variables.tf b/3-networks-dual-svpc/modules/restricted_shared_vpc/variables.tf index 7774c1d49..27e733385 100644 --- a/3-networks-dual-svpc/modules/restricted_shared_vpc/variables.tf +++ b/3-networks-dual-svpc/modules/restricted_shared_vpc/variables.tf @@ -14,6 +14,17 @@ * limitations under the License. */ +variable "restricted_dns_project_id" { + description = "Project ID for DNS Restricted Shared." + type = string + default = "" +} + +variable "target_name_server_addresses" { + description = "List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones." + type = list(map(any)) +} + variable "access_context_manager_policy_id" { type = number description = "The id of the default Access Context Manager policy. Can be obtained by running `gcloud access-context-manager policies list --organization YOUR_ORGANIZATION_ID --format=\"value(name)\"`." @@ -29,11 +40,6 @@ variable "project_number" { description = "Project number for Restricted Shared VPC. It is the project INSIDE the regular service perimeter." } -variable "dns_hub_project_id" { - type = string - description = "The DNS hub project ID" -} - variable "environment_code" { type = string description = "A short form of the folder level resources (environment) within the Google Cloud organization." @@ -214,3 +220,4 @@ variable "ingress_policies_dry_run" { })) default = [] } + diff --git a/3-networks-dual-svpc/shared.auto.example.tfvars b/3-networks-dual-svpc/production.auto.example.tfvars similarity index 99% rename from 3-networks-dual-svpc/shared.auto.example.tfvars rename to 3-networks-dual-svpc/production.auto.example.tfvars index 0db7e30ea..6003cdb9a 100644 --- a/3-networks-dual-svpc/shared.auto.example.tfvars +++ b/3-networks-dual-svpc/production.auto.example.tfvars @@ -26,3 +26,4 @@ target_name_server_addresses = [ forwarding_path = "default" } ] + diff --git a/3-networks-hub-and-spoke/envs/shared/README.md b/3-networks-hub-and-spoke/envs/shared/README.md index f4a8db3d9..73394b3e5 100644 --- a/3-networks-hub-and-spoke/envs/shared/README.md +++ b/3-networks-hub-and-spoke/envs/shared/README.md @@ -52,6 +52,11 @@ The purpose of this step is to set up the global [DNS Hub](https://cloud.google. | Name | Description | |------|-------------| -| dns\_hub\_project\_id | The DNS hub project ID | +| base\_dns\_policy | The name of the DNS policy being created | +| base\_host\_project\_id | The base host project ID | +| base\_network\_name | The name of the VPC being created | +| restricted\_dns\_policy | The name of the DNS policy being created | +| restricted\_host\_project\_id | The restricted host project ID | +| restricted\_network\_name | The name of the VPC being created | diff --git a/3-networks-hub-and-spoke/envs/shared/dns-hub.tf b/3-networks-hub-and-spoke/envs/shared/dns-hub.tf deleted file mode 100644 index 8235754ef..000000000 --- a/3-networks-hub-and-spoke/envs/shared/dns-hub.tf +++ /dev/null @@ -1,156 +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. - */ - -/****************************************** - DNS Hub VPC -*****************************************/ - -module "dns_hub_vpc" { - source = "terraform-google-modules/network/google" - version = "~> 10.0" - - project_id = local.dns_hub_project_id - network_name = "vpc-net-dns" - shared_vpc_host = "false" - delete_default_internet_gateway_routes = "true" - - subnets = [{ - subnet_name = "sb-net-dns-${local.default_region1}" - subnet_ip = "172.16.0.0/25" - subnet_region = local.default_region1 - subnet_private_access = "true" - subnet_flow_logs = var.dns_vpc_flow_logs.enable_logging - subnet_flow_logs_interval = var.dns_vpc_flow_logs.aggregation_interval - subnet_flow_logs_sampling = var.dns_vpc_flow_logs.flow_sampling - subnet_flow_logs_metadata = var.dns_vpc_flow_logs.metadata - subnet_flow_logs_metadata_fields = var.dns_vpc_flow_logs.metadata_fields - subnet_flow_logs_filter = var.dns_vpc_flow_logs.filter_expr - description = "DNS hub subnet for region 1." - }, { - subnet_name = "sb-net-dns-${local.default_region2}" - subnet_ip = "172.16.0.128/25" - subnet_region = local.default_region2 - subnet_private_access = "true" - subnet_flow_logs = var.dns_vpc_flow_logs.enable_logging - subnet_flow_logs_interval = var.dns_vpc_flow_logs.aggregation_interval - subnet_flow_logs_sampling = var.dns_vpc_flow_logs.flow_sampling - subnet_flow_logs_metadata = var.dns_vpc_flow_logs.metadata - subnet_flow_logs_metadata_fields = var.dns_vpc_flow_logs.metadata_fields - subnet_flow_logs_filter = var.dns_vpc_flow_logs.filter_expr - description = "DNS hub subnet for region 2." - }] - - routes = [{ - name = "rt-net-dns-1000-all-default-private-api" - description = "Route through IGW to allow private google api access." - destination_range = "199.36.153.8/30" - next_hop_internet = "true" - priority = "1000" - }] -} - -/****************************************** - Default DNS Policy - *****************************************/ - -resource "google_dns_policy" "default_policy" { - project = local.dns_hub_project_id - name = "dp-dns-hub-default-policy" - enable_inbound_forwarding = true - enable_logging = var.dns_enable_logging - networks { - network_url = module.dns_hub_vpc.network_self_link - } -} - -/****************************************** - DNS Forwarding -*****************************************/ - -module "dns-forwarding-zone" { - source = "terraform-google-modules/cloud-dns/google" - version = "~> 5.0" - - project_id = local.dns_hub_project_id - type = "forwarding" - name = "fz-dns-hub" - domain = var.domain - - private_visibility_config_networks = [ - module.dns_hub_vpc.network_self_link - ] - target_name_server_addresses = var.target_name_server_addresses -} - -/********************************************************* - Routers to advertise DNS proxy range "35.199.192.0/19" -*********************************************************/ - -module "dns_hub_region1_router1" { - source = "terraform-google-modules/cloud-router/google" - version = "~> 6.0" - - name = "cr-net-dns-${local.default_region1}-cr1" - project = local.dns_hub_project_id - network = module.dns_hub_vpc.network_name - region = local.default_region1 - bgp = { - asn = local.dns_bgp_asn_number - advertised_ip_ranges = [{ range = "35.199.192.0/19" }] - } -} - -module "dns_hub_region1_router2" { - source = "terraform-google-modules/cloud-router/google" - version = "~> 6.0" - - name = "cr-net-dns-${local.default_region1}-cr2" - project = local.dns_hub_project_id - network = module.dns_hub_vpc.network_name - region = local.default_region1 - bgp = { - asn = local.dns_bgp_asn_number - advertised_ip_ranges = [{ range = "35.199.192.0/19" }] - } -} - -module "dns_hub_region2_router1" { - source = "terraform-google-modules/cloud-router/google" - version = "~> 6.0" - - name = "cr-net-dns-${local.default_region2}-cr3" - project = local.dns_hub_project_id - network = module.dns_hub_vpc.network_name - region = local.default_region2 - bgp = { - asn = local.dns_bgp_asn_number - advertised_ip_ranges = [{ range = "35.199.192.0/19" }] - } -} - -module "dns_hub_region2_router2" { - source = "terraform-google-modules/cloud-router/google" - version = "~> 6.0" - - name = "cr-net-dns-${local.default_region2}-cr4" - project = local.dns_hub_project_id - network = module.dns_hub_vpc.network_name - region = local.default_region2 - bgp = { - asn = local.dns_bgp_asn_number - advertised_ip_ranges = [{ range = "35.199.192.0/19" }] - } -} diff --git a/3-networks-hub-and-spoke/envs/shared/interconnect.tf.example b/3-networks-hub-and-spoke/envs/shared/interconnect.tf.example index 9151fa3fa..c4486e270 100644 --- a/3-networks-hub-and-spoke/envs/shared/interconnect.tf.example +++ b/3-networks-hub-and-spoke/envs/shared/interconnect.tf.example @@ -14,50 +14,6 @@ * limitations under the License. */ -module "dns_hub_interconnect" { - source = "../../modules/dedicated_interconnect" - - vpc_name = "net-dns" - interconnect_project_id = local.dns_hub_project_id - - region1 = local.default_region1 - region1_router1_name = module.dns_hub_region1_router1.router.name - region1_interconnect1_candidate_subnets = ["169.254.0.0/29"] - region1_interconnect1_vlan_tag8021q = "3931" - region1_interconnect1 = "https://www.googleapis.com/compute/v1/projects/${local.interconnect_project_id}/global/interconnects/example-interconnect-1" - region1_interconnect1_location = "las-zone1-770" - region1_interconnect1_onprem_dc = "onprem-dc1" - region1_router2_name = module.dns_hub_region1_router2.router.name - region1_interconnect2_candidate_subnets = ["169.254.0.8/29"] - region1_interconnect2_vlan_tag8021q = "3932" - region1_interconnect2 = "https://www.googleapis.com/compute/v1/projects/${local.interconnect_project_id}/global/interconnects/example-interconnect-2" - region1_interconnect2_location = "las-zone1-770" - region1_interconnect2_onprem_dc = "onprem-dc2" - - region2 = local.default_region2 - region2_router1_name = module.dns_hub_region2_router1.router.name - region2_interconnect1_candidate_subnets = ["169.254.0.16/29"] - region2_interconnect1_vlan_tag8021q = "3933" - region2_interconnect1 = "https://www.googleapis.com/compute/v1/projects/${local.interconnect_project_id}/global/interconnects/example-interconnect-3" - region2_interconnect1_location = "lax-zone2-19" - region2_interconnect1_onprem_dc = "onprem-dc3" - region2_router2_name = module.dns_hub_region2_router2.router.name - region2_interconnect2_candidate_subnets = ["169.254.0.24/29"] - region2_interconnect2_vlan_tag8021q = "3934" - region2_interconnect2 = "https://www.googleapis.com/compute/v1/projects/${local.interconnect_project_id}/global/interconnects/example-interconnect-4" - region2_interconnect2_location = "lax-zone1-403" - region2_interconnect2_onprem_dc = "onprem-dc4" - - peer_asn = "64515" - peer_name = "interconnect-peer" - - cloud_router_labels = { - vlan_1 = "cr1", - vlan_2 = "cr2", - vlan_3 = "cr3", - vlan_4 = "cr4" - } -} module "shared_restricted_interconnect" { source = "../../modules/dedicated_interconnect" diff --git a/3-networks-hub-and-spoke/envs/shared/net-hubs.tf b/3-networks-hub-and-spoke/envs/shared/net-hubs.tf index ec6a99e84..dcffa010d 100644 --- a/3-networks-hub-and-spoke/envs/shared/net-hubs.tf +++ b/3-networks-hub-and-spoke/envs/shared/net-hubs.tf @@ -175,7 +175,6 @@ module "base_shared_vpc" { source = "../../modules/base_shared_vpc" project_id = local.base_net_hub_project_id - dns_hub_project_id = local.dns_hub_project_id environment_code = local.environment_code private_service_connect_ip = "10.17.0.1" bgp_asn_subnet = local.bgp_asn_number @@ -190,6 +189,7 @@ module "base_shared_vpc" { nat_num_addresses_region1 = var.base_hub_nat_num_addresses_region1 nat_num_addresses_region2 = var.base_hub_nat_num_addresses_region2 windows_activation_enabled = var.base_hub_windows_activation_enabled + target_name_server_addresses = var.target_name_server_addresses mode = "hub" subnets = [ @@ -240,7 +240,6 @@ module "base_shared_vpc" { ] secondary_ranges = {} - depends_on = [module.dns_hub_vpc] } /****************************************** @@ -252,7 +251,6 @@ module "restricted_shared_vpc" { project_id = local.restricted_net_hub_project_id project_number = local.restricted_net_hub_project_number - dns_hub_project_id = local.dns_hub_project_id environment_code = local.environment_code private_service_connect_ip = "10.17.0.5" access_context_manager_policy_id = var.access_context_manager_policy_id @@ -280,6 +278,7 @@ module "restricted_shared_vpc" { nat_num_addresses_region1 = var.restricted_hub_nat_num_addresses_region1 nat_num_addresses_region2 = var.restricted_hub_nat_num_addresses_region2 windows_activation_enabled = var.restricted_hub_windows_activation_enabled + target_name_server_addresses = var.target_name_server_addresses mode = "hub" subnets = [ @@ -337,5 +336,4 @@ module "restricted_shared_vpc" { ingress_policies = var.ingress_policies - depends_on = [module.dns_hub_vpc] } diff --git a/3-networks-hub-and-spoke/envs/shared/outputs.tf b/3-networks-hub-and-spoke/envs/shared/outputs.tf index 06f9b0702..6af4101cf 100644 --- a/3-networks-hub-and-spoke/envs/shared/outputs.tf +++ b/3-networks-hub-and-spoke/envs/shared/outputs.tf @@ -14,7 +14,32 @@ * limitations under the License. */ -output "dns_hub_project_id" { - value = local.dns_hub_project_id - description = "The DNS hub project ID" +output "restricted_host_project_id" { + value = local.restricted_net_hub_project_id + description = "The restricted host project ID" +} + +output "base_host_project_id" { + value = local.base_net_hub_project_id + description = "The base host project ID" +} + +output "base_network_name" { + value = module.base_shared_vpc.network_name + description = "The name of the VPC being created" +} + +output "restricted_network_name" { + value = module.restricted_shared_vpc.network_name + description = "The name of the VPC being created" +} + +output "base_dns_policy" { + value = module.base_shared_vpc.base_dns_policy + description = "The name of the DNS policy being created" +} + +output "restricted_dns_policy" { + value = module.restricted_shared_vpc.restricted_dns_policy + description = "The name of the DNS policy being created" } diff --git a/3-networks-hub-and-spoke/envs/shared/partner_interconnect.tf.example b/3-networks-hub-and-spoke/envs/shared/partner_interconnect.tf.example index c85b39594..92cd21dde 100644 --- a/3-networks-hub-and-spoke/envs/shared/partner_interconnect.tf.example +++ b/3-networks-hub-and-spoke/envs/shared/partner_interconnect.tf.example @@ -15,37 +15,6 @@ */ -module "dns_hub_interconnect" { - source = "../../modules/partner_interconnect" - - vpc_name = "net-dns" - attachment_project_id = local.dns_hub_project_id - preactivate = var.preactivate_partner_interconnect - - region1 = local.default_region1 - region1_router1_name = module.dns_hub_region1_router1.router.name - region1_interconnect1_location = "las-zone1-770" - region1_interconnect1_onprem_dc = "onprem-dc-1" - region1_router2_name = module.dns_hub_region1_router2.router.name - region1_interconnect2_location = "las-zone1-770" - region1_interconnect2_onprem_dc = "onprem-dc-2" - - region2 = local.default_region2 - region2_router1_name = module.dns_hub_region2_router1.router.name - region2_interconnect1_location = "lax-zone2-19" - region2_interconnect1_onprem_dc = "onprem-dc-3" - region2_router2_name = module.dns_hub_region2_router2.router.name - region2_interconnect2_location = "lax-zone1-403" - region2_interconnect2_onprem_dc = "onprem-dc-4" - - cloud_router_labels = { - vlan_1 = "cr1", - vlan_2 = "cr2", - vlan_3 = "cr3", - vlan_4 = "cr4" - } -} - module "shared_restricted_interconnect" { source = "../../modules/partner_interconnect" diff --git a/3-networks-hub-and-spoke/envs/shared/remote.tf b/3-networks-hub-and-spoke/envs/shared/remote.tf index 6660a6627..78e898578 100644 --- a/3-networks-hub-and-spoke/envs/shared/remote.tf +++ b/3-networks-hub-and-spoke/envs/shared/remote.tf @@ -15,7 +15,6 @@ */ locals { - dns_hub_project_id = data.terraform_remote_state.org.outputs.dns_hub_project_id interconnect_project_id = data.terraform_remote_state.org.outputs.interconnect_project_id interconnect_project_number = data.terraform_remote_state.org.outputs.interconnect_project_number parent_folder = data.terraform_remote_state.bootstrap.outputs.common_config.parent_folder diff --git a/3-networks-hub-and-spoke/envs/shared/remote.tf.cloud.example b/3-networks-hub-and-spoke/envs/shared/remote.tf.cloud.example index 127d907ee..f609c65e4 100644 --- a/3-networks-hub-and-spoke/envs/shared/remote.tf.cloud.example +++ b/3-networks-hub-and-spoke/envs/shared/remote.tf.cloud.example @@ -15,7 +15,6 @@ */ locals { - dns_hub_project_id = data.tfe_outputs.org.nonsensitive_values.dns_hub_project_id interconnect_project_id = data.tfe_outputs.org.nonsensitive_values.interconnect_project_id interconnect_project_number = data.tfe_outputs.org.nonsensitive_values.interconnect_project_number parent_folder = data.tfe_outputs.bootstrap.nonsensitive_values.common_config.parent_folder diff --git a/3-networks-hub-and-spoke/modules/base_env/README.md b/3-networks-hub-and-spoke/modules/base_env/README.md index a4f1f2ba6..b3683838d 100644 --- a/3-networks-hub-and-spoke/modules/base_env/README.md +++ b/3-networks-hub-and-spoke/modules/base_env/README.md @@ -33,6 +33,7 @@ | restricted\_subnet\_proxy\_ranges | The base proxy-only subnet primary IPTs ranges to the Restricted Shared Vpc. | `map(string)` | n/a | yes | | restricted\_subnet\_secondary\_ranges | The base subnet secondary IPTs ranges to the Restricted Shared Vpc | `map(list(map(string)))` | n/a | yes | | restricted\_vpc\_flow\_logs | aggregation\_interval: Toggles the aggregation interval for collecting flow logs. Increasing the interval time will reduce the amount of generated flow logs for long lasting connections. Possible values are: INTERVAL\_5\_SEC, INTERVAL\_30\_SEC, INTERVAL\_1\_MIN, INTERVAL\_5\_MIN, INTERVAL\_10\_MIN, INTERVAL\_15\_MIN.
flow\_sampling: Set the sampling rate of VPC flow logs within the subnetwork where 1.0 means all collected logs are reported and 0.0 means no logs are reported. The value of the field must be in [0, 1].
metadata: Configures whether metadata fields should be added to the reported VPC flow logs. Possible values are: EXCLUDE\_ALL\_METADATA, INCLUDE\_ALL\_METADATA, CUSTOM\_METADATA.
metadata\_fields: ist of metadata fields that should be added to reported logs. Can only be specified if VPC flow logs for this subnetwork is enabled and "metadata" is set to CUSTOM\_METADATA.
filter\_expr: Export filter used to define which VPC flow logs should be logged, as as CEL expression. See https://cloud.google.com/vpc/docs/flow-logs#filtering for details on how to format this field. |
object({
aggregation_interval = optional(string, "INTERVAL_5_SEC")
flow_sampling = optional(string, "0.5")
metadata = optional(string, "INCLUDE_ALL_METADATA")
metadata_fields = optional(list(string), [])
filter_expr = optional(string, "true")
})
| `{}` | no | +| target\_name\_server\_addresses | List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones. | `list(map(any))` | `[]` | no | | tfc\_org\_name | Name of the TFC organization | `string` | n/a | yes | ## Outputs @@ -57,5 +58,6 @@ | restricted\_subnets\_names | The names of the subnets being created | | restricted\_subnets\_secondary\_ranges | The secondary ranges associated with these subnets | | restricted\_subnets\_self\_links | The self-links of subnets being created | +| target\_name\_server\_addresses | List of IPv4 address of target name servers for the forwarding zone configuration | diff --git a/3-networks-hub-and-spoke/modules/base_env/main.tf b/3-networks-hub-and-spoke/modules/base_env/main.tf index 354ce2957..a50e05619 100644 --- a/3-networks-hub-and-spoke/modules/base_env/main.tf +++ b/3-networks-hub-and-spoke/modules/base_env/main.tf @@ -166,7 +166,6 @@ module "restricted_shared_vpc" { project_id = local.restricted_project_id project_number = local.restricted_project_number - dns_hub_project_id = local.dns_hub_project_id restricted_net_hub_project_id = local.restricted_net_hub_project_id restricted_net_hub_project_number = local.restricted_net_hub_project_number environment_code = var.environment_code @@ -183,15 +182,16 @@ module "restricted_shared_vpc" { "serviceAccount:${local.projects_service_account}", "serviceAccount:${local.organization_service_account}", ], var.perimeter_additional_members)) - private_service_cidr = var.restricted_private_service_cidr - private_service_connect_ip = var.restricted_private_service_connect_ip - ingress_policies = var.ingress_policies - egress_policies = var.egress_policies - bgp_asn_subnet = local.bgp_asn_number - default_region1 = var.default_region1 - default_region2 = var.default_region2 - domain = var.domain - mode = "spoke" + private_service_cidr = var.restricted_private_service_cidr + private_service_connect_ip = var.restricted_private_service_connect_ip + ingress_policies = var.ingress_policies + egress_policies = var.egress_policies + bgp_asn_subnet = local.bgp_asn_number + default_region1 = var.default_region1 + default_region2 = var.default_region2 + domain = var.domain + mode = "spoke" + target_name_server_addresses = var.target_name_server_addresses subnets = [ { @@ -251,17 +251,17 @@ module "restricted_shared_vpc" { module "base_shared_vpc" { source = "../base_shared_vpc" - project_id = local.base_project_id - dns_hub_project_id = local.dns_hub_project_id - base_net_hub_project_id = local.base_net_hub_project_id - environment_code = var.environment_code - private_service_cidr = var.base_private_service_cidr - private_service_connect_ip = var.base_private_service_connect_ip - default_region1 = var.default_region1 - default_region2 = var.default_region2 - domain = var.domain - bgp_asn_subnet = local.bgp_asn_number - mode = "spoke" + project_id = local.base_project_id + base_net_hub_project_id = local.base_net_hub_project_id + environment_code = var.environment_code + private_service_cidr = var.base_private_service_cidr + private_service_connect_ip = var.base_private_service_connect_ip + default_region1 = var.default_region1 + default_region2 = var.default_region2 + domain = var.domain + bgp_asn_subnet = local.bgp_asn_number + mode = "spoke" + target_name_server_addresses = var.target_name_server_addresses subnets = [ { diff --git a/3-networks-hub-and-spoke/modules/base_env/outputs.tf b/3-networks-hub-and-spoke/modules/base_env/outputs.tf index b51cda651..053c1c134 100644 --- a/3-networks-hub-and-spoke/modules/base_env/outputs.tf +++ b/3-networks-hub-and-spoke/modules/base_env/outputs.tf @@ -14,6 +14,11 @@ * limitations under the License. */ +output "target_name_server_addresses" { + value = var.target_name_server_addresses + description = "List of IPv4 address of target name servers for the forwarding zone configuration" +} + /********************* Restricted Outputs *********************/ diff --git a/3-networks-hub-and-spoke/modules/base_env/remote.tf b/3-networks-hub-and-spoke/modules/base_env/remote.tf index 755146d7a..8a6e50259 100644 --- a/3-networks-hub-and-spoke/modules/base_env/remote.tf +++ b/3-networks-hub-and-spoke/modules/base_env/remote.tf @@ -18,7 +18,6 @@ locals { restricted_project_id = data.terraform_remote_state.org.outputs.shared_vpc_projects[var.env].restricted_shared_vpc_project_id restricted_project_number = data.terraform_remote_state.org.outputs.shared_vpc_projects[var.env].restricted_shared_vpc_project_number base_project_id = data.terraform_remote_state.org.outputs.shared_vpc_projects[var.env].base_shared_vpc_project_id - dns_hub_project_id = data.terraform_remote_state.org.outputs.dns_hub_project_id base_net_hub_project_id = data.terraform_remote_state.org.outputs.base_net_hub_project_id restricted_net_hub_project_id = data.terraform_remote_state.org.outputs.restricted_net_hub_project_id restricted_net_hub_project_number = data.terraform_remote_state.org.outputs.restricted_net_hub_project_number diff --git a/3-networks-hub-and-spoke/modules/base_env/remote.tf.cloud.example b/3-networks-hub-and-spoke/modules/base_env/remote.tf.cloud.example index 14d3bd29f..05eefabbe 100644 --- a/3-networks-hub-and-spoke/modules/base_env/remote.tf.cloud.example +++ b/3-networks-hub-and-spoke/modules/base_env/remote.tf.cloud.example @@ -18,7 +18,6 @@ locals { restricted_project_id = data.tfe_outputs.org.nonsensitive_values.shared_vpc_projects[var.env].restricted_shared_vpc_project_id restricted_project_number = data.tfe_outputs.org.nonsensitive_values.shared_vpc_projects[var.env].restricted_shared_vpc_project_number base_project_id = data.tfe_outputs.org.nonsensitive_values.shared_vpc_projects[var.env].base_shared_vpc_project_id - dns_hub_project_id = data.tfe_outputs.org.nonsensitive_values.dns_hub_project_id base_net_hub_project_id = data.tfe_outputs.org.nonsensitive_values.base_net_hub_project_id restricted_net_hub_project_id = data.tfe_outputs.org.nonsensitive_values.restricted_net_hub_project_id restricted_net_hub_project_number = data.tfe_outputs.org.nonsensitive_values.restricted_net_hub_project_number diff --git a/3-networks-hub-and-spoke/modules/base_env/variables.tf b/3-networks-hub-and-spoke/modules/base_env/variables.tf index bdbf39987..aa4cdef97 100644 --- a/3-networks-hub-and-spoke/modules/base_env/variables.tf +++ b/3-networks-hub-and-spoke/modules/base_env/variables.tf @@ -14,6 +14,12 @@ * limitations under the License. */ +variable "target_name_server_addresses" { + description = "List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones." + type = list(map(any)) + default = [] +} + variable "remote_state_bucket" { description = "Backend bucket to load Terraform Remote State Data from previous steps." type = string diff --git a/3-networks-hub-and-spoke/modules/base_shared_vpc/README.md b/3-networks-hub-and-spoke/modules/base_shared_vpc/README.md index bc1d6b4e1..7e0b74baa 100644 --- a/3-networks-hub-and-spoke/modules/base_shared_vpc/README.md +++ b/3-networks-hub-and-spoke/modules/base_shared_vpc/README.md @@ -9,7 +9,6 @@ | default\_region2 | Default region 2 for subnets and Cloud Routers | `string` | n/a | yes | | dns\_enable\_inbound\_forwarding | Toggle inbound query forwarding for VPC DNS. | `bool` | `true` | no | | dns\_enable\_logging | Toggle DNS logging for VPC DNS. | `bool` | `true` | no | -| dns\_hub\_project\_id | The DNS hub project ID | `string` | n/a | yes | | domain | The DNS name of peering managed zone, for instance 'example.com.' | `string` | n/a | yes | | enable\_all\_vpc\_internal\_traffic | Enable firewall policy rule to allow internal traffic (ingress and egress). | `bool` | `false` | no | | enable\_transitivity\_traffic | Enable a firewall policy rule to allow traffic between Hub and Spokes (ingress only). | `bool` | `true` | no | @@ -25,12 +24,14 @@ | project\_id | Project ID for Private Shared VPC. | `string` | n/a | yes | | secondary\_ranges | Secondary ranges that will be used in some of the subnets | `map(list(object({ range_name = string, ip_cidr_range = string })))` | `{}` | no | | subnets | The list of subnets being created |
list(object({
subnet_name = string
subnet_ip = string
subnet_region = string
subnet_private_access = optional(string, "false")
subnet_private_ipv6_access = optional(string)
subnet_flow_logs = optional(string, "false")
subnet_flow_logs_interval = optional(string, "INTERVAL_5_SEC")
subnet_flow_logs_sampling = optional(string, "0.5")
subnet_flow_logs_metadata = optional(string, "INCLUDE_ALL_METADATA")
subnet_flow_logs_filter = optional(string, "true")
subnet_flow_logs_metadata_fields = optional(list(string), [])
description = optional(string)
purpose = optional(string)
role = optional(string)
stack_type = optional(string)
ipv6_access_type = optional(string)
}))
| `[]` | no | +| target\_name\_server\_addresses | List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones. | `list(map(any))` | n/a | yes | | windows\_activation\_enabled | Enable Windows license activation for Windows workloads. | `bool` | `false` | no | ## Outputs | Name | Description | |------|-------------| +| base\_dns\_policy | The name of the DNS policy being created | | firewall\_policy | Policy created for firewall policy rules. | | network\_name | The name of the VPC being created | | network\_self\_link | The URI of the VPC being created | diff --git a/3-networks-hub-and-spoke/modules/base_shared_vpc/dns.tf b/3-networks-hub-and-spoke/modules/base_shared_vpc/dns.tf index 99a7db603..355031822 100644 --- a/3-networks-hub-and-spoke/modules/base_shared_vpc/dns.tf +++ b/3-networks-hub-and-spoke/modules/base_shared_vpc/dns.tf @@ -31,15 +31,13 @@ resource "google_dns_policy" "default_policy" { /****************************************** Creates DNS Peering to DNS HUB *****************************************/ -data "google_compute_network" "vpc_dns_hub" { - name = "vpc-net-dns" - project = var.dns_hub_project_id -} module "peering_zone" { source = "terraform-google-modules/cloud-dns/google" version = "~> 5.0" + count = var.mode == "spoke" ? 1 : 0 + project_id = var.project_id type = "peering" name = "dz-${var.environment_code}-shared-base-to-dns-hub" @@ -49,5 +47,25 @@ module "peering_zone" { private_visibility_config_networks = [ module.main.network_self_link ] - target_network = data.google_compute_network.vpc_dns_hub.self_link + target_network = data.google_compute_network.vpc_base_net_hub[0].self_link +} + +/****************************************** + DNS Forwarding +*****************************************/ +module "dns_forwarding_zone" { + source = "terraform-google-modules/cloud-dns/google" + version = "~> 5.0" + + count = var.mode != "spoke" ? 1 : 0 + + project_id = var.project_id + type = "forwarding" + name = "fz-dns-hub" + domain = var.domain + + private_visibility_config_networks = [ + module.main.network_self_link + ] + target_name_server_addresses = var.target_name_server_addresses } diff --git a/3-networks-hub-and-spoke/modules/base_shared_vpc/main.tf b/3-networks-hub-and-spoke/modules/base_shared_vpc/main.tf index c353140d2..5be4fb015 100644 --- a/3-networks-hub-and-spoke/modules/base_shared_vpc/main.tf +++ b/3-networks-hub-and-spoke/modules/base_shared_vpc/main.tf @@ -15,10 +15,13 @@ */ locals { - mode = var.mode == "hub" ? "-hub" : "-spoke" - vpc_name = "${var.environment_code}-shared-base${local.mode}" - network_name = "vpc-${local.vpc_name}" - private_googleapis_cidr = module.private_service_connect.private_service_connect_ip + mode = var.mode == null ? "" : var.mode == "hub" ? "-hub" : "-spoke" + vpc_name = "${var.environment_code}-shared-base${local.mode}" + network_name = "vpc-${local.vpc_name}" + private_googleapis_cidr = module.private_service_connect.private_service_connect_ip + google_forward_source_range = "35.199.192.0/19" + advertised_ip = var.environment_code == "c" ? [{ range = local.google_forward_source_range }, { range = local.private_googleapis_cidr }] : [{ range = local.private_googleapis_cidr }] + } /****************************************** @@ -126,7 +129,7 @@ module "region1_router1" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.private_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } @@ -142,7 +145,7 @@ module "region1_router2" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.private_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } @@ -158,7 +161,7 @@ module "region2_router1" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.private_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } @@ -174,6 +177,6 @@ module "region2_router2" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.private_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } diff --git a/3-networks-hub-and-spoke/modules/base_shared_vpc/outputs.tf b/3-networks-hub-and-spoke/modules/base_shared_vpc/outputs.tf index d7527cbc7..3d13190d7 100644 --- a/3-networks-hub-and-spoke/modules/base_shared_vpc/outputs.tf +++ b/3-networks-hub-and-spoke/modules/base_shared_vpc/outputs.tf @@ -19,6 +19,11 @@ output "network_name" { description = "The name of the VPC being created" } +output "base_dns_policy" { + value = google_dns_policy.default_policy.name + description = "The name of the DNS policy being created" +} + output "network_self_link" { value = module.main.network_self_link description = "The URI of the VPC being created" diff --git a/3-networks-hub-and-spoke/modules/base_shared_vpc/variables.tf b/3-networks-hub-and-spoke/modules/base_shared_vpc/variables.tf index 0afd5bbaa..ed45d3a9a 100644 --- a/3-networks-hub-and-spoke/modules/base_shared_vpc/variables.tf +++ b/3-networks-hub-and-spoke/modules/base_shared_vpc/variables.tf @@ -14,14 +14,14 @@ * limitations under the License. */ -variable "project_id" { - type = string - description = "Project ID for Private Shared VPC." +variable "target_name_server_addresses" { + description = "List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones." + type = list(map(any)) } -variable "dns_hub_project_id" { +variable "project_id" { type = string - description = "The DNS hub project ID" + description = "Project ID for Private Shared VPC." } variable "base_net_hub_project_id" { diff --git a/3-networks-hub-and-spoke/modules/restricted_shared_vpc/README.md b/3-networks-hub-and-spoke/modules/restricted_shared_vpc/README.md index 03b4b29e9..130845c51 100644 --- a/3-networks-hub-and-spoke/modules/restricted_shared_vpc/README.md +++ b/3-networks-hub-and-spoke/modules/restricted_shared_vpc/README.md @@ -9,7 +9,6 @@ | default\_region2 | Second subnet region. The shared vpc modules only configures two regions. | `string` | n/a | yes | | dns\_enable\_inbound\_forwarding | Toggle inbound query forwarding for VPC DNS. | `bool` | `true` | no | | dns\_enable\_logging | Toggle DNS logging for VPC DNS. | `bool` | `true` | no | -| dns\_hub\_project\_id | The DNS hub project ID | `string` | n/a | yes | | domain | The DNS name of peering managed zone, for instance 'example.com.' | `string` | n/a | yes | | egress\_policies | A list of all [egress policies](https://cloud.google.com/vpc-service-controls/docs/ingress-egress-rules#egress-rules-reference) to use in an enforced perimeter. Each list object has a `from` and `to` value that describes egress\_from and egress\_to.

Example: `[{ from={ identities=[], identity_type="ID_TYPE" }, to={ resources=[], operations={ "SRV_NAME"={ OP_TYPE=[] }}}}]`

Valid Values:
`ID_TYPE` = `null` or `IDENTITY_TYPE_UNSPECIFIED` (only allow indentities from list); `ANY_IDENTITY`; `ANY_USER_ACCOUNT`; `ANY_SERVICE_ACCOUNT`
`SRV_NAME` = "`*`" (allow all services) or [Specific Services](https://cloud.google.com/vpc-service-controls/docs/supported-products#supported_products)
`OP_TYPE` = [methods](https://cloud.google.com/vpc-service-controls/docs/supported-method-restrictions) or [permissions](https://cloud.google.com/vpc-service-controls/docs/supported-method-restrictions) |
list(object({
from = any
to = any
}))
| `[]` | no | | egress\_policies\_dry\_run | A list of all [egress policies](https://cloud.google.com/vpc-service-controls/docs/ingress-egress-rules#egress-rules-reference) to use in a dry-run perimeter. Each list object has a `from` and `to` value that describes egress\_from and egress\_to.

Example: `[{ from={ identities=[], identity_type="ID_TYPE" }, to={ resources=[], operations={ "SRV_NAME"={ OP_TYPE=[] }}}}]`

Valid Values:
`ID_TYPE` = `null` or `IDENTITY_TYPE_UNSPECIFIED` (only allow indentities from list); `ANY_IDENTITY`; `ANY_USER_ACCOUNT`; `ANY_SERVICE_ACCOUNT`
`SRV_NAME` = "`*`" (allow all services) or [Specific Services](https://cloud.google.com/vpc-service-controls/docs/supported-products#supported_products)
`OP_TYPE` = [methods](https://cloud.google.com/vpc-service-controls/docs/supported-method-restrictions) or [permissions](https://cloud.google.com/vpc-service-controls/docs/supported-method-restrictions) |
list(object({
from = any
to = any
}))
| `[]` | no | @@ -37,6 +36,7 @@ | restricted\_services\_dry\_run | List of services to restrict in a dry-run perimeter. | `list(string)` | n/a | yes | | secondary\_ranges | Secondary ranges that will be used in some of the subnets | `map(list(object({ range_name = string, ip_cidr_range = string })))` | `{}` | no | | subnets | The list of subnets being created |
list(object({
subnet_name = string
subnet_ip = string
subnet_region = string
subnet_private_access = optional(string, "false")
subnet_private_ipv6_access = optional(string)
subnet_flow_logs = optional(string, "false")
subnet_flow_logs_interval = optional(string, "INTERVAL_5_SEC")
subnet_flow_logs_sampling = optional(string, "0.5")
subnet_flow_logs_metadata = optional(string, "INCLUDE_ALL_METADATA")
subnet_flow_logs_filter = optional(string, "true")
subnet_flow_logs_metadata_fields = optional(list(string), [])
description = optional(string)
purpose = optional(string)
role = optional(string)
stack_type = optional(string)
ipv6_access_type = optional(string)
}))
| `[]` | no | +| target\_name\_server\_addresses | List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones. | `list(map(any))` | n/a | yes | | windows\_activation\_enabled | Enable Windows license activation for Windows workloads. | `bool` | `false` | no | ## Outputs @@ -53,6 +53,7 @@ | region1\_router2 | Router 2 for Region 1 | | region2\_router1 | Router 1 for Region 2 | | region2\_router2 | Router 2 for Region 2 | +| restricted\_dns\_policy | The name of the DNS policy being created | | service\_perimeter\_name | Access context manager service perimeter name for the enforced perimeter | | subnets\_ips | The IPs and CIDRs of the subnets being created | | subnets\_names | The names of the subnets being created | diff --git a/3-networks-hub-and-spoke/modules/restricted_shared_vpc/dns.tf b/3-networks-hub-and-spoke/modules/restricted_shared_vpc/dns.tf index edef23d18..e9dadbb59 100644 --- a/3-networks-hub-and-spoke/modules/restricted_shared_vpc/dns.tf +++ b/3-networks-hub-and-spoke/modules/restricted_shared_vpc/dns.tf @@ -31,15 +31,13 @@ resource "google_dns_policy" "default_policy" { /****************************************** Creates DNS Peering to DNS HUB *****************************************/ -data "google_compute_network" "vpc_dns_hub" { - name = "vpc-net-dns" - project = var.dns_hub_project_id -} module "peering_zone" { source = "terraform-google-modules/cloud-dns/google" version = "~> 5.0" + count = var.mode == "spoke" ? 1 : 0 + project_id = var.project_id type = "peering" name = "dz-${var.environment_code}-shared-restricted-to-dns-hub" @@ -49,5 +47,25 @@ module "peering_zone" { private_visibility_config_networks = [ module.main.network_self_link ] - target_network = data.google_compute_network.vpc_dns_hub.self_link + target_network = data.google_compute_network.vpc_restricted_net_hub[0].self_link +} + +/****************************************** + DNS Forwarding +*****************************************/ +module "dns_forwarding_zone" { + source = "terraform-google-modules/cloud-dns/google" + version = "~> 5.0" + + count = var.mode != "spoke" ? 1 : 0 + + project_id = var.project_id + type = "forwarding" + name = "fz-dns-hub" + domain = var.domain + + private_visibility_config_networks = [ + module.main.network_self_link + ] + target_name_server_addresses = var.target_name_server_addresses } diff --git a/3-networks-hub-and-spoke/modules/restricted_shared_vpc/main.tf b/3-networks-hub-and-spoke/modules/restricted_shared_vpc/main.tf index 2c056e53f..eeafe07bf 100644 --- a/3-networks-hub-and-spoke/modules/restricted_shared_vpc/main.tf +++ b/3-networks-hub-and-spoke/modules/restricted_shared_vpc/main.tf @@ -15,10 +15,12 @@ */ locals { - mode = var.mode == null ? "" : var.mode == "hub" ? "-hub" : "-spoke" - vpc_name = "${var.environment_code}-shared-restricted${local.mode}" - network_name = "vpc-${local.vpc_name}" - restricted_googleapis_cidr = module.private_service_connect.private_service_connect_ip + mode = var.mode == null ? "" : var.mode == "hub" ? "-hub" : "-spoke" + vpc_name = "${var.environment_code}-shared-restricted${local.mode}" + network_name = "vpc-${local.vpc_name}" + restricted_googleapis_cidr = module.private_service_connect.private_service_connect_ip + google_forward_source_range = "35.199.192.0/19" + advertised_ip = var.environment_code == "c" ? [{ range = local.google_forward_source_range }, { range = local.restricted_googleapis_cidr }] : [{ range = local.restricted_googleapis_cidr }] } /****************************************** @@ -130,7 +132,7 @@ module "region1_router1" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.restricted_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } @@ -146,7 +148,7 @@ module "region1_router2" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.restricted_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } @@ -162,7 +164,7 @@ module "region2_router1" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.restricted_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } @@ -178,6 +180,6 @@ module "region2_router2" { bgp = { asn = var.bgp_asn_subnet advertised_groups = ["ALL_SUBNETS"] - advertised_ip_ranges = [{ range = local.restricted_googleapis_cidr }] + advertised_ip_ranges = local.advertised_ip } } diff --git a/3-networks-hub-and-spoke/modules/restricted_shared_vpc/outputs.tf b/3-networks-hub-and-spoke/modules/restricted_shared_vpc/outputs.tf index 40ac84c4c..442fc44dc 100644 --- a/3-networks-hub-and-spoke/modules/restricted_shared_vpc/outputs.tf +++ b/3-networks-hub-and-spoke/modules/restricted_shared_vpc/outputs.tf @@ -19,6 +19,11 @@ output "network_name" { description = "The name of the VPC being created" } +output "restricted_dns_policy" { + value = google_dns_policy.default_policy.name + description = "The name of the DNS policy being created" +} + output "network_self_link" { value = module.main.network_self_link description = "The URI of the VPC being created" diff --git a/3-networks-hub-and-spoke/modules/restricted_shared_vpc/variables.tf b/3-networks-hub-and-spoke/modules/restricted_shared_vpc/variables.tf index 853e47bdc..4814ff734 100644 --- a/3-networks-hub-and-spoke/modules/restricted_shared_vpc/variables.tf +++ b/3-networks-hub-and-spoke/modules/restricted_shared_vpc/variables.tf @@ -14,6 +14,11 @@ * limitations under the License. */ +variable "target_name_server_addresses" { + description = "List of IPv4 address of target name servers for the forwarding zone configuration. See https://cloud.google.com/dns/docs/overview#dns-forwarding-zones for details on target name servers in the context of Cloud DNS forwarding zones." + type = list(map(any)) +} + variable "access_context_manager_policy_id" { type = number description = "The id of the default Access Context Manager policy. Can be obtained by running `gcloud access-context-manager policies list --organization YOUR_ORGANIZATION_ID --format=\"value(name)\"`." @@ -29,11 +34,6 @@ variable "project_number" { description = "Project number for Restricted Shared VPC. It is the project INSIDE the regular service perimeter." } -variable "dns_hub_project_id" { - type = string - description = "The DNS hub project ID" -} - variable "restricted_net_hub_project_id" { type = string description = "The restricted net hub project ID" diff --git a/helpers/foundation-deployer/stages/apply.go b/helpers/foundation-deployer/stages/apply.go index fd37abb48..174acb4a5 100644 --- a/helpers/foundation-deployer/stages/apply.go +++ b/helpers/foundation-deployer/stages/apply.go @@ -279,6 +279,14 @@ func DeployNetworksStage(t testing.TB, s steps.Steps, tfvars GlobalTFVars, outpu step := GetNetworkStep(c.EnableHubAndSpoke) + var localStep []string + + if c.EnableHubAndSpoke { + localStep = []string{"shared"} + } else { + localStep = []string{"shared", "production"} + } + // shared sharedTfvars := NetSharedTfvars{ TargetNameServerAddresses: tfvars.TargetNameServerAddresses, @@ -287,6 +295,14 @@ func DeployNetworksStage(t testing.TB, s steps.Steps, tfvars GlobalTFVars, outpu if err != nil { return err } + // production + productionTfvars := NetProductionTfvars{ + TargetNameServerAddresses: tfvars.TargetNameServerAddresses, + } + err = utils.WriteTfvars(filepath.Join(c.FoundationPath, step, "production.auto.tfvars"), productionTfvars) + if err != nil { + return err + } // common commonTfvars := NetCommonTfvars{ Domain: tfvars.Domain, @@ -318,15 +334,16 @@ func DeployNetworksStage(t testing.TB, s steps.Steps, tfvars GlobalTFVars, outpu Step: step, Repo: NetworksRepo, GitConf: conf, - HasManualStep: true, + HasLocalStep: true, + LocalSteps: localStep, GroupingUnits: []string{"envs"}, Envs: []string{"production", "nonproduction", "development"}, } - return deployStage(t, stageConf, s, c) } func DeployProjectsStage(t testing.TB, s steps.Steps, tfvars GlobalTFVars, outputs BootstrapOutputs, c CommonConf) error { + // shared sharedTfvars := ProjSharedTfvars{ DefaultRegion: tfvars.DefaultRegion, @@ -369,7 +386,8 @@ func DeployProjectsStage(t testing.TB, s steps.Steps, tfvars GlobalTFVars, outpu Step: ProjectsStep, Repo: ProjectsRepo, GitConf: conf, - HasManualStep: true, + HasLocalStep: true, + LocalSteps: []string{"shared"}, GroupingUnits: []string{"business_unit_1"}, Envs: []string{"production", "nonproduction", "development"}, } @@ -434,22 +452,25 @@ func deployStage(t testing.TB, sc StageConf, s steps.Steps, c CommonConf) error return err } - shared := []string{} - if sc.HasManualStep { - shared = sc.GroupingUnits + groupunit := []string{} + if sc.HasLocalStep { + groupunit = sc.GroupingUnits } - for _, bu := range shared { - buOptions := &terraform.Options{ - TerraformDir: filepath.Join(filepath.Join(c.CheckoutPath, sc.Repo), bu, "shared"), - Logger: c.Logger, - NoColor: true, - } - err := s.RunStep(fmt.Sprintf("%s.%s.apply-shared", sc.Stage, bu), func() error { - return applyLocal(t, buOptions, sc.StageSA, c.PolicyPath, c.ValidatorProject) - }) - if err != nil { - return err + for _, bu := range groupunit { + for _, localStep := range sc.LocalSteps { + buOptions := &terraform.Options{ + TerraformDir: filepath.Join(filepath.Join(c.CheckoutPath, sc.Repo), bu, localStep), + Logger: c.Logger, + NoColor: true, + } + + err := s.RunStep(fmt.Sprintf("%s.%s.apply-%s", sc.Stage, bu, localStep), func() error { + return applyLocal(t, buOptions, sc.StageSA, c.PolicyPath, c.ValidatorProject) + }) + if err != nil { + return err + } } } @@ -515,6 +536,7 @@ func copyStepCode(t testing.TB, conf utils.GitRepo, foundationPath, checkoutPath } func planStage(t testing.TB, conf utils.GitRepo, project, region, repo string) error { + err := conf.CommitFiles(fmt.Sprintf("Initialize %s repo", repo)) if err != nil { return err diff --git a/helpers/foundation-deployer/stages/data.go b/helpers/foundation-deployer/stages/data.go index 2c1ad59c3..e27639d91 100644 --- a/helpers/foundation-deployer/stages/data.go +++ b/helpers/foundation-deployer/stages/data.go @@ -63,9 +63,10 @@ type StageConf struct { Repo string CustomTargetDirPath string GitConf utils.GitRepo - HasManualStep bool + HasLocalStep bool GroupingUnits []string Envs []string + LocalSteps []string } type BootstrapOutputs struct { @@ -247,6 +248,10 @@ type NetSharedTfvars struct { TargetNameServerAddresses []ServerAddress `hcl:"target_name_server_addresses"` } +type NetProductionTfvars struct { + TargetNameServerAddresses []ServerAddress `hcl:"target_name_server_addresses"` +} + type NetAccessContextTfvars struct { AccessContextManagerPolicyID string `hcl:"access_context_manager_policy_id"` } @@ -309,7 +314,7 @@ func GetInfraPipelineOutputs(t testing.TB, checkoutPath, workspace string) Infra func ReadGlobalTFVars(file string) (GlobalTFVars, error) { var globalTfvars GlobalTFVars if file == "" { - return globalTfvars, fmt.Errorf("tfvars file is required.") + return globalTfvars, fmt.Errorf("tfvars file is required") } _, err := os.Stat(file) if os.IsNotExist(err) { diff --git a/helpers/foundation-deployer/stages/destroy.go b/helpers/foundation-deployer/stages/destroy.go index 392a2f24a..3b02873e4 100644 --- a/helpers/foundation-deployer/stages/destroy.go +++ b/helpers/foundation-deployer/stages/destroy.go @@ -120,7 +120,7 @@ func DestroyNetworksStage(t testing.TB, s steps.Steps, outputs BootstrapOutputs, CICDProject: outputs.CICDProject, Step: step, Repo: NetworksRepo, - HasManualStep: true, + HasLocalStep: true, GroupingUnits: []string{"envs"}, Envs: []string{"development", "nonproduction", "production"}, } @@ -134,7 +134,7 @@ func DestroyProjectsStage(t testing.TB, s steps.Steps, outputs BootstrapOutputs, CICDProject: outputs.CICDProject, Step: ProjectsStep, Repo: ProjectsRepo, - HasManualStep: true, + HasLocalStep: true, GroupingUnits: []string{"business_unit_1"}, Envs: []string{"development", "nonproduction", "production"}, } @@ -188,7 +188,7 @@ func destroyStage(t testing.TB, sc StageConf, s steps.Steps, c CommonConf) error } } groupingUnits := []string{} - if sc.HasManualStep { + if sc.HasLocalStep { groupingUnits = sc.GroupingUnits } for _, g := range groupingUnits { diff --git a/test/disable_tf_files.sh b/test/disable_tf_files.sh index 6b2743493..bdd22f199 100755 --- a/test/disable_tf_files.sh +++ b/test/disable_tf_files.sh @@ -23,6 +23,9 @@ function networks(){ network_dir="3-networks-hub-and-spoke" else network_dir="3-networks-dual-svpc" + + # disable production.auto.tfvars in main module # + mv $network_dir/envs/production/production.auto.tfvars $network_dir/envs/production/production.auto.tfvars.disabled fi # disable access_context.auto.tfvars in main module @@ -40,6 +43,9 @@ function shared(){ if [ "$TF_VAR_example_foundations_mode" == "HubAndSpoke" ]; then network_dir="3-networks-hub-and-spoke" + + # disable shared.auto.tfvars in main module + mv $network_dir/envs/shared/shared.auto.tfvars $network_dir/envs/shared/shared.auto.tfvars.disabled else network_dir="3-networks-dual-svpc" fi @@ -49,9 +55,6 @@ function shared(){ # disable common.auto.tfvars in main module mv $network_dir/envs/shared/common.auto.tfvars $network_dir/envs/shared/common.auto.tfvars.disabled - - # disable shared.auto.tfvars in main module - mv $network_dir/envs/shared/shared.auto.tfvars $network_dir/envs/shared/shared.auto.tfvars.disabled } function projectsshared(){ diff --git a/test/integration/networks/networks_test.go b/test/integration/networks/networks_test.go index 51fd8bc7f..b37a35682 100644 --- a/test/integration/networks/networks_test.go +++ b/test/integration/networks/networks_test.go @@ -16,6 +16,7 @@ package networks import ( "fmt" + "os" "strings" "testing" "time" @@ -51,6 +52,7 @@ func getNetworkResourceNames(envCode string, networkMode string, firewallMode st "base": { "network_name": fmt.Sprintf("vpc-%s-shared-base%s", envCode, networkMode), "global_address": fmt.Sprintf("ga-%s-shared-base%s-vpc-peering-internal", envCode, networkMode), + "dns_zone_forward": "fz-dns-hub", "dns_zone_googleapis": fmt.Sprintf("dz-%s-shared-base-apis", envCode), "dns_zone_gcr": fmt.Sprintf("dz-%s-shared-base-gcr", envCode), "dns_zone_pkg_dev": fmt.Sprintf("dz-%s-shared-base-pkg-dev", envCode), @@ -69,6 +71,7 @@ func getNetworkResourceNames(envCode string, networkMode string, firewallMode st "restricted": { "network_name": fmt.Sprintf("vpc-%s-shared-restricted%s", envCode, networkMode), "global_address": fmt.Sprintf("ga-%s-shared-restricted%s-vpc-peering-internal", envCode, networkMode), + "dns_zone_forward": "fz-dns-hub", "dns_zone_googleapis": fmt.Sprintf("dz-%s-shared-restricted-apis", envCode), "dns_zone_gcr": fmt.Sprintf("dz-%s-shared-restricted-gcr", envCode), "dns_zone_pkg_dev": fmt.Sprintf("dz-%s-shared-restricted-pkg-dev", envCode), @@ -307,14 +310,26 @@ func TestNetworks(t *testing.T) { }, } - for _, envName := range []string{ - "development", - "nonproduction", - "production", - } { + envStage := os.Getenv(utils.RUN_STAGE_ENV_VAR) + var envNames []string + + if strings.Contains(envStage, "teardown") { + envNames = []string{ + "nonproduction", + "development", + "production", + } + } else { + envNames = []string{ + "production", + "development", + "nonproduction", + } + } + + for _, envName := range envNames { envName := envName t.Run(envName, func(t *testing.T) { - t.Parallel() vars := map[string]interface{}{ "access_context_manager_policy_id": policyID, @@ -339,6 +354,9 @@ func TestNetworks(t *testing.T) { tft.WithPolicyLibraryPath("/workspace/policy-library", bootstrap.GetTFSetupStringOutput("project_id")), tft.WithBackendConfig(backendConfig), ) + + networkMode := getNetworkMode(t) + networks.DefineVerify( func(assert *assert.Assertions) { // perform default verification ensuring Terraform reports no additional changes on an applied blueprint @@ -367,15 +385,28 @@ func TestNetworks(t *testing.T) { } { projectID := networks.GetStringOutput(fmt.Sprintf("%s_host_project_id", networkType)) - for _, dnsType := range []string{ - "dns_zone_googleapis", - "dns_zone_gcr", - "dns_zone_pkg_dev", - "dns_zone_peering_zone", - } { - dnsName := networkNames[networkType][dnsType] - dnsZone := gcloud.Runf(t, "dns managed-zones describe %s --project %s --impersonate-service-account %s", dnsName, projectID, terraformSA) - assert.Equal(dnsName, dnsZone.Get("name").String(), fmt.Sprintf("dnsZone %s should exist", dnsName)) + if strings.Contains(projectID, "-p-") && networkMode != "-spoke" { + for _, dnsType := range []string{ + "dns_zone_googleapis", + "dns_zone_gcr", + "dns_zone_pkg_dev", + "dns_zone_forward", + } { + dnsName := networkNames[networkType][dnsType] + dnsZone := gcloud.Runf(t, "dns managed-zones describe %s --project %s --impersonate-service-account %s", dnsName, projectID, terraformSA) + assert.Equal(dnsName, dnsZone.Get("name").String(), fmt.Sprintf("dnsZone %s should exist", dnsName)) + } + } else { + for _, dnsType := range []string{ + "dns_zone_googleapis", + "dns_zone_gcr", + "dns_zone_pkg_dev", + "dns_zone_peering_zone", + } { + dnsName := networkNames[networkType][dnsType] + dnsZone := gcloud.Runf(t, "dns managed-zones describe %s --project %s --impersonate-service-account %s", dnsName, projectID, terraformSA) + assert.Equal(dnsName, dnsZone.Get("name").String(), fmt.Sprintf("dnsZone %s should exist", dnsName)) + } } networkName := networkNames[networkType]["network_name"] @@ -446,13 +477,27 @@ func TestNetworks(t *testing.T) { } { routerName := networkNames[networkType][router.router] + bgpAdvertisedIpRange := "35.199.192.0/19" computeRouter := gcloud.Runf(t, "compute routers describe %s --region %s --project %s --impersonate-service-account %s", routerName, router.region, projectID, terraformSA) networkSelfLink := fmt.Sprintf("https://www.googleapis.com/compute/v1/projects/%s/global/networks/%s", projectID, networkNames[networkType]["network_name"]) assert.Equal(routerName, computeRouter.Get("name").String(), fmt.Sprintf("router %s should exist", routerName)) assert.Equal("64514", computeRouter.Get("bgp.asn").String(), fmt.Sprintf("router %s should have bgp asm 64514", routerName)) - assert.Equal(1, len(computeRouter.Get("bgp.advertisedIpRanges").Array()), fmt.Sprintf("router %s should have only one advertised IP range", routerName)) - assert.Equal(googleapisCIDR[envName][networkType], computeRouter.Get("bgp.advertisedIpRanges.0.range").String(), fmt.Sprintf("router %s should have only range %s", routerName, googleapisCIDR[envName][networkType])) - assert.Equal(networkSelfLink, computeRouter.Get("network").String(), fmt.Sprintf("router %s should have be from network %s", routerName, networkNames[networkType]["network_name"])) + assert.Equal(networkSelfLink, computeRouter.Get("network").String(), fmt.Sprintf("router %s should be on network %s", routerName, networkNames[networkType]["network_name"])) + assert.Contains(googleapisCIDR[envName][networkType], computeRouter.Get("bgp.advertisedIpRanges.1.range").String(), fmt.Sprintf("router %s should have range %s", routerName, googleapisCIDR[envName][networkType])) + + if strings.Contains(projectID, "prj-p") && networkMode != "-spoke" { + advertisedIpRanges := computeRouter.Get("bgp.advertisedIpRanges").Array() + found := false + for _, ipRange := range advertisedIpRanges { + if ipRange.Get("range").String() == bgpAdvertisedIpRange { + found = true + break + } + } + assert.True(found, fmt.Sprintf("router %s should have range %s", routerName, bgpAdvertisedIpRange)) + assert.True(found, fmt.Sprintf("router %s should have range %s", routerName, googleapisCIDR[envName][networkType])) + } + } } } diff --git a/test/integration/org/org_test.go b/test/integration/org/org_test.go index 927783abb..7cae2023e 100644 --- a/test/integration/org/org_test.go +++ b/test/integration/org/org_test.go @@ -442,16 +442,6 @@ func TestOrg(t *testing.T) { "securitycenter.googleapis.com", }, }, - { - output: "dns_hub_project_id", - apis: []string{ - "compute.googleapis.com", - "dns.googleapis.com", - "servicenetworking.googleapis.com", - "logging.googleapis.com", - "cloudresourcemanager.googleapis.com", - }, - }, } { projectID := org.GetStringOutput(projectOutput.output) prj := gcloud.Runf(t, "projects describe %s", projectID) diff --git a/test/integration/shared/shared_test.go b/test/integration/shared/shared_test.go index 8102b7163..6f7d21f9d 100644 --- a/test/integration/shared/shared_test.go +++ b/test/integration/shared/shared_test.go @@ -78,81 +78,144 @@ func TestShared(t *testing.T) { // do a time.Sleep to wait for propagation of VPC Service Controls configuration in the Hub and Spoke network mode if isHubAndSpokeMode(t) { time.Sleep(60 * time.Second) - } - - // perform default verification ensuring Terraform reports no additional changes on an applied blueprint - // Comment DefaultVerify because proxy-only subnets tries to change `ipv6_access_type` from `INTERNAL` to `null` on every run (plan and apply) - // Module issue: https://github.com/terraform-google-modules/terraform-google-network/issues/528 - // Resource issue: https://github.com/hashicorp/terraform-provider-google/issues/16801 - // Resource issue: https://github.com/hashicorp/terraform-provider-google/issues/16804 - // shared.DefaultVerify(assert) - - projectID := shared.GetStringOutput("dns_hub_project_id") - networkName := "vpc-net-dns" - dnsHubNetworkUrl := fmt.Sprintf("https://www.googleapis.com/compute/v1/projects/%s/global/networks/vpc-net-dns", projectID) - dnsPolicyName := "dp-dns-hub-default-policy" - - dnsPolicy := gcloud.Runf(t, "dns policies describe %s --project %s", dnsPolicyName, projectID) - assert.True(dnsPolicy.Get("enableInboundForwarding").Bool(), fmt.Sprintf("dns policy %s should have inbound forwarding enabled", dnsPolicyName)) - assert.Equal(dnsHubNetworkUrl, dnsPolicy.Get("networks.0.networkUrl").String(), fmt.Sprintf("dns policy %s should be on network %s", dnsPolicyName, networkName)) - - dnsFwZoneName := "fz-dns-hub" - dnsZone := gcloud.Runf(t, "dns managed-zones describe %s --project %s", dnsFwZoneName, projectID) - assert.Equal(dnsFwZoneName, dnsZone.Get("name").String(), fmt.Sprintf("dnsZone %s should exist", dnsFwZoneName)) - - projectNetwork := gcloud.Runf(t, "compute networks describe %s --project %s", networkName, projectID) - assert.Equal(networkName, projectNetwork.Get("name").String(), fmt.Sprintf("network %s should exist", networkName)) - - for _, subnet := range []struct { - name string - cidrRange string - region string - }{ - { - name: "sb-net-dns-us-west1", - cidrRange: "172.16.0.128/25", - region: "us-west1", - }, - { - name: "sb-net-dns-us-central1", - cidrRange: "172.16.0.0/25", - region: "us-central1", - }, - } { - sub := gcloud.Runf(t, "compute networks subnets describe %s --region %s --project %s", subnet.name, subnet.region, projectID) - assert.Equal(subnet.name, sub.Get("name").String(), fmt.Sprintf("subnet %s should exist", subnet.name)) - assert.Equal(subnet.cidrRange, sub.Get("ipCidrRange").String(), fmt.Sprintf("IP CIDR range %s should be", subnet.cidrRange)) - } - bgpAdvertisedIpRange := "35.199.192.0/19" - - for _, router := range []struct { - name string - region string - }{ - { - name: "cr-net-dns-us-central1-cr1", - region: "us-central1", - }, - { - name: "cr-net-dns-us-central1-cr2", - region: "us-central1", - }, - { - name: "cr-net-dns-us-west1-cr3", - region: "us-west1", - }, - { - name: "cr-net-dns-us-west1-cr4", - region: "us-west1", - }, - } { - computeRouter := gcloud.Runf(t, "compute routers describe %s --region %s --project %s", router.name, router.region, projectID) - assert.Equal(router.name, computeRouter.Get("name").String(), fmt.Sprintf("router %s should exist", router.name)) - assert.Equal("64667", computeRouter.Get("bgp.asn").String(), fmt.Sprintf("router %s should have bgp asm 64667", router.name)) - assert.Equal(1, len(computeRouter.Get("bgp.advertisedIpRanges").Array()), fmt.Sprintf("router %s should have only one advertised IP range", router.name)) - assert.Equal(bgpAdvertisedIpRange, computeRouter.Get("bgp.advertisedIpRanges.0.range").String(), fmt.Sprintf("router %s should have only range %s", router.name, bgpAdvertisedIpRange)) - assert.Equal(dnsHubNetworkUrl, computeRouter.Get("network").String(), fmt.Sprintf("router %s should have be from network vpc-net-dns", router.name)) + // perform default verification ensuring Terraform reports no additional changes on an applied blueprint + // Comment DefaultVerify because proxy-only subnets tries to change `ipv6_access_type` from `INTERNAL` to `null` on every run (plan and apply) + // Module issue: https://github.com/terraform-google-modules/terraform-google-network/issues/528 + // Resource issue: https://github.com/hashicorp/terraform-provider-google/issues/16801 + // Resource issue: https://github.com/hashicorp/terraform-provider-google/issues/16804 + // shared.DefaultVerify(assert) + + dnsFwZoneName := "fz-dns-hub" + bgpAdvertisedIpRange := "35.199.192.0/19" + + baseProjectID := shared.GetStringOutput("base_host_project_id") + baseNetworkName := shared.GetStringOutput("base_network_name") + baseDNSPolicyName := shared.GetStringOutput("base_dns_policy") + baseDNSHubNetworkUrl := fmt.Sprintf("https://www.googleapis.com/compute/v1/projects/%s/global/networks/%s", baseProjectID, baseNetworkName) + + baseDNSPolicy := gcloud.Runf(t, "dns policies describe %s --project %s", baseDNSPolicyName, baseProjectID) /////// + assert.True(baseDNSPolicy.Get("enableInboundForwarding").Bool(), fmt.Sprintf("dns policy %s should have inbound forwarding enabled", baseDNSPolicyName)) + assert.Equal(baseDNSHubNetworkUrl, baseDNSPolicy.Get("networks.0.networkUrl").String(), fmt.Sprintf("dns policy %s should be on network %s", baseDNSPolicyName, baseNetworkName)) + + baseDNSZone := gcloud.Runf(t, "dns managed-zones describe %s --project %s", dnsFwZoneName, baseProjectID) + assert.Equal(dnsFwZoneName, baseDNSZone.Get("name").String(), fmt.Sprintf("baseDNSZone %s should exist", dnsFwZoneName)) // + + baseProjectNetwork := gcloud.Runf(t, "compute networks describe %s --project %s", baseNetworkName, baseProjectID) + assert.Equal(baseNetworkName, baseProjectNetwork.Get("name").String(), fmt.Sprintf("network %s should exist", baseNetworkName)) + + for _, subnet := range []struct { + name string + cidrRange string + region string + }{ + { + name: "sb-c-shared-base-hub-us-west1", + cidrRange: "10.1.0.0/18", + region: "us-west1", + }, + { + name: "sb-c-shared-base-hub-us-central1", + cidrRange: "10.0.0.0/18", + region: "us-central1", + }, + } { + baseSubnet := gcloud.Runf(t, "compute networks subnets describe %s --region %s --project %s", subnet.name, subnet.region, baseProjectID) + assert.Equal(subnet.name, baseSubnet.Get("name").String(), fmt.Sprintf("subnet %s should exist", subnet.name)) + assert.Equal(subnet.cidrRange, baseSubnet.Get("ipCidrRange").String(), fmt.Sprintf("IP CIDR range %s should be", subnet.cidrRange)) + } + + for _, router := range []struct { + name string + region string + }{ + { + name: "cr-c-shared-base-hub-us-central1-cr1", + region: "us-central1", + }, + { + name: "cr-c-shared-base-hub-us-central1-cr2", + region: "us-central1", + }, + { + name: "cr-c-shared-base-hub-us-west1-cr3", + region: "us-west1", + }, + { + name: "cr-c-shared-base-hub-us-west1-cr4", + region: "us-west1", + }, + } { + baseComputeRouter := gcloud.Runf(t, "compute routers describe %s --region %s --project %s", router.name, router.region, baseProjectID) + assert.Equal(router.name, baseComputeRouter.Get("name").String(), fmt.Sprintf("router %s should exist", router.name)) + assert.Equal("64514", baseComputeRouter.Get("bgp.asn").String(), fmt.Sprintf("router %s should have bgp asm 64514", router.name)) + assert.Equal(bgpAdvertisedIpRange, baseComputeRouter.Get("bgp.advertisedIpRanges.0.range").String(), fmt.Sprintf("router %s should have range %s", router.name, bgpAdvertisedIpRange)) + assert.Equal(baseDNSHubNetworkUrl, baseComputeRouter.Get("network").String(), fmt.Sprintf("router %s should be on network vpc-c-shared-base-hub", router.name)) + } + + restrictedProjectID := shared.GetStringOutput("restricted_host_project_id") + restrictedNetworkName := shared.GetStringOutput("restricted_network_name") + restrictedDNSPolicyName := shared.GetStringOutput("restricted_dns_policy") + restrictedDNSHubNetworkUrl := fmt.Sprintf("https://www.googleapis.com/compute/v1/projects/%s/global/networks/%s", restrictedProjectID, restrictedNetworkName) + + restrictedDNSPolicy := gcloud.Runf(t, "dns policies describe %s --project %s", restrictedDNSPolicyName, restrictedProjectID) + assert.True(restrictedDNSPolicy.Get("enableInboundForwarding").Bool(), fmt.Sprintf("dns policy %s should have inbound forwarding enabled", restrictedDNSPolicyName)) + assert.Equal(restrictedDNSHubNetworkUrl, restrictedDNSPolicy.Get("networks.0.networkUrl").String(), fmt.Sprintf("dns policy %s should be on network %s", restrictedDNSPolicyName, restrictedNetworkName)) + + restrictedDNSZone := gcloud.Runf(t, "dns managed-zones describe %s --project %s", dnsFwZoneName, restrictedProjectID) + assert.Equal(dnsFwZoneName, restrictedDNSZone.Get("name").String(), fmt.Sprintf("restrictedDNSZone %s should exist", dnsFwZoneName)) + + restrictedProjectNetwork := gcloud.Runf(t, "compute networks describe %s --project %s", restrictedNetworkName, restrictedProjectID) + assert.Equal(restrictedNetworkName, restrictedProjectNetwork.Get("name").String(), fmt.Sprintf("network %s should exist", restrictedNetworkName)) + + for _, subnet := range []struct { + name string + cidrRange string + region string + }{ + { + name: "sb-c-shared-restricted-hub-us-west1", + cidrRange: "10.9.0.0/18", + region: "us-west1", + }, + { + name: "sb-c-shared-restricted-hub-us-central1", + cidrRange: "10.8.0.0/18", + region: "us-central1", + }, + } { + restrictedSubnet := gcloud.Runf(t, "compute networks subnets describe %s --region %s --project %s", subnet.name, subnet.region, restrictedProjectID) + assert.Equal(subnet.name, restrictedSubnet.Get("name").String(), fmt.Sprintf("subnet %s should exist", subnet.name)) + assert.Equal(subnet.cidrRange, restrictedSubnet.Get("ipCidrRange").String(), fmt.Sprintf("IP CIDR range %s should be", subnet.cidrRange)) + } + + for _, router := range []struct { + name string + region string + }{ + { + name: "cr-c-shared-restricted-hub-us-central1-cr5", + region: "us-central1", + }, + { + name: "cr-c-shared-restricted-hub-us-central1-cr6", + region: "us-central1", + }, + { + name: "cr-c-shared-restricted-hub-us-west1-cr7", + region: "us-west1", + }, + { + name: "cr-c-shared-restricted-hub-us-west1-cr8", + region: "us-west1", + }, + } { + restrictedComputeRouter := gcloud.Runf(t, "compute routers describe %s --region %s --project %s", router.name, router.region, restrictedProjectID) + assert.Equal(router.name, restrictedComputeRouter.Get("name").String(), fmt.Sprintf("router %s should exist", router.name)) + assert.Equal("64514", restrictedComputeRouter.Get("bgp.asn").String(), fmt.Sprintf("router %s should have bgp asm 64514", router.name)) + assert.Equal(bgpAdvertisedIpRange, restrictedComputeRouter.Get("bgp.advertisedIpRanges.0.range").String(), fmt.Sprintf("router %s should have range %s", router.name, bgpAdvertisedIpRange)) + assert.Equal(restrictedDNSHubNetworkUrl, restrictedComputeRouter.Get("network").String(), fmt.Sprintf("router %s should be on network vpc-c-shared-restricted-hub", router.name)) + } } }) shared.Test() diff --git a/test/integration/testutils/retry.go b/test/integration/testutils/retry.go index e50bc2a45..67c05bb19 100644 --- a/test/integration/testutils/retry.go +++ b/test/integration/testutils/retry.go @@ -42,5 +42,8 @@ var ( // Error 400: Service account {} does not exist. ".*Error 400.*Service account.*does not exist*": "Error setting IAM policy", + + // Error waiting for creating service network connection. This happens randomly for development, production and non-production environments + ".*Error code 16.*Error waiting for Create Service Networking Connection*": "Request had invalid authentication credentials", } ) diff --git a/test/restore_tf_files.sh b/test/restore_tf_files.sh index 4a71bfa9e..74d530c13 100644 --- a/test/restore_tf_files.sh +++ b/test/restore_tf_files.sh @@ -35,6 +35,9 @@ function networks(){ network_dir="3-networks-hub-and-spoke" else network_dir="3-networks-dual-svpc" + + # disable shared.auto.tfvars in main module # + mv $network_dir/envs/production/production.auto.tfvars.disabled $network_dir/envs/production/production.auto.tfvars fi # restore backend configs in main module @@ -57,6 +60,9 @@ function shared(){ if [ "$TF_VAR_example_foundations_mode" == "HubAndSpoke" ]; then network_dir="3-networks-hub-and-spoke" + + # restore shared.auto.tfvars in main module + mv $network_dir/envs/shared/shared.auto.tfvars.disabled $network_dir/envs/shared/shared.auto.tfvars else network_dir="3-networks-dual-svpc" fi @@ -69,9 +75,6 @@ function shared(){ # restore common.auto.tfvars in main module mv $network_dir/envs/shared/common.auto.tfvars.disabled $network_dir/envs/shared/common.auto.tfvars - - # restore shared.auto.tfvars in main module - mv $network_dir/envs/shared/shared.auto.tfvars.disabled $network_dir/envs/shared/shared.auto.tfvars } function projects(){