Merge branch 'master' into lcaggioni(data-platform-svpc-members
This commit is contained in:
commit
902e8a24fa
|
@ -12,6 +12,7 @@ All notable changes to this project will be documented in this file.
|
|||
- **incompatible change** the variable for service identities IAM has changed in the project factory
|
||||
- the `net-vpc` and `project` modules now use the beta provider for shared VPC-related resources
|
||||
- add `data-catalog-policy-tag` module
|
||||
- **incompatible change** the `psn_ranges` variable has been renamed to `psa_ranges` in the `net-vpc` module and its type changed from `list(string)` to `map(string)`
|
||||
|
||||
## [13.0.0] - 2022-01-27
|
||||
|
||||
|
|
|
@ -77,7 +77,7 @@ module "branch-teams-team-dev-folder" {
|
|||
for_each = coalesce(var.team_folders, {})
|
||||
parent = module.branch-teams-team-folder[each.key].id
|
||||
# naming: environment descriptive name
|
||||
name = "${module.branch-teams-team-folder[each.key].name} - Development"
|
||||
name = "Development"
|
||||
# environment-wide human permissions on the whole teams environment
|
||||
group_iam = {}
|
||||
iam = {
|
||||
|
@ -127,7 +127,7 @@ module "branch-teams-team-prod-folder" {
|
|||
for_each = coalesce(var.team_folders, {})
|
||||
parent = module.branch-teams-team-folder[each.key].id
|
||||
# naming: environment descriptive name
|
||||
name = "${module.branch-teams-team-folder[each.key].name} - Production"
|
||||
name = "Production"
|
||||
# environment-wide human permissions on the whole teams environment
|
||||
group_iam = {}
|
||||
iam = {
|
||||
|
|
|
@ -353,8 +353,8 @@ Don't forget to add a peering zone in the landing project and point it to the ne
|
|||
| [monitoring.tf](./monitoring.tf) | Network monitoring dashboards. | | <code>google_monitoring_dashboard</code> |
|
||||
| [nva.tf](./nva.tf) | None | <code>compute-mig</code> · <code>compute-vm</code> · <code>net-ilb</code> | |
|
||||
| [outputs.tf](./outputs.tf) | Module outputs. | | <code>local_file</code> |
|
||||
| [spoke-dev.tf](./spoke-dev.tf) | Dev spoke VPC and related resources. | <code>net-address</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>net-vpc-peering</code> · <code>project</code> | |
|
||||
| [spoke-prod.tf](./spoke-prod.tf) | Production spoke VPC and related resources. | <code>net-address</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>net-vpc-peering</code> · <code>project</code> | |
|
||||
| [spoke-dev.tf](./spoke-dev.tf) | Dev spoke VPC and related resources. | <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>net-vpc-peering</code> · <code>project</code> | |
|
||||
| [spoke-prod.tf](./spoke-prod.tf) | Production spoke VPC and related resources. | <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>net-vpc-peering</code> · <code>project</code> | |
|
||||
| [test-resources.tf](./test-resources.tf) | temporary instances for testing | <code>compute-vm</code> | |
|
||||
| [variables.tf](./variables.tf) | Module variables. | | |
|
||||
| [vpn-onprem.tf](./vpn-onprem.tf) | VPN between landing and onprem. | <code>net-vpn-ha</code> | |
|
||||
|
|
|
@ -50,6 +50,7 @@ module "dev-spoke-vpc" {
|
|||
mtu = 1500
|
||||
data_folder = "${var.data_dir}/subnets/dev"
|
||||
delete_default_routes_on_create = true
|
||||
psa_ranges = var.psa_ranges.dev
|
||||
subnets_l7ilb = local.l7ilb_subnets.dev
|
||||
# Set explicit routes for googleapis; send everything else to NVAs
|
||||
routes = {
|
||||
|
@ -110,17 +111,6 @@ module "dev-spoke-firewall" {
|
|||
cidr_template_file = "${var.data_dir}/cidrs.yaml"
|
||||
}
|
||||
|
||||
module "dev-spoke-psa-addresses" {
|
||||
source = "../../../modules/net-address"
|
||||
project_id = module.dev-spoke-project.project_id
|
||||
psa_addresses = { for r, v in var.psa_ranges.dev : r => {
|
||||
address = cidrhost(v, 0)
|
||||
network = module.dev-spoke-vpc.self_link
|
||||
prefix_length = split("/", v)[1]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
module "peering-dev" {
|
||||
source = "../../../modules/net-vpc-peering"
|
||||
prefix = "dev-peering-0"
|
||||
|
|
|
@ -50,6 +50,7 @@ module "prod-spoke-vpc" {
|
|||
mtu = 1500
|
||||
data_folder = "${var.data_dir}/subnets/prod"
|
||||
delete_default_routes_on_create = true
|
||||
psa_ranges = var.psa_ranges.prod
|
||||
subnets_l7ilb = local.l7ilb_subnets.prod
|
||||
# Set explicit routes for googleapis; send everything else to NVAs
|
||||
routes = {
|
||||
|
@ -110,17 +111,6 @@ module "prod-spoke-firewall" {
|
|||
cidr_template_file = "${var.data_dir}/cidrs.yaml"
|
||||
}
|
||||
|
||||
module "prod-spoke-psa-addresses" {
|
||||
source = "../../../modules/net-address"
|
||||
project_id = module.prod-spoke-project.project_id
|
||||
psa_addresses = { for r, v in var.psa_ranges.prod : r => {
|
||||
address = cidrhost(v, 0)
|
||||
network = module.prod-spoke-vpc.self_link
|
||||
prefix_length = split("/", v)[1]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
module "peering-prod" {
|
||||
source = "../../../modules/net-vpc-peering"
|
||||
prefix = "prod-peering-0"
|
||||
|
|
|
@ -296,8 +296,8 @@ DNS configurations are centralised in the `dns.tf` file. Spokes delegate DNS res
|
|||
| [main.tf](./main.tf) | Networking folder and hierarchical policy. | <code>folder</code> | |
|
||||
| [monitoring.tf](./monitoring.tf) | Network monitoring dashboards. | | <code>google_monitoring_dashboard</code> |
|
||||
| [outputs.tf](./outputs.tf) | Module outputs. | | <code>local_file</code> |
|
||||
| [spoke-dev.tf](./spoke-dev.tf) | Dev spoke VPC and related resources. | <code>net-address</code> · <code>net-cloudnat</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>project</code> | <code>google_project_iam_binding</code> |
|
||||
| [spoke-prod.tf](./spoke-prod.tf) | Production spoke VPC and related resources. | <code>net-address</code> · <code>net-cloudnat</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>project</code> | <code>google_project_iam_binding</code> |
|
||||
| [spoke-dev.tf](./spoke-dev.tf) | Dev spoke VPC and related resources. | <code>net-cloudnat</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>project</code> | <code>google_project_iam_binding</code> |
|
||||
| [spoke-prod.tf](./spoke-prod.tf) | Production spoke VPC and related resources. | <code>net-cloudnat</code> · <code>net-vpc</code> · <code>net-vpc-firewall</code> · <code>project</code> | <code>google_project_iam_binding</code> |
|
||||
| [test-resources.tf](./test-resources.tf) | temporary instances for testing | <code>compute-vm</code> | |
|
||||
| [variables.tf](./variables.tf) | Module variables. | | |
|
||||
| [vpn-onprem.tf](./vpn-onprem.tf) | VPN between landing and onprem. | <code>net-vpn-ha</code> | |
|
||||
|
|
|
@ -52,6 +52,7 @@ module "dev-spoke-vpc" {
|
|||
name = "dev-spoke-0"
|
||||
mtu = 1500
|
||||
data_folder = "${var.data_dir}/subnets/dev"
|
||||
psa_ranges = var.psa_ranges.dev
|
||||
subnets_l7ilb = local.l7ilb_subnets.dev
|
||||
# set explicit routes for googleapis in case the default route is deleted
|
||||
routes = {
|
||||
|
@ -96,17 +97,6 @@ module "dev-spoke-cloudnat" {
|
|||
logging_filter = "ERRORS_ONLY"
|
||||
}
|
||||
|
||||
module "dev-spoke-psa-addresses" {
|
||||
source = "../../../modules/net-address"
|
||||
project_id = module.dev-spoke-project.project_id
|
||||
psa_addresses = { for r, v in var.psa_ranges.dev : r => {
|
||||
address = cidrhost(v, 0)
|
||||
network = module.dev-spoke-vpc.self_link
|
||||
prefix_length = split("/", v)[1]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
# Create delegated grants for stage3 service accounts
|
||||
resource "google_project_iam_binding" "dev_spoke_project_iam_delegated" {
|
||||
project = module.dev-spoke-project.project_id
|
||||
|
|
|
@ -52,6 +52,7 @@ module "prod-spoke-vpc" {
|
|||
name = "prod-spoke-0"
|
||||
mtu = 1500
|
||||
data_folder = "${var.data_dir}/subnets/prod"
|
||||
psa_ranges = var.psa_ranges.prod
|
||||
subnets_l7ilb = local.l7ilb_subnets.prod
|
||||
# set explicit routes for googleapis in case the default route is deleted
|
||||
routes = {
|
||||
|
@ -96,17 +97,6 @@ module "prod-spoke-cloudnat" {
|
|||
logging_filter = "ERRORS_ONLY"
|
||||
}
|
||||
|
||||
module "prod-spoke-psa-addresses" {
|
||||
source = "../../../modules/net-address"
|
||||
project_id = module.prod-spoke-project.project_id
|
||||
psa_addresses = { for r, v in var.psa_ranges.prod : r => {
|
||||
address = cidrhost(v, 0)
|
||||
network = module.prod-spoke-vpc.self_link
|
||||
prefix_length = split("/", v)[1]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
# Create delegated grants for stage3 service accounts
|
||||
resource "google_project_iam_binding" "prod_spoke_project_iam_delegated" {
|
||||
project = module.prod-spoke-project.project_id
|
||||
|
|
|
@ -3,4 +3,4 @@
|
|||
The Project Factory (PF) builds on top of your foundations to create and set up projects (and related resources) to be used for your workloads.
|
||||
It is organized in folders representing environments (e.g. "dev", "prod"), each implemented by a stand-alone terraform [resource factory](https://medium.com/google-cloud/resource-factories-a-descriptive-approach-to-terraform-581b3ebb59c).
|
||||
|
||||
This directory contains a single project factory ([`prod/`](./prod/)) as an example - to implement multiple environments (e.g. "prod" and "dev") you'll need to copy the `prod` folder into one folder per environment, then customize each one following the instructions found in [`prod/README.md`](./prod/README.md).
|
||||
This directory contains a single project factory ([`dev/`](./dev/)) as an example - to implement multiple environments (e.g. "prod" and "dev") you'll need to copy the `dev` folder into one folder per environment, then customize each one following the instructions found in [`dev/README.md`](./dev/README.md).
|
||||
|
|
|
@ -49,7 +49,7 @@ It's of course possible to run this stage in isolation, by making sure the archi
|
|||
- `"roles/compute.viewer"`
|
||||
- `"roles/dns.admin"`
|
||||
- If networking is used (e.g., for VMs, GKE Clusters or AppEngine flex), VPC Host projects and their subnets should exist when creating projects
|
||||
- If per-environment DNS sub-zones are required, one "root" zone per environment should exist when creating projects (e.g., prod.gcp.example.com.)
|
||||
- If per-environment DNS sub-zones are required, one "root" zone per environment should exist when creating projects (e.g., dev.gcp.example.com.)
|
||||
|
||||
### Providers configuration
|
||||
|
||||
|
@ -57,8 +57,8 @@ If you're running this on top of Fast, you should run the following commands to
|
|||
|
||||
```bash
|
||||
# Variable `outputs_location` is set to `../../../config` in stage 01-resman
|
||||
$ cd fabric-fast/stages/03-project-factory/prod
|
||||
ln -s ../../../config/03-project-factory-prod/providers.tf
|
||||
$ cd fabric-fast/stages/03-project-factory/dev
|
||||
ln -s ../../../config/03-project-factory-dev/providers.tf
|
||||
```
|
||||
|
||||
### Variable configuration
|
||||
|
@ -74,16 +74,16 @@ If you configured a valid path for `outputs_location` in the bootstrap and netwo
|
|||
|
||||
```bash
|
||||
# Variable `outputs_location` is set to `../../../config` in stages 01-bootstrap and the 02-networking stage in use
|
||||
ln -s ../../../config/03-project-factory-prod/terraform-bootstrap.auto.tfvars.json
|
||||
ln -s ../../../config/03-project-factory-prod/terraform-networking.auto.tfvars.json
|
||||
ln -s ../../../config/03-project-factory-dev/terraform-bootstrap.auto.tfvars.json
|
||||
ln -s ../../../config/03-project-factory-dev/terraform-networking.auto.tfvars.json
|
||||
```
|
||||
|
||||
If you're not using Fast, refer to the [Variables](#variables) table at the bottom of this document for a full list of variables, their origin (e.g., a stage or specific to this one), and descriptions explaining their meaning.
|
||||
|
||||
Besides the values above, a project factory takes 2 additional inputs:
|
||||
|
||||
- `data/defaults.yaml`, manually configured by adapting the [`prod/data/defaults.yaml.sample`](./prod/data/defaults.yaml.sample), which defines per-environment default values e.g., for billing alerts and labels.
|
||||
- `data/projects/*.yaml`, one file per project (optionally grouped in folders), which configures each project. A [`prod/data/projects/project.yaml.sample`](./prod/data/projects/project.yaml.sample) is provided as reference and documentation for the schema. Projects will be named after the filename, e.g., `fast-prod-lab0.yaml` will create project `fast-prod-lab0`.
|
||||
- `data/defaults.yaml`, manually configured by adapting the [`data/defaults.yaml`](./data/defaults.yaml), which defines per-environment default values e.g., for billing alerts and labels.
|
||||
- `data/projects/*.yaml`, one file per project (optionally grouped in folders), which configures each project. A [`data/projects/project.yaml`](./data/projects/project.yaml) is provided as reference and documentation for the schema. Projects will be named after the filename, e.g., `fast-dev-lab0.yaml` will create project `fast-dev-lab0`.
|
||||
|
||||
Once the configuration is complete, run the project factory by running
|
||||
|
|
@ -15,7 +15,7 @@ essential_contacts: ["team-contacts@example.com"]
|
|||
|
||||
# [opt] Labels set for all projects
|
||||
labels:
|
||||
environment: prod
|
||||
environment: dev
|
||||
department: accounting
|
||||
application: example-app
|
||||
foo: bar
|
|
@ -44,7 +44,7 @@ kms_service_agents:
|
|||
|
||||
# [opt] Labels for the project - merged with the ones defined in defaults
|
||||
labels:
|
||||
environment: prod
|
||||
environment: dev
|
||||
|
||||
# [opt] Org policy overrides defined at project level
|
||||
org_policies:
|
||||
|
@ -56,7 +56,7 @@ org_policies:
|
|||
status: true
|
||||
suggested_value: null
|
||||
values:
|
||||
- projects/fast-prod-iac-core-0
|
||||
- projects/fast-dev-iac-core-0
|
||||
|
||||
# [opt] Service account to create for the project and their roles on the project
|
||||
# in name => [roles] format
|
||||
|
@ -90,11 +90,11 @@ vpc:
|
|||
enable_security_admin: true
|
||||
|
||||
# Host project the project will be service project of
|
||||
host_project: fast-prod-net-spoke-0
|
||||
host_project: fast-dev-net-spoke-0
|
||||
|
||||
# [opt] Subnets in the host project where principals will be granted networkUser
|
||||
# in region/subnet-name => [principals]
|
||||
subnets_iam:
|
||||
europe-west1/prod-default-ew1:
|
||||
europe-west1/dev-default-ew1:
|
||||
- user:foobar@example.com
|
||||
- serviceAccount:service-account1
|
Before Width: | Height: | Size: 56 KiB After Width: | Height: | Size: 56 KiB |
Before Width: | Height: | Size: 590 KiB After Width: | Height: | Size: 590 KiB |
|
@ -25,7 +25,7 @@ module "vpc" {
|
|||
source = "./modules/net-vpc"
|
||||
project_id = module.project.project_id
|
||||
name = "my-network"
|
||||
psn_ranges = ["10.60.0.0/16"]
|
||||
psa_ranges = {cloudsql-ew1-0="10.60.0.0/16"}
|
||||
}
|
||||
|
||||
module "db" {
|
||||
|
|
|
@ -61,7 +61,7 @@ module "folder" {
|
|||
policy_name = null
|
||||
rules_file = "data/rules.yaml"
|
||||
}
|
||||
firewall_policy_attachments = {
|
||||
firewall_policy_association = {
|
||||
factory-policy = module.folder.firewall_policy_id["factory"]
|
||||
}
|
||||
}
|
||||
|
|
|
@ -138,7 +138,7 @@ module "vpc" {
|
|||
secondary_ip_range = null
|
||||
}
|
||||
]
|
||||
psn_ranges = ["10.10.0.0/16"]
|
||||
psa_ranges = {range-a = "10.10.0.0/16"}
|
||||
}
|
||||
# tftest modules=1 resources=4
|
||||
```
|
||||
|
@ -171,8 +171,8 @@ module "vpc" {
|
|||
```
|
||||
|
||||
### Subnet Factory
|
||||
The `net-vpc` module includes a subnet factory (see [Resource Factories](../../examples/factories/)) for the massive creation of subnets leveraging one configuration file per subnet.
|
||||
|
||||
The `net-vpc` module includes a subnet factory (see [Resource Factories](../../examples/factories/)) for the massive creation of subnets leveraging one configuration file per subnet.
|
||||
|
||||
```hcl
|
||||
module "vpc" {
|
||||
|
@ -220,7 +220,7 @@ flow_logs: # enable, set to empty map to use defaults
|
|||
| [mtu](variables.tf#L80) | Maximum Transmission Unit in bytes. The minimum value for this field is 1460 and the maximum value is 1500 bytes. | <code></code> | | <code>null</code> |
|
||||
| [peering_config](variables.tf#L90) | VPC peering configuration. | <code title="object({ peer_vpc_self_link = string export_routes = bool import_routes = bool })">object({…})</code> | | <code>null</code> |
|
||||
| [peering_create_remote_end](variables.tf#L100) | Skip creation of peering on the remote end when using peering_config. | <code>bool</code> | | <code>true</code> |
|
||||
| [psn_ranges](variables.tf#L111) | CIDR ranges used for Google services that support Private Service Networking. | <code>list(string)</code> | | <code>null</code> |
|
||||
| [psa_ranges](variables.tf#L111) | CIDR ranges used for Google services that support Private Service Networking. | <code>map(string)</code> | | <code>null</code> |
|
||||
| [routes](variables.tf#L124) | Network routes, keyed by name. | <code title="map(object({ dest_range = string priority = number tags = list(string) next_hop_type = string # gateway, instance, ip, vpn_tunnel, ilb next_hop = string }))">map(object({…}))</code> | | <code>{}</code> |
|
||||
| [routing_mode](variables.tf#L136) | The network routing mode (default 'GLOBAL'). | <code>string</code> | | <code>"GLOBAL"</code> |
|
||||
| [shared_vpc_host](variables.tf#L146) | Enable shared VPC for this project. | <code>bool</code> | | <code>false</code> |
|
||||
|
|
|
@ -78,11 +78,11 @@ locals {
|
|||
? null
|
||||
: element(reverse(split("/", var.peering_config.peer_vpc_self_link)), 0)
|
||||
)
|
||||
psn_ranges = {
|
||||
for r in(var.psn_ranges == null ? [] : var.psn_ranges) : r => {
|
||||
address = split("/", r)[0]
|
||||
name = replace(split("/", r)[0], ".", "-")
|
||||
prefix_length = split("/", r)[1]
|
||||
psa_ranges = {
|
||||
for k, v in coalesce(var.psa_ranges, {}) : k => {
|
||||
address = split("/", v)[0]
|
||||
name = k
|
||||
prefix_length = split("/", v)[1]
|
||||
}
|
||||
}
|
||||
routes = {
|
||||
|
@ -328,10 +328,10 @@ resource "google_dns_policy" "default" {
|
|||
}
|
||||
}
|
||||
|
||||
resource "google_compute_global_address" "psn_ranges" {
|
||||
for_each = local.psn_ranges
|
||||
resource "google_compute_global_address" "psa_ranges" {
|
||||
for_each = local.psa_ranges
|
||||
project = var.project_id
|
||||
name = "${var.name}-psn-${each.value.name}"
|
||||
name = "${var.name}-psa-${each.key}"
|
||||
purpose = "VPC_PEERING"
|
||||
address_type = "INTERNAL"
|
||||
address = each.value.address
|
||||
|
@ -339,11 +339,11 @@ resource "google_compute_global_address" "psn_ranges" {
|
|||
network = local.network.id
|
||||
}
|
||||
|
||||
resource "google_service_networking_connection" "psn_connection" {
|
||||
for_each = toset(local.psn_ranges == {} ? [] : [""])
|
||||
resource "google_service_networking_connection" "psa_connection" {
|
||||
for_each = toset(local.psa_ranges == {} ? [] : [""])
|
||||
network = local.network.id
|
||||
service = "servicenetworking.googleapis.com"
|
||||
reserved_peering_ranges = [
|
||||
for k, v in google_compute_global_address.psn_ranges : v.name
|
||||
for k, v in google_compute_global_address.psa_ranges : v.name
|
||||
]
|
||||
}
|
||||
|
|
|
@ -27,7 +27,7 @@ output "name" {
|
|||
google_compute_network_peering.remote,
|
||||
google_compute_shared_vpc_host_project.shared_vpc_host,
|
||||
google_compute_shared_vpc_service_project.service_projects,
|
||||
google_service_networking_connection.psn_connection
|
||||
google_service_networking_connection.psa_connection
|
||||
]
|
||||
}
|
||||
|
||||
|
@ -39,7 +39,7 @@ output "network" {
|
|||
google_compute_network_peering.remote,
|
||||
google_compute_shared_vpc_host_project.shared_vpc_host,
|
||||
google_compute_shared_vpc_service_project.service_projects,
|
||||
google_service_networking_connection.psn_connection
|
||||
google_service_networking_connection.psa_connection
|
||||
]
|
||||
}
|
||||
|
||||
|
@ -52,7 +52,7 @@ output "project_id" {
|
|||
google_compute_network_peering.remote,
|
||||
google_compute_shared_vpc_host_project.shared_vpc_host,
|
||||
google_compute_shared_vpc_service_project.service_projects,
|
||||
google_service_networking_connection.psn_connection
|
||||
google_service_networking_connection.psa_connection
|
||||
]
|
||||
}
|
||||
|
||||
|
@ -64,7 +64,7 @@ output "self_link" {
|
|||
google_compute_network_peering.remote,
|
||||
google_compute_shared_vpc_host_project.shared_vpc_host,
|
||||
google_compute_shared_vpc_service_project.service_projects,
|
||||
google_service_networking_connection.psn_connection
|
||||
google_service_networking_connection.psa_connection
|
||||
]
|
||||
}
|
||||
|
||||
|
|
|
@ -108,16 +108,16 @@ variable "project_id" {
|
|||
type = string
|
||||
}
|
||||
|
||||
variable "psn_ranges" {
|
||||
variable "psa_ranges" {
|
||||
description = "CIDR ranges used for Google services that support Private Service Networking."
|
||||
type = list(string)
|
||||
type = map(string)
|
||||
default = null
|
||||
validation {
|
||||
condition = alltrue([
|
||||
for r in(var.psn_ranges == null ? [] : var.psn_ranges) :
|
||||
can(cidrnetmask(r))
|
||||
for k, v in(var.psa_ranges == null ? {} : var.psa_ranges) :
|
||||
can(cidrnetmask(v))
|
||||
])
|
||||
error_message = "Specify a valid RFC1918 CIDR range for Private Service Networking."
|
||||
error_message = "Specify valid RFC1918 CIDR ranges for Private Service Networking."
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -14,44 +14,15 @@
|
|||
* limitations under the License.
|
||||
*/
|
||||
|
||||
# tfdoc:file:description Project factory.
|
||||
|
||||
|
||||
locals {
|
||||
_defaults = yamldecode(file(var.defaults_file))
|
||||
_defaults_net = {
|
||||
billing_account_id = var.billing_account_id
|
||||
environment_dns_zone = var.environment_dns_zone
|
||||
shared_vpc_self_link = var.shared_vpc_self_link
|
||||
vpc_host_project = var.vpc_host_project
|
||||
}
|
||||
defaults = merge(local._defaults, local._defaults_net)
|
||||
projects = {
|
||||
for f in fileset("${var.data_dir}", "**/*.yaml") :
|
||||
trimsuffix(f, ".yaml") => yamldecode(file("${var.data_dir}/${f}"))
|
||||
}
|
||||
}
|
||||
|
||||
module "projects" {
|
||||
#TODO(sruffilli): Pin to release
|
||||
source = "../../../../../examples/factories/project-factory"
|
||||
for_each = local.projects
|
||||
defaults = local.defaults
|
||||
project_id = each.key
|
||||
billing_account_id = try(each.value.billing_account_id, null)
|
||||
billing_alert = try(each.value.billing_alert, null)
|
||||
dns_zones = try(each.value.dns_zones, [])
|
||||
essential_contacts = try(each.value.essential_contacts, [])
|
||||
folder_id = each.value.folder_id
|
||||
group_iam = try(each.value.group_iam, {})
|
||||
iam = try(each.value.iam, {})
|
||||
kms_service_agents = try(each.value.kms, {})
|
||||
labels = try(each.value.labels, {})
|
||||
org_policies = try(each.value.org_policies, null)
|
||||
service_accounts = try(each.value.service_accounts, {})
|
||||
services = try(each.value.services, [])
|
||||
services_iam = try(each.value.services_iam, {})
|
||||
vpc = try(each.value.vpc, null)
|
||||
source = "../../../../../fast/stages/03-project-factory/dev"
|
||||
data_dir = "./data/projects/"
|
||||
defaults_file = "./data/defaults.yaml"
|
||||
prefix = "test"
|
||||
billing_account_id = "12345-67890A-BCDEF0"
|
||||
environment_dns_zone = "dev"
|
||||
shared_vpc_self_link = "fake_link"
|
||||
vpc_host_project = "host_project"
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -30,6 +30,6 @@ module "test" {
|
|||
subnet_flow_logs = var.subnet_flow_logs
|
||||
subnet_private_access = var.subnet_private_access
|
||||
auto_create_subnetworks = var.auto_create_subnetworks
|
||||
psn_ranges = var.psn_ranges
|
||||
psa_ranges = var.psa_ranges
|
||||
data_folder = var.data_folder
|
||||
}
|
||||
|
|
|
@ -61,8 +61,8 @@ variable "peering_config" {
|
|||
default = null
|
||||
}
|
||||
|
||||
variable "psn_ranges" {
|
||||
type = list(string)
|
||||
variable "psa_ranges" {
|
||||
type = map(string)
|
||||
default = null
|
||||
}
|
||||
|
||||
|
|
|
@ -16,20 +16,21 @@ import tftest
|
|||
|
||||
|
||||
def test_single_range(plan_runner):
|
||||
"Test single PSN range."
|
||||
_, resources = plan_runner(psn_ranges='["172.16.100.0/24"]')
|
||||
"Test single PSA range."
|
||||
_, resources = plan_runner(psa_ranges='{foobar="172.16.100.0/24"}')
|
||||
assert len(resources) == 3
|
||||
|
||||
|
||||
def test_multi_range(plan_runner):
|
||||
"Test multiple PSN ranges."
|
||||
_, resources = plan_runner(psn_ranges='["172.16.100.0/24", "172.16.101.0/24"]')
|
||||
"Test multiple PSA ranges."
|
||||
psa_ranges = '{foobar="172.16.100.0/24", frobniz="172.16.101.0/24"}'
|
||||
_, resources = plan_runner(psa_ranges=psa_ranges)
|
||||
assert len(resources) == 4
|
||||
|
||||
|
||||
def test_validation(plan_runner):
|
||||
"Test PSN variable validation."
|
||||
"Test PSA variable validation."
|
||||
try:
|
||||
plan_runner(psn_ranges='["foobar"]')
|
||||
plan_runner(psa_ranges='{foobar="foobar"}')
|
||||
except tftest.TerraformTestError as e:
|
||||
assert 'Invalid value for variable' in e.args[0]
|
Loading…
Reference in New Issue