diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/README.md b/iac-template/terraform-hcl-standard/gcp-cloud/README.md new file mode 100644 index 0000000..d831537 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/README.md @@ -0,0 +1,32 @@ +# GCP Cloud Terraform Standard + +该目录提供与 `aws-cloud` 模板一一对应的 GCP 版本,用于在 GCP 上快速引导基础设施。结构与 AWS 目录保持一致,包括引导阶段 (bootstrap)、环境示例 (envs) 与模块库 (modules)。 + +## 模板映射 +- **bootstrap-dynamodb → Firestore**:使用 Firestore(Datastore 模式)作为无服务器键值存储。 +- **bootstrap-iam → IAM**:创建基础服务账号与自定义角色,替代 AWS IAM 角色与策略。 +- **bootstrap-s3 → Cloud Storage**:创建 GCS 存储桶并启用版本化,对应 AWS S3。 +- **modules**:保留原始模块命名(alb、nlb、vpc 等),内部实现改为 GCP 资源: + - `alb`/`nlb`:使用 Google HTTP(S) / TCP 负载均衡。 + - `ec2`:映射到 Compute Engine 实例或 MIG。 + - `keypair`:生成 SSH 密钥并写入元数据。 + - `msk`:映射到 Pub/Sub(发布/订阅)。 + - `rds`:映射到 Cloud SQL。 + - `s3`:映射到 Cloud Storage。 + - `vpc`:使用 VPC 网络与子网。 + - `ami_lookup`:映射到最新公共镜像查找(debian/ubuntu)。 + - `iam`:分配 IAM 角色与绑定。 + - `landingzone`:创建基础网络、日志与审计配置。 + - `redis`:映射到 Memorystore。 + - `sg`:映射到 VPC 防火墙规则。 + +## 使用方式 +1. 在 `config/backend.tf` 中配置远端状态(GCS 存储桶)。 +2. 在 `config/provider.tf` 中设置 `project`、`region`、`credentials` 等参数。 +3. 按需修改 `envs` 下的环境示例,执行: + ```bash + terraform -chdir=envs/dev init + terraform -chdir=envs/dev apply + ``` + +本目录仅新增 GCP 代码,不改动现有 AWS 模板。 diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/bootstrap-dynamodb/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/bootstrap-dynamodb/main.tf new file mode 100644 index 0000000..2bdd975 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/bootstrap-dynamodb/main.tf @@ -0,0 +1,42 @@ +terraform { + required_providers { + google = { + source = "hashicorp/google" + version = ">= 5.0" + } + } +} + +variable "project_id" { + description = "GCP project id where Firestore will be enabled" + type = string +} + +variable "location" { + description = "Firestore location" + type = string + default = "us-central" +} + +resource "google_project_service" "firestore" { + service = "firestore.googleapis.com" + project = var.project_id +} + +resource "google_project_service" "cloudresourcemanager" { + service = "cloudresourcemanager.googleapis.com" + project = var.project_id +} + +resource "google_firestore_database" "default" { + name = "(default)" + location_id = var.location + project = var.project_id + type = "DATASTORE_MODE" + depends_on = [google_project_service.firestore, google_project_service.cloudresourcemanager] +} + +output "firestore_database" { + description = "Firestore database ID" + value = google_firestore_database.default.name +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/bootstrap-iam/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/bootstrap-iam/main.tf new file mode 100644 index 0000000..1ca2c18 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/bootstrap-iam/main.tf @@ -0,0 +1,47 @@ +terraform { + required_providers { + google = { + source = "hashicorp/google" + version = ">= 5.0" + } + } +} + +variable "project_id" { + description = "Target project for IAM bootstrap" + type = string +} + +variable "service_account_id" { + description = "ID of the bootstrap service account" + type = string + default = "terraform-bootstrap" +} + +variable "service_account_roles" { + description = "List of roles to attach to the bootstrap service account" + type = list(string) + default = [ + "roles/resourcemanager.projectIamAdmin", + "roles/storage.admin", + "roles/compute.admin" + ] +} + +resource "google_service_account" "bootstrap" { + account_id = var.service_account_id + display_name = "Terraform Bootstrap" + project = var.project_id +} + +resource "google_project_iam_member" "bootstrap" { + for_each = toset(var.service_account_roles) + project = var.project_id + role = each.value + member = "serviceAccount:${google_service_account.bootstrap.email}" +} + +output "service_account_email" { + value = google_service_account.bootstrap.email + description = "Bootstrap service account email" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/bootstrap-s3/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/bootstrap-s3/main.tf new file mode 100644 index 0000000..bca892d --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/bootstrap-s3/main.tf @@ -0,0 +1,47 @@ +terraform { + required_providers { + google = { + source = "hashicorp/google" + version = ">= 5.0" + } + } +} + +variable "project_id" { + description = "Project id where the state bucket will be created" + type = string +} + +variable "bucket_name" { + description = "Name of the GCS bucket" + type = string +} + +variable "location" { + description = "Bucket location" + type = string + default = "US" +} + +resource "google_storage_bucket" "state" { + name = var.bucket_name + location = var.location + project = var.project_id + uniform_bucket_level_access = true + versioning { + enabled = true + } + lifecycle_rule { + action { + type = "Delete" + } + condition { + age = 365 + } + } +} + +output "bucket" { + value = google_storage_bucket.state.name + description = "Created state bucket" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/config/backend.tf b/iac-template/terraform-hcl-standard/gcp-cloud/config/backend.tf new file mode 100644 index 0000000..981f5ec --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/config/backend.tf @@ -0,0 +1,9 @@ +terraform { + required_version = ">= 1.5.0" + + backend "gcs" { + bucket = var.state_bucket + prefix = var.state_prefix + project = var.project_id + } +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/config/provider.tf b/iac-template/terraform-hcl-standard/gcp-cloud/config/provider.tf new file mode 100644 index 0000000..3b856df --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/config/provider.tf @@ -0,0 +1,24 @@ +terraform { + required_providers { + google = { + source = "hashicorp/google" + version = ">= 5.0" + } + google-beta = { + source = "hashicorp/google-beta" + version = ">= 5.0" + } + } +} + +provider "google" { + project = var.project_id + region = var.region + zone = var.zone +} + +provider "google-beta" { + project = var.project_id + region = var.region + zone = var.zone +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/config/variables.tf b/iac-template/terraform-hcl-standard/gcp-cloud/config/variables.tf new file mode 100644 index 0000000..f4cdcd1 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/config/variables.tf @@ -0,0 +1,27 @@ +variable "project_id" { + description = "GCP project id" + type = string +} + +variable "region" { + description = "Default region" + type = string + default = "us-central1" +} + +variable "zone" { + description = "Default zone" + type = string + default = "us-central1-a" +} + +variable "state_bucket" { + description = "GCS bucket used for Terraform remote state" + type = string +} + +variable "state_prefix" { + description = "Prefix within the state bucket" + type = string + default = "terraform/state" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-alb/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-alb/main.tf new file mode 100644 index 0000000..253e73f --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-alb/main.tf @@ -0,0 +1,27 @@ +terraform { + required_version = ">= 1.5.0" + required_providers { + google = { + source = "hashicorp/google" + version = ">= 5.0" + } + } +} + +variable "project_id" { type = string } + +provider "google" { + project = var.project_id + region = "us-central1" +} + +module "alb" { + source = "../../modules/alb" + project_id = var.project_id + bucket_name = "dev-alb-static-${var.project_id}" + name = "dev-alb" +} + +output "forwarding_rule" { + value = module.alb.forwarding_rule +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-ec2/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-ec2/main.tf new file mode 100644 index 0000000..3e1d68b --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-ec2/main.tf @@ -0,0 +1,48 @@ +terraform { + required_version = ">= 1.5.0" + required_providers { + google = { source = "hashicorp/google" version = ">= 5.0" } + } +} + +variable "project_id" { type = string } +variable "region" { type = string default = "us-central1" } +variable "zone" { type = string default = "us-central1-a" } + +provider "google" { + project = var.project_id + region = var.region + zone = var.zone +} + +module "vpc" { + source = "../../modules/vpc" + project_id = var.project_id + subnets = [{ + name = "ec2-subnet" + ip_cidr_range = "10.40.0.0/24" + region = var.region + }] +} + +data "google_client_config" "current" {} + +module "ami" { + source = "../../modules/ami_lookup" +} + +module "vm" { + source = "../../modules/ec2" + project_id = var.project_id + name = "dev-compute" + zone = var.zone + machine_type = "e2-medium" + network = module.vpc.network_self_link + subnet = module.vpc.subnet_self_links[0] + image = module.ami.image + ssh_keys = ["terraform:${data.google_client_config.current.access_token}"] +} + +output "instance" { + value = module.vm.instance_self_link +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-kafka/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-kafka/main.tf new file mode 100644 index 0000000..2a14222 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-kafka/main.tf @@ -0,0 +1,24 @@ +terraform { + required_version = ">= 1.5.0" + required_providers { + google = { source = "hashicorp/google" version = ">= 5.0" } + } +} + +variable "project_id" { type = string } + +provider "google" { + project = var.project_id + region = "us-central1" +} + +module "pubsub" { + source = "../../modules/msk" + project_id = var.project_id + topic = "dev-topic" + subscription = "dev-subscription" +} + +output "topic" { + value = module.pubsub.topic +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-landingzone/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-landingzone/main.tf new file mode 100644 index 0000000..72f7db9 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-landingzone/main.tf @@ -0,0 +1,28 @@ +terraform { + required_version = ">= 1.5.0" + required_providers { + google = { source = "hashicorp/google" version = ">= 5.0" } + } +} + +variable "project_id" { type = string } + +provider "google" { + project = var.project_id + region = "us-central1" +} + +module "landingzone" { + source = "../../modules/landingzone" + project_id = var.project_id + services = [ + "compute.googleapis.com", + "pubsub.googleapis.com", + "sqladmin.googleapis.com", + "redis.googleapis.com" + ] +} + +output "services" { + value = module.landingzone.enabled_services +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-nlb/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-nlb/main.tf new file mode 100644 index 0000000..2ffe088 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-nlb/main.tf @@ -0,0 +1,43 @@ +terraform { + required_version = ">= 1.5.0" + required_providers { + google = { + source = "hashicorp/google" + version = ">= 5.0" + } + } +} + +variable "project_id" { type = string } +variable "region" { type = string default = "us-central1" } +variable "zone" { type = string default = "us-central1-a" } + +provider "google" { + project = var.project_id + region = var.region + zone = var.zone +} + +module "vpc" { + source = "../../modules/vpc" + project_id = var.project_id + subnets = [{ + name = "nlb-subnet" + ip_cidr_range = "10.30.0.0/24" + region = var.region + }] +} + +module "nlb" { + source = "../../modules/nlb" + project_id = var.project_id + network = module.vpc.network_self_link + subnet = module.vpc.subnet_self_links[0] + port = 8080 + zone = var.zone + name = "dev-nlb" +} + +output "forwarding_rule" { + value = module.nlb.forwarding_rule +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-object/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-object/main.tf new file mode 100644 index 0000000..bb28e7a --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-object/main.tf @@ -0,0 +1,24 @@ +terraform { + required_version = ">= 1.5.0" + required_providers { + google = { source = "hashicorp/google" version = ">= 5.0" } + } +} + +variable "project_id" { type = string } + +provider "google" { + project = var.project_id + region = "us-central1" +} + +module "bucket" { + source = "../../modules/s3" + project_id = var.project_id + name = "dev-object-${var.project_id}" + location = "US" +} + +output "bucket" { + value = module.bucket.bucket +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-rds/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-rds/main.tf new file mode 100644 index 0000000..b64253d --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-rds/main.tf @@ -0,0 +1,27 @@ +terraform { + required_version = ">= 1.5.0" + required_providers { + google = { source = "hashicorp/google" version = ">= 5.0" } + } +} + +variable "project_id" { type = string } +variable "region" { type = string default = "us-central1" } + +provider "google" { + project = var.project_id + region = var.region +} + +module "sql" { + source = "../../modules/rds" + project_id = var.project_id + name = "dev-postgres" + database_version = "POSTGRES_15" + region = var.region + tier = "db-custom-1-3840" +} + +output "connection_name" { + value = module.sql.connection_name +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-redis/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-redis/main.tf new file mode 100644 index 0000000..6e24d42 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-redis/main.tf @@ -0,0 +1,26 @@ +terraform { + required_version = ">= 1.5.0" + required_providers { + google = { source = "hashicorp/google" version = ">= 5.0" } + } +} + +variable "project_id" { type = string } +variable "region" { type = string default = "us-central1" } + +provider "google" { + project = var.project_id + region = var.region +} + +module "redis" { + source = "../../modules/redis" + project_id = var.project_id + name = "dev-redis" + region = var.region + memory_size_gb = 2 +} + +output "redis_host" { + value = module.redis.host +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-role/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-role/main.tf new file mode 100644 index 0000000..c670079 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-role/main.tf @@ -0,0 +1,25 @@ +terraform { + required_version = ">= 1.5.0" + required_providers { + google = { source = "hashicorp/google" version = ">= 5.0" } + } +} + +variable "project_id" { type = string } + +provider "google" { + project = var.project_id + region = "us-central1" +} + +module "iam" { + source = "../../modules/iam" + project_id = var.project_id + bindings = [ + { role = "roles/storage.objectViewer", member = "allAuthenticatedUsers" } + ] +} + +output "roles" { + value = module.iam.applied_bindings +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-vpc/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-vpc/main.tf new file mode 100644 index 0000000..1296fd9 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev-vpc/main.tf @@ -0,0 +1,33 @@ +terraform { + required_version = ">= 1.5.0" + required_providers { + google = { + source = "hashicorp/google" + version = ">= 5.0" + } + } +} + +variable "project_id" { type = string } +variable "region" { type = string default = "us-central1" } + +provider "google" { + project = var.project_id + region = var.region +} + +module "vpc" { + source = "../../modules/vpc" + project_id = var.project_id + subnets = [ + { + name = "dev-subnet" + ip_cidr_range = "10.20.0.0/24" + region = var.region + } + ] +} + +output "network" { + value = module.vpc.network_self_link +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev/main.tf new file mode 100644 index 0000000..893937a --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/envs/dev/main.tf @@ -0,0 +1,34 @@ +terraform { + required_version = ">= 1.5.0" + required_providers { + google = { + source = "hashicorp/google" + version = ">= 5.0" + } + } +} + +variable "project_id" { + type = string + description = "Target project" +} + +variable "region" { + type = string + default = "us-central1" +} + +provider "google" { + project = var.project_id + region = var.region +} + +module "landingzone" { + source = "../../modules/landingzone" + project_id = var.project_id +} + +output "enabled_services" { + value = module.landingzone.enabled_services + description = "APIs enabled for the project" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/alb/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/alb/main.tf new file mode 100644 index 0000000..61bd817 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/alb/main.tf @@ -0,0 +1,59 @@ +variable "project_id" { + description = "Project id" + type = string +} + +variable "name" { + description = "Load balancer name" + type = string + default = "http-lb" +} + +variable "bucket_name" { + description = "Name for the backend bucket" + type = string +} + +resource "google_storage_bucket" "static" { + name = var.bucket_name + location = "US" + project = var.project_id + uniform_bucket_level_access = true + website { + main_page_suffix = "index.html" + not_found_page = "404.html" + } +} + +resource "google_compute_backend_bucket" "static" { + name = "${var.name}-backend" + bucket_name = google_storage_bucket.static.name + enable_cdn = true +} + +resource "google_compute_url_map" "static" { + name = "${var.name}-url-map" + default_service = google_compute_backend_bucket.static.self_link +} + +resource "google_compute_target_http_proxy" "static" { + name = "${var.name}-http-proxy" + url_map = google_compute_url_map.static.self_link +} + +resource "google_compute_global_forwarding_rule" "static" { + name = "${var.name}-fwd" + port_range = "80" + target = google_compute_target_http_proxy.static.self_link + load_balancing_scheme = "EXTERNAL" +} + +output "bucket" { + value = google_storage_bucket.static.name + description = "Static site bucket" +} + +output "forwarding_rule" { + value = google_compute_global_forwarding_rule.static.name + description = "HTTP forwarding rule" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/ami_lookup/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/ami_lookup/main.tf new file mode 100644 index 0000000..49798de --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/ami_lookup/main.tf @@ -0,0 +1,21 @@ +variable "family" { + description = "Image family to lookup" + type = string + default = "debian-12" +} + +variable "project" { + description = "Project hosting the image" + type = string + default = "debian-cloud" +} + +data "google_compute_image" "family" { + family = var.family + project = var.project +} + +output "image" { + value = data.google_compute_image.family.self_link + description = "Self link of the resolved image" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/ec2/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/ec2/main.tf new file mode 100644 index 0000000..6a9a332 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/ec2/main.tf @@ -0,0 +1,70 @@ +variable "project_id" { + description = "Project id" + type = string +} + +variable "name" { + description = "Instance name" + type = string +} + +variable "zone" { + description = "Instance zone" + type = string + default = "us-central1-a" +} + +variable "machine_type" { + description = "Machine type" + type = string + default = "e2-medium" +} + +variable "network" { + description = "Network self link" + type = string +} + +variable "subnet" { + description = "Subnetwork self link" + type = string +} + +variable "image" { + description = "Source image" + type = string +} + +variable "ssh_keys" { + description = "SSH key metadata entries" + type = list(string) + default = [] +} + +resource "google_compute_instance" "vm" { + name = var.name + project = var.project_id + zone = var.zone + machine_type = var.machine_type + + boot_disk { + initialize_params { + image = var.image + } + } + + network_interface { + network = var.network + subnetwork = var.subnet + access_config {} + } + + metadata = length(var.ssh_keys) > 0 ? { + ssh-keys = join("\n", var.ssh_keys) + } : {} +} + +output "instance_self_link" { + value = google_compute_instance.vm.self_link + description = "Instance self link" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/iam/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/iam/main.tf new file mode 100644 index 0000000..e2b52af --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/iam/main.tf @@ -0,0 +1,25 @@ +variable "project_id" { + type = string + description = "Project id" +} + +variable "bindings" { + type = list(object({ + role = string + member = string + })) + description = "List of role/member bindings" + default = [] +} + +resource "google_project_iam_member" "bindings" { + for_each = { for idx, binding in var.bindings : idx => binding } + project = var.project_id + role = each.value.role + member = each.value.member +} + +output "applied_bindings" { + value = [for binding in google_project_iam_member.bindings : binding.role] + description = "Roles applied to members" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/keypair/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/keypair/main.tf new file mode 100644 index 0000000..4c1907d --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/keypair/main.tf @@ -0,0 +1,36 @@ +terraform { + required_providers { + tls = { + source = "hashicorp/tls" + version = ">= 4.0" + } + } +} + +variable "algorithm" { + type = string + description = "Algorithm for the SSH key" + default = "RSA" +} + +variable "rsa_bits" { + type = number + description = "RSA key length when algorithm is RSA" + default = 4096 +} + +resource "tls_private_key" "ssh" { + algorithm = var.algorithm + rsa_bits = var.rsa_bits +} + +output "public_key_openssh" { + value = tls_private_key.ssh.public_key_openssh + description = "Generated public key" +} + +output "private_key_pem" { + value = tls_private_key.ssh.private_key_pem + sensitive = true + description = "Generated private key" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/landingzone/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/landingzone/main.tf new file mode 100644 index 0000000..856e18e --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/landingzone/main.tf @@ -0,0 +1,26 @@ +variable "project_id" { + description = "Project id" + type = string +} + +variable "services" { + description = "APIs to enable" + type = list(string) + default = [ + "compute.googleapis.com", + "iam.googleapis.com", + "cloudresourcemanager.googleapis.com", + "logging.googleapis.com" + ] +} + +resource "google_project_service" "enabled" { + for_each = toset(var.services) + project = var.project_id + service = each.key +} + +output "enabled_services" { + value = [for s in google_project_service.enabled : s.service] + description = "List of enabled services" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/msk/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/msk/main.tf new file mode 100644 index 0000000..513f652 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/msk/main.tf @@ -0,0 +1,36 @@ +variable "project_id" { + description = "Project id" + type = string +} + +variable "topic" { + description = "Pub/Sub topic name" + type = string + default = "default-topic" +} + +variable "subscription" { + description = "Subscription name" + type = string + default = "default-subscription" +} + +resource "google_pubsub_topic" "this" { + name = var.topic + project = var.project_id +} + +resource "google_pubsub_subscription" "this" { + name = var.subscription + topic = google_pubsub_topic.this.name +} + +output "topic" { + value = google_pubsub_topic.this.name + description = "Pub/Sub topic name" +} + +output "subscription" { + value = google_pubsub_subscription.this.name + description = "Pub/Sub subscription name" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/nlb/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/nlb/main.tf new file mode 100644 index 0000000..6e853a1 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/nlb/main.tf @@ -0,0 +1,78 @@ +variable "project_id" { + description = "Project id" + type = string +} + +variable "name" { + description = "Load balancer name" + type = string + default = "tcp-lb" +} + +variable "network" { + description = "Network self link" + type = string +} + +variable "subnet" { + description = "Subnetwork self link" + type = string +} + +variable "port" { + description = "Service port" + type = number + default = 80 +} + +variable "zone" { + description = "Zone for unmanaged instance group" + type = string + default = "us-central1-a" +} + +resource "google_compute_instance_group" "placeholder" { + name = "${var.name}-ig" + project = var.project_id + zone = var.zone + network = var.network + named_port { + name = "service" + port = var.port + } +} + +resource "google_compute_health_check" "tcp" { + name = "${var.name}-hc" + project = var.project_id + tcp_health_check { + port = var.port + } +} + +resource "google_compute_backend_service" "tcp" { + name = "${var.name}-backend" + project = var.project_id + load_balancing_scheme = "EXTERNAL" + protocol = "TCP" + health_checks = [google_compute_health_check.tcp.self_link] + backend { + group = google_compute_instance_group.placeholder.self_link + } +} + +resource "google_compute_forwarding_rule" "tcp" { + name = "${var.name}-fwd" + project = var.project_id + load_balancing_scheme = "EXTERNAL" + ip_protocol = "TCP" + port_range = tostring(var.port) + backend_service = google_compute_backend_service.tcp.self_link + network = var.network + subnetwork = var.subnet +} + +output "forwarding_rule" { + value = google_compute_forwarding_rule.tcp.name + description = "TCP forwarding rule" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/rds/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/rds/main.tf new file mode 100644 index 0000000..826f4f9 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/rds/main.tf @@ -0,0 +1,44 @@ +variable "project_id" { + description = "Project id" + type = string +} + +variable "name" { + description = "Instance name" + type = string + default = "default-sql" +} + +variable "database_version" { + description = "Cloud SQL engine" + type = string + default = "POSTGRES_15" +} + +variable "tier" { + description = "Machine tier" + type = string + default = "db-f1-micro" +} + +variable "region" { + description = "Instance region" + type = string + default = "us-central1" +} + +resource "google_sql_database_instance" "this" { + name = var.name + project = var.project_id + region = var.region + database_version = var.database_version + + settings { + tier = var.tier + } +} + +output "connection_name" { + value = google_sql_database_instance.this.connection_name + description = "Instance connection string" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/redis/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/redis/main.tf new file mode 100644 index 0000000..1ec2b2c --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/redis/main.tf @@ -0,0 +1,41 @@ +variable "project_id" { + description = "Project id" + type = string +} + +variable "name" { + description = "Redis instance name" + type = string + default = "default-redis" +} + +variable "region" { + description = "Region for the instance" + type = string + default = "us-central1" +} + +variable "tier" { + description = "Service tier" + type = string + default = "STANDARD_HA" +} + +variable "memory_size_gb" { + description = "Memory size" + type = number + default = 1 +} + +resource "google_redis_instance" "this" { + name = var.name + project = var.project_id + region = var.region + tier = var.tier + memory_size_gb = var.memory_size_gb +} + +output "host" { + value = google_redis_instance.this.host + description = "Redis host" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/s3/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/s3/main.tf new file mode 100644 index 0000000..ea7bcdd --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/s3/main.tf @@ -0,0 +1,28 @@ +variable "project_id" { + description = "Project id" + type = string +} + +variable "name" { + description = "Bucket name" + type = string +} + +variable "location" { + description = "Bucket location" + type = string + default = "US" +} + +resource "google_storage_bucket" "this" { + name = var.name + project = var.project_id + location = var.location + uniform_bucket_level_access = true + versioning { enabled = true } +} + +output "bucket" { + value = google_storage_bucket.this.name + description = "Storage bucket" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/sg/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/sg/main.tf new file mode 100644 index 0000000..37f0047 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/sg/main.tf @@ -0,0 +1,45 @@ +variable "project_id" { + description = "Project id" + type = string +} + +variable "network" { + description = "Network self link" + type = string +} + +variable "rules" { + description = "Firewall rules" + type = list(object({ + name = string + direction = string + ranges = list(string) + protocols = map(list(number)) + target_tags = list(string) + })) + default = [] +} + +resource "google_compute_firewall" "rules" { + for_each = { for rule in var.rules : rule.name => rule } + + name = each.value.name + project = var.project_id + network = var.network + direction = upper(each.value.direction) + priority = 1000 + + allow = [for proto, ports in each.value.protocols : { + protocol = proto + ports = [for port in ports : tostring(port)] + }] + + source_ranges = each.value.direction == "ingress" ? each.value.ranges : null + destination_ranges = each.value.direction == "egress" ? each.value.ranges : null + target_tags = each.value.target_tags +} + +output "firewall_rules" { + value = [for rule in google_compute_firewall.rules : rule.name] + description = "Created firewall rules" +} diff --git a/iac-template/terraform-hcl-standard/gcp-cloud/modules/vpc/main.tf b/iac-template/terraform-hcl-standard/gcp-cloud/modules/vpc/main.tf new file mode 100644 index 0000000..5a186c9 --- /dev/null +++ b/iac-template/terraform-hcl-standard/gcp-cloud/modules/vpc/main.tf @@ -0,0 +1,51 @@ +variable "project_id" { + description = "Project id" + type = string +} + +variable "network_name" { + description = "Name of the VPC network" + type = string + default = "main-vpc" +} + +variable "subnets" { + description = "List of subnet definitions" + type = list(object({ + name = string + ip_cidr_range = string + region = string + })) + default = [ + { + name = "default-subnet" + ip_cidr_range = "10.10.0.0/24" + region = "us-central1" + } + ] +} + +resource "google_compute_network" "this" { + name = var.network_name + project = var.project_id + auto_create_subnetworks = false +} + +resource "google_compute_subnetwork" "this" { + for_each = { for subnet in var.subnets : subnet.name => subnet } + name = each.value.name + ip_cidr_range = each.value.ip_cidr_range + region = each.value.region + network = google_compute_network.this.id + private_ip_google_access = true +} + +output "network_self_link" { + value = google_compute_network.this.self_link + description = "VPC network self link" +} + +output "subnet_self_links" { + value = [for subnet in google_compute_subnetwork.this : subnet.self_link] + description = "Subnetwork self links" +}