12

我有一个在 AWS Route53 中注册的现有域名,并且我在 API Gateway 中设置了一个自定义域名。在控制台中,我可以从外部配置诸如 xxxxxx.zenxxxxxxfoundry.com 之类的东西,实际上到达 API Gateway API,然后到达我的 Lambda 函数。

现在我想用 AWS CDK 来实现这一点。

我尝试了以下方法:

    const zone = route53.HostedZone.fromHostedZoneId(this, 'ZenithWebFoundryZone', 'ZXXXXXX04V8134');
    new route53.AliasRecord(this, 'BlogAPIRecord', {
      zone: zone,
      recordName: 'xxxxxx.zenxxxxxxfoundry.com',
      target: {
        bind: (): route53.AliasRecordTargetProps => ({
          dnsName: 'd-xxxxxxy00g.execute-api.ap-southeast-2.amazonaws.com',
          hostedZoneId: 'ZXXXXXX04V8134'
        })
      }
    });

可以构建npm run build,但是当我运行时,cdk synth我得到了相当迟钝的错误:

$ cdk synth
HostedZone.fromHostedZoneId doesn't support "zoneName"
Subprocess exited with error 1

打开--trace并没有太大帮助:附加信息:

Error: Subprocess exited with error 1
    at ChildProcess.proc.on.code (/Users/mikecoxon/.npm-packages/lib/node_modules/aws-cdk/lib/api/cxapp/exec.ts:108:23)
    at ChildProcess.emit (events.js:189:13)
    at ChildProcess.EventEmitter.emit (domain.js:441:20)
    at Process.ChildProcess._handle.onexit (internal/child_process.js:248:12)

我查看了整个堆栈脚本,没有zoneName任何地方引用。有谁知道这个错误来自哪里?

4

6 回答 6

10

我在使用 cdk 1.36.1 时遇到了同样的问题,并设法使用 ApiGateway 中的新自定义域名以及 BasePath 映射来解决它,然后在 route53 上指向新自定义域的现有托管区域中添加 CName 记录:

import {BasePathMapping, DomainName, EndpointType, LambdaRestApi} from '@aws-cdk/aws-apigateway';
import {Certificate} from '@aws-cdk/aws-certificatemanager';
import {HostedZone, CnameRecord} from '@aws-cdk/aws-route53'

// First create a custom domain:
const customDomain = new DomainName(this, 'customDomain', {
      domainName: 'api.xxxxxxx.com',
      certificate: Certificate.fromCertificateArn(this, 'ACM_Certificate', ACM_CERTIFICATE_ARN),
      endpointType: EndpointType.EDGE
});

// create a new ApiGateway instance and associate a lambda function with it:
const api = new LambdaRestApi(this, 'MainGatewayEndpoint', {
      handler: toyFunction,
});

// Associate the Custom domain that we created with new APIGateway using BasePathMapping:
new BasePathMapping(this, 'CustomBasePathMapping', {
      domainName: custom,
      restApi: api
});

// Get a reference to AN EXISTING hosted zone using the HOSTED_ZONE_ID. You can get this from route53
const hostedZone = HostedZone.fromHostedZoneAttributes(this, 'HostedZone', {
      hostedZoneId: PROD_HOSTED_ZONE_ID,
      zoneName: 'xxxxxxx.com'
});

// Finally, add a CName record in the hosted zone with a value of the new custom domain that was created above:
new CnameRecord(this, 'ApiGatewayRecordSet', {
      zone: hostedZone,
      recordName: 'api',
      domainName: customDomain.domainNameAliasDomainName
});

于 2020-05-03T11:24:23.490 回答
8

使用aws-cdkv1 应该能够执行以下操作:

const zone = route53.HostedZone.fromHostedZoneAttributes(this, 'ZenithWebFoundryZone', {
  hostedZoneId: 'ZXXXXXX04V8134',
  zoneName: 'zenxxxxxxfoundry.com' // your zone name here
});

new route53.ARecord(this, 'BlogAPIRecord', {
  zone,
  recordName: 'xxxxxx.zenxxxxxxfoundry.com',
  target: route53.RecordTarget.fromAlias({
    bind() {
      return {
        dnsName: 'd-xxxxxxy00g.execute-api.ap-southeast-2.amazonaws.com', // Specify the applicable domain name for your API.,
        hostedZoneId: 'XXXX', // Specify the hosted zone ID for your API.
      };
    },
  }),
});

如果您的 API 在同一个堆栈/代码库中,您可以从中获取dnsNameand hostedZoneId(这是一个 CF 属性)。

否则请参阅AWS ::Route53::RecordSet AliasTarget 文档DNSName中的和。HostedZoneId

注意hostedZoneId您的别名记录您自己区域的托管区域 ID 不同。

于 2019-06-14T13:50:02.350 回答
5

在 AWS CDK 0.36.1 中,您可以使用 @aws-cdk/aws-route53-targets 包创建别名。

import { HostedZone, RecordSet, RecordType, RecordTarget } from '@aws-cdk/aws-route53'
import { ApiGatewayDomain } from '@aws-cdk/aws-route53-targets'
import { Certificate } from '@aws-cdk/aws-certificatemanager'

// ...

  const customDomain = new apigateway.DomainName(this, 'CustomDomain', {
    domainName: props.apiDomain,
    certificate: Certificate.fromCertificateArn(this, 'Certificate', props.certificateArn),
    endpointType: apigateway.EndpointType.EDGE,
  })

  const hostedZone = HostedZone.fromHostedZoneAttributes(this, 'HostedZone', {
    hostedZoneId: props.hostedZoneId,
    zoneName: props.hostedZoneName,
  })

  new RecordSet(this, 'ApiRecordSetA', {
    zone: hostedZone,
    recordType: RecordType.A,
    recordName: 'api',
    target: RecordTarget.fromAlias(new ApiGatewayDomain(customDomain))
  })

  new RecordSet(this, 'ApiRecordSetAAAA', {
    zone: hostedZone,
    recordType: RecordType.AAAA,
    recordName: 'api',
    target: RecordTarget.fromAlias(new ApiGatewayDomain(customDomain))
  })
于 2019-07-03T01:12:25.550 回答
2

我设法使这项工作正常进行,但被要求使用“。”的托管区域名称所吸引。最后。

这适用于手动创建并需要查找以通过 CDK 添加别名记录的现有托管区域。

const hostedZone = route53.HostedZone.fromHostedZoneAttributes(this, 'HostedZone', {
  hostedZoneId: config.apiHostedZoneId,
  name: `${config.apiDomainName}.`,
});

new route53.RecordSet(this, 'ApiRecordSetA', {
  zone: hostedZone,
  recordType: route53.RecordType.A,
  recordName: config.apiDomainName,
  target: route53.RecordTarget.fromAlias(new route53Targets.ApiGatewayDomain(apiDomain))
});

new route53.RecordSet(this, 'ApiRecordSetAAAA', {
  zone: hostedZone,
  recordType: route53.RecordType.AAAA,
  recordName: config.apiDomainName,
  target: route53.RecordTarget.fromAlias(new route53Targets.ApiGatewayDomain(apiDomain))
});
于 2019-12-30T19:30:28.490 回答
0

我遇到了以下相同的错误:

const zone = route53.HostedZone.fromHostedZoneId(this, 'MyZone', 'ZXXXXXXXXXXXXX');

我在 Route53 中有一个类似于下面的区域:

Domain Name:    example.com.
Type:           Public Hosted Zone
Hosted Zone ID: ZXXXXXXXXXXXXX

我更改为以下内容并且它有效(CDK 0.34.0):

const zone = new route53.HostedZoneProvider(this,  {
  domainName: 'example.com',
}).findAndImport(this, 'MyZone');
于 2019-06-14T03:55:59.797 回答
0

在托管区域的文档中 - 特别是 fromHostedZoneID 和 fromHostedZoneAttributes 的方法:

https://docs.aws.amazon.com/cdk/api/latest/docs/@aws-cdk_aws-route53.HostedZone.html#static-fromwbrhostedwbrzonewbrattributesscope-id-attrs

它特别提到“托管区域名称通过此查询变得不可用”

fromHostedZoneID 返回的 HostedZone 对象没有 zoneName 的属性,因此不能与 route53.AliasRecord 一起使用 - 您必须使用 fromHostedZoneAttributes。为了检索 cdk 的 A 记录所需的信息设置。

注意:如果您在 API 的声明中分配域,则使用(在 python 中,因为这是我方便的,抱歉)

route53.ARecord(
        self, "DomainAliasLogicalID",
        zone=route53_host_zone,
        target=route53.RecordTarget.from_alias(route53_targets.ApiGateway(your_api_object)),
        record_name=your_domain_name
    )

如果您设置自己的域名对象(不是 API 网关的一部分,请使用 route53_targets.ApiGatewayDomain(your_domain_object)

于 2021-08-16T16:38:25.507 回答