如何从 Terraform / Pulumi 访问 Cloud 运行 服务 IP 以动态创建 A 记录?
How to access Cloud Run service IPs from Terraform / Pulumi to dynamically create A records?
我正在使用 Google Cloud 运行 和 Pulumi(类似于 Terraform)。我对 Cloud 运行 域映射的设置是:
new gcp.cloudrun.DomainMapping(
`${prefix}-domain-mapping`,
{
location,
name: 'xxx',
metadata: {
namespace: projectId,
},
spec: {
routeName: appService.name,
},
},
{
dependsOn: [appService],
},
)
其中 appService
指向 Cloud 运行 服务的一个实例。这成功创建了到云 运行 服务的域映射。
接下来我要设置一个包含记录的 DNS 区域:
const zone = new gcp.dns.ManagedZone(`${prefix}-zone`, {
name: `${prefix}-zone`,
dnsName: 'xxx.',
visibility: 'public',
})
const ips = ['xxx', 'xxx', 'xxx', 'xxx']
new gcp.dns.RecordSet(
`${prefix}-a-records`,
{
name: 'xxx.',
managedZone: zone.name,
type: 'A',
ttl: 3600,
rrdatas: ips,
},
{
dependsOn: [zone],
deleteBeforeReplace: true,
},
)
上面的代码有效。我有一个 DNS 区域,其中有四个 A 记录指向 4 个不同的 IP 地址,这些 IP 地址指向云 运行 服务。我的问题是:如何自动化上面硬编码的 IP?我希望为 A 记录动态设置 Cloud 运行 的 IP 地址。 ips
变量必须指向云 运行 实例的 IP,但我找不到方法来做到这一点。
或者也许我做错了,还有另一种方法可以做到这一点?我的目标是,如果 Cloud 运行 服务更新并接收新 IP,DNS 记录也应该自动更新。我不想手动更新地址。
由于 Pulumi 或多或少等同于 Terraform,非常感谢 Terraform 或 Pulumi 中的答案!
我还没有尝试过 运行 但至少这段代码可以编译:
const mapping = new gcp.cloudrun.DomainMapping(...);
const records = mapping.status.resourceRecords?.apply(rs => rs ?? []) ?? pulumi.output([]);
new gcp.dns.RecordSet(`${prefix}-a-records`, {
name: 'xxx.',
managedZone: zone.name,
type: 'A',
ttl: 3600,
rrdatas: records.apply(rs => rs.map(r => r.rrdata)),
}, {
dependsOn: [zone, mapping],
deleteBeforeReplace: true,
});
与records
的舞蹈是为了在两个层面上摆脱undefined
...不确定是否可以简化。
由于这个问题是用 Pulumi 和 Terraform 标签标记的,这里有一个可能的 Terraform 解决方案:
resource "google_cloud_run_domain_mapping" "example" {
location = "us-central1"
name = "xxx"
metadata {
namespace = local.project_name
}
spec {
route_name = google_cloud_run_service.app.name
}
}
resource "google_dns_managed_zone" "example" {
name = "${local.prefix}-zone"
dns_name = "xxx."
visibility = "public"
}
locals {
dns_records = {
"A" = [
for rr in google_cloud_run_domain_mapping.example.resource_records :
rr.rrdata if rr.type == "A"
]
"AAAA" = [
for rr in google_cloud_run_domain_mapping.example.resource_records :
rr.rrdata if rr.type == "AAAA"
]
}
}
resource "google_dns_record_set" "example" {
for_each = local.dns_records
managed_zone = google_dns_managed_zone.example.name
name = "xxx."
type = each.key
ttl = 3600
rrdatas = each.value
}
我正在使用 Google Cloud 运行 和 Pulumi(类似于 Terraform)。我对 Cloud 运行 域映射的设置是:
new gcp.cloudrun.DomainMapping(
`${prefix}-domain-mapping`,
{
location,
name: 'xxx',
metadata: {
namespace: projectId,
},
spec: {
routeName: appService.name,
},
},
{
dependsOn: [appService],
},
)
其中 appService
指向 Cloud 运行 服务的一个实例。这成功创建了到云 运行 服务的域映射。
接下来我要设置一个包含记录的 DNS 区域:
const zone = new gcp.dns.ManagedZone(`${prefix}-zone`, {
name: `${prefix}-zone`,
dnsName: 'xxx.',
visibility: 'public',
})
const ips = ['xxx', 'xxx', 'xxx', 'xxx']
new gcp.dns.RecordSet(
`${prefix}-a-records`,
{
name: 'xxx.',
managedZone: zone.name,
type: 'A',
ttl: 3600,
rrdatas: ips,
},
{
dependsOn: [zone],
deleteBeforeReplace: true,
},
)
上面的代码有效。我有一个 DNS 区域,其中有四个 A 记录指向 4 个不同的 IP 地址,这些 IP 地址指向云 运行 服务。我的问题是:如何自动化上面硬编码的 IP?我希望为 A 记录动态设置 Cloud 运行 的 IP 地址。 ips
变量必须指向云 运行 实例的 IP,但我找不到方法来做到这一点。
或者也许我做错了,还有另一种方法可以做到这一点?我的目标是,如果 Cloud 运行 服务更新并接收新 IP,DNS 记录也应该自动更新。我不想手动更新地址。
由于 Pulumi 或多或少等同于 Terraform,非常感谢 Terraform 或 Pulumi 中的答案!
我还没有尝试过 运行 但至少这段代码可以编译:
const mapping = new gcp.cloudrun.DomainMapping(...);
const records = mapping.status.resourceRecords?.apply(rs => rs ?? []) ?? pulumi.output([]);
new gcp.dns.RecordSet(`${prefix}-a-records`, {
name: 'xxx.',
managedZone: zone.name,
type: 'A',
ttl: 3600,
rrdatas: records.apply(rs => rs.map(r => r.rrdata)),
}, {
dependsOn: [zone, mapping],
deleteBeforeReplace: true,
});
与records
的舞蹈是为了在两个层面上摆脱undefined
...不确定是否可以简化。
由于这个问题是用 Pulumi 和 Terraform 标签标记的,这里有一个可能的 Terraform 解决方案:
resource "google_cloud_run_domain_mapping" "example" {
location = "us-central1"
name = "xxx"
metadata {
namespace = local.project_name
}
spec {
route_name = google_cloud_run_service.app.name
}
}
resource "google_dns_managed_zone" "example" {
name = "${local.prefix}-zone"
dns_name = "xxx."
visibility = "public"
}
locals {
dns_records = {
"A" = [
for rr in google_cloud_run_domain_mapping.example.resource_records :
rr.rrdata if rr.type == "A"
]
"AAAA" = [
for rr in google_cloud_run_domain_mapping.example.resource_records :
rr.rrdata if rr.type == "AAAA"
]
}
}
resource "google_dns_record_set" "example" {
for_each = local.dns_records
managed_zone = google_dns_managed_zone.example.name
name = "xxx."
type = each.key
ttl = 3600
rrdatas = each.value
}