Skip to content

Commit

Permalink
Merge pull request GoogleCloudPlatform#1364 from juliodiez/serverless…
Browse files Browse the repository at this point in the history
…-program

Cloud Run services in service projects
  • Loading branch information
juliodiez authored May 8, 2023
2 parents bf182bf + 0e9b685 commit f0d928f
Show file tree
Hide file tree
Showing 5 changed files with 62 additions and 29 deletions.
40 changes: 19 additions & 21 deletions blueprints/serverless/cloud-run-corporate/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -152,11 +152,11 @@ tf_identity = "[user or SA account]"

#### Use case 3.4

Another possibility is for a project to be a Service Project with the Cloud Run service running in the Host Project, since this is also considered `"internal"` traffic. In this case a VPC SC perimeter is not needed.
Another possibility is to use an architecture based on Shared VPC that allows direct service-to-service calls while ensuring all traffic stays within your private network. In this case a VPC SC perimeter is not needed.

<p style="left"> <img src="images/use-case-3.4.png" width="800"> </p>
<p style="left"> <img src="images/use-case-3.4.png" width="600"> </p>

Note that the service project can't have a different DNS entry for the same domain, so it uses the DNS and PSC configuration of the host project. Set the following in `terraform.tfvars`:
For simplicity, the two Cloud Run services are deployed in the same service project. To test access, VMs are created in the host and service projects. Note that the service project can't have a different DNS entry for the same domain, so it uses the DNS and PSC configuration of the host project. Set the following in `terraform.tfvars`:

```tfvars
prj_main_id = "[your-main-project-id]" # Used as host project
Expand All @@ -165,11 +165,11 @@ prj_svc1_id = "[your-service-project1-id]"

### Use case 4: Access to Cloud Run with custom domain

You need to use a L7 ILB with Serverless NEGs (in Preview) to set a custom domain for Cloud Run. As a practical example, this blueprint deploys this configuration in a Shared VPC environment with two Cloud Run services running in service projects and the ILB exposing them via a custom domain, pointing to them through a URL map: `/cart` and `/checkout`.
You need to use a L7 ILB with Serverless NEGs (in Preview) to set a custom domain for Cloud Run. As a practical example, this blueprint deploys this configuration in a Shared VPC environment with two Cloud Run services running in a service project and the ILB exposing them via a custom domain, pointing to them through a URL map: `/cart` and `/checkout`.

<p align="center"> <img src="images/use-case-4.png" width="600"> </p>

For simplicity, both services are deployed in the same service project. Also, the blueprint uses an HTTP connection to the ILB to avoid management of SSL certificates. To test access, VMs are created in the host and service projects. Set the following in `terraform.tfvars`:
The blueprint uses an HTTP connection to the ILB to avoid management of SSL certificates. To test access, VMs are created in the host and service projects. Set the following in `terraform.tfvars`:

```tfvars
prj_main_id = "[your-main-project-id]" # Used as host project
Expand All @@ -181,8 +181,6 @@ SSH into a test VM and run `curl` specifying as URL the host, your custom domain

<p align="center"> <img src="images/service-running-4.png" width="700"> </p>

Note that the default URLs for both services are also output, and the PSC endpoint for the `*.run.app` domain from previous examples is still created. However, access to these URLs from both VMs in the host or service project is blocked since the requests come from a VPC network in a different project to the service.

## Cleaning up your environment

The easiest way to remove all the deployed resources is to run the following command:
Expand All @@ -196,22 +194,22 @@ The above command will delete the associated resources so there will be no billa

| name | description | type | required | default |
|---|---|:---:|:---:|:---:|
| [prj_main_id](variables.tf#L78) | Main Project ID. | <code>string</code> || |
| [prj_main_id](variables.tf#L79) | Main Project ID. | <code>string</code> || |
| [access_policy](variables.tf#L17) | VPC SC access policy, if it exists. | <code>string</code> | | <code>null</code> |
| [access_policy_create](variables.tf#L23) | Parameters for the creation of a VPC SC access policy. | <code title="object&#40;&#123;&#10; parent &#61; string&#10; title &#61; string&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>null</code> |
| [custom_domain](variables.tf#L32) | Custom domain for the Load Balancer. | <code>string</code> | | <code>null</code> |
| [image](variables.tf#L38) | Container image to deploy. | <code>string</code> | | <code>&#34;us-docker.pkg.dev&#47;cloudrun&#47;container&#47;hello&#34;</code> |
| [ingress_settings](variables.tf#L44) | Ingress traffic sources allowed to call the service. | <code>string</code> | | <code>&#34;internal&#34;</code> |
| [ip_ranges](variables.tf#L50) | IPs or IP ranges used by VPCs. | <code>map&#40;map&#40;string&#41;&#41;</code> | | <code title="&#123;&#10; main &#61; &#123;&#10; subnet &#61; &#34;10.0.1.0&#47;24&#34;&#10; subnet_proxy &#61; &#34;10.10.0.0&#47;24&#34;&#10; psc_addr &#61; &#34;10.0.0.100&#34;&#10; &#125;&#10; onprem &#61; &#123;&#10; subnet &#61; &#34;172.16.1.0&#47;24&#34;&#10; &#125;&#10; prj1 &#61; &#123;&#10; subnet &#61; &#34;10.0.2.0&#47;24&#34;&#10; psc_addr &#61; &#34;10.0.0.200&#34;&#10; &#125;&#10;&#125;">&#123;&#8230;&#125;</code> |
| [prj_main_create](variables.tf#L69) | Parameters for the creation of the main project. | <code title="object&#40;&#123;&#10; billing_account_id &#61; string&#10; parent &#61; string&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>null</code> |
| [prj_onprem_create](variables.tf#L83) | Parameters for the creation of an 'onprem' project. | <code title="object&#40;&#123;&#10; billing_account_id &#61; string&#10; parent &#61; string&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>null</code> |
| [prj_onprem_id](variables.tf#L92) | Onprem Project ID. | <code>string</code> | | <code>null</code> |
| [prj_prj1_create](variables.tf#L98) | Parameters for the creation of project 1. | <code title="object&#40;&#123;&#10; billing_account_id &#61; string&#10; parent &#61; string&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>null</code> |
| [prj_prj1_id](variables.tf#L107) | Project 1 ID. | <code>string</code> | | <code>null</code> |
| [prj_svc1_create](variables.tf#L113) | Parameters for the creation of service project 1. | <code title="object&#40;&#123;&#10; billing_account_id &#61; string&#10; parent &#61; string&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>null</code> |
| [prj_svc1_id](variables.tf#L122) | Service Project 1 ID. | <code>string</code> | | <code>null</code> |
| [region](variables.tf#L128) | Cloud region where resource will be deployed. | <code>string</code> | | <code>&#34;europe-west1&#34;</code> |
| [tf_identity](variables.tf#L134) | Terraform identity to include in VPC SC perimeter. | <code>string</code> | | <code>null</code> |
| [ip_ranges](variables.tf#L50) | IPs or IP ranges used by VPCs. | <code>map&#40;map&#40;string&#41;&#41;</code> | | <code title="&#123;&#10; main &#61; &#123;&#10; subnet &#61; &#34;10.0.1.0&#47;24&#34;&#10; subnet_proxy &#61; &#34;10.10.0.0&#47;24&#34;&#10; subnet_vpc_access &#61; &#34;10.10.10.0&#47;28&#34;&#10; psc_addr &#61; &#34;10.0.0.100&#34;&#10; &#125;&#10; onprem &#61; &#123;&#10; subnet &#61; &#34;172.16.1.0&#47;24&#34;&#10; &#125;&#10; prj1 &#61; &#123;&#10; subnet &#61; &#34;10.0.2.0&#47;24&#34;&#10; psc_addr &#61; &#34;10.0.0.200&#34;&#10; &#125;&#10;&#125;">&#123;&#8230;&#125;</code> |
| [prj_main_create](variables.tf#L70) | Parameters for the creation of the main project. | <code title="object&#40;&#123;&#10; billing_account_id &#61; string&#10; parent &#61; string&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>null</code> |
| [prj_onprem_create](variables.tf#L84) | Parameters for the creation of an 'onprem' project. | <code title="object&#40;&#123;&#10; billing_account_id &#61; string&#10; parent &#61; string&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>null</code> |
| [prj_onprem_id](variables.tf#L93) | Onprem Project ID. | <code>string</code> | | <code>null</code> |
| [prj_prj1_create](variables.tf#L99) | Parameters for the creation of project 1. | <code title="object&#40;&#123;&#10; billing_account_id &#61; string&#10; parent &#61; string&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>null</code> |
| [prj_prj1_id](variables.tf#L108) | Project 1 ID. | <code>string</code> | | <code>null</code> |
| [prj_svc1_create](variables.tf#L114) | Parameters for the creation of service project 1. | <code title="object&#40;&#123;&#10; billing_account_id &#61; string&#10; parent &#61; string&#10;&#125;&#41;">object&#40;&#123;&#8230;&#125;&#41;</code> | | <code>null</code> |
| [prj_svc1_id](variables.tf#L123) | Service Project 1 ID. | <code>string</code> | | <code>null</code> |
| [region](variables.tf#L129) | Cloud region where resource will be deployed. | <code>string</code> | | <code>&#34;europe-west1&#34;</code> |
| [tf_identity](variables.tf#L135) | Terraform identity to include in VPC SC perimeter. | <code>string</code> | | <code>null</code> |

## Outputs

Expand Down Expand Up @@ -240,7 +238,7 @@ module "test" {
prj_onprem_id = "onprem-project-id"
}
# tftest modules=15 resources=45
# tftest modules=15 resources=46
```

```hcl
Expand All @@ -264,7 +262,7 @@ module "test" {
tf_identity = "[email protected]"
}
# tftest modules=15 resources=31
# tftest modules=15 resources=32
```

```hcl
Expand All @@ -283,5 +281,5 @@ module "test" {
custom_domain = "cloud-run-corporate.example.org"
}
# tftest modules=14 resources=38
# tftest modules=14 resources=43
```
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
40 changes: 37 additions & 3 deletions blueprints/serverless/cloud-run-corporate/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -103,11 +103,20 @@ module "project_svc1" {
parent = try(var.prj_svc1_create.parent, null)
shared_vpc_service_config = {
host_project = module.project_main.project_id
service_identity_iam = {
"roles/compute.networkUser" = [
"vpcaccess"
],
"roles/editor" = [
"cloudservices"
]
}
}
services = [
"compute.googleapis.com",
"dns.googleapis.com",
"run.googleapis.com"
"run.googleapis.com",
"vpcaccess.googleapis.com"
]
skip_delete = true
}
Expand All @@ -133,10 +142,24 @@ module "cloud_run_hello" {
ingress_settings = var.ingress_settings
}

# VPC Access connector in the service project.
# The Shared VPC Ingress feature needs a VPC connector. In the future,
# this need will be removed.
resource "google_vpc_access_connector" "connector" {
count = var.prj_svc1_id != null ? 1 : 0
name = "connector"
project = module.project_svc1[0].project_id
region = var.region
subnet {
name = module.vpc_main.subnets["${var.region}/subnet-vpc-access"].name
project_id = module.project_main.project_id
}
}

# Cloud Run service 1 in service project
module "cloud_run_cart" {
source = "../../../modules/cloud-run"
count = var.custom_domain == null ? 0 : 1
count = var.prj_svc1_id != null ? 1 : 0
project_id = module.project_svc1[0].project_id
name = local.service_name_cr1 # "cart"
region = var.region
Expand All @@ -149,12 +172,15 @@ module "cloud_run_cart" {
"roles/run.invoker" = ["allUsers"]
}
ingress_settings = var.ingress_settings
revision_annotations = {
vpcaccess_connector = google_vpc_access_connector.connector[0].name
}
}

# Cloud Run service 2 in service project
module "cloud_run_checkout" {
source = "../../../modules/cloud-run"
count = var.custom_domain == null ? 0 : 1
count = var.prj_svc1_id != null ? 1 : 0
project_id = module.project_svc1[0].project_id
name = local.service_name_cr2 # "checkout"
region = var.region
Expand All @@ -167,6 +193,9 @@ module "cloud_run_checkout" {
"roles/run.invoker" = ["allUsers"]
}
ingress_settings = var.ingress_settings
revision_annotations = {
vpcaccess_connector = google_vpc_access_connector.connector[0].name
}
}

###############################################################################
Expand All @@ -183,6 +212,11 @@ module "vpc_main" {
ip_cidr_range = var.ip_ranges["main"].subnet
name = "subnet-main"
region = var.region
},
{
ip_cidr_range = var.ip_ranges["main"].subnet_vpc_access
name = "subnet-vpc-access"
region = var.region
}
]
subnets_proxy_only = [
Expand Down
4 changes: 2 additions & 2 deletions blueprints/serverless/cloud-run-corporate/outputs.tf
Original file line number Diff line number Diff line change
Expand Up @@ -16,13 +16,13 @@

output "default_URL_cart" {
description = "Cloud Run service 'cart' default URL."
value = (var.custom_domain != null ?
value = (var.prj_svc1_id != null ?
module.cloud_run_cart[0].service.status[0].url : "none")
}

output "default_URL_checkout" {
description = "Cloud Run service 'checkout' default URL."
value = (var.custom_domain != null ?
value = (var.prj_svc1_id != null ?
module.cloud_run_checkout[0].service.status[0].url : "none")
}

Expand Down
7 changes: 4 additions & 3 deletions blueprints/serverless/cloud-run-corporate/variables.tf
Original file line number Diff line number Diff line change
Expand Up @@ -52,9 +52,10 @@ variable "ip_ranges" {
type = map(map(string))
default = {
main = {
subnet = "10.0.1.0/24"
subnet_proxy = "10.10.0.0/24"
psc_addr = "10.0.0.100"
subnet = "10.0.1.0/24"
subnet_proxy = "10.10.0.0/24"
subnet_vpc_access = "10.10.10.0/28"
psc_addr = "10.0.0.100"
}
onprem = {
subnet = "172.16.1.0/24"
Expand Down

0 comments on commit f0d928f

Please sign in to comment.