logo
Edge API Gateway Custom Domain with SAM

Edge API Gateway Custom Domain with SAM

certificate in us-east-1 when using another region

Published Jan 2, 2024

I want to deploy an edge-optimized API Gateway with a custom domain name.

The tool to build it?

My infrastructure background led me to CloudFormation when I started on AWS. Where some developers can start with SST, ServerlessFramework, or CDK.
In the serverless world, I use SAM (Serverless Application Model).

Problem?

To deploy an Edge API Gateway, it's mandatory to generate a certificate in us-east-1.
The problem with CloudFormation is that resources in one stack are deployed in a single region. We are not able to set another region for a specific resource.
Example: Create a Certificate with ACM (AWS Certificat Manager) in us-east-1.

How to solve it?

From this statement, we have multiple options to choose from:
  1. To create a dedicated stack for the certificate in us-east-1, and use the certificate in our main stack, for me in eu-west-1.
  2. To create a unique stack (in eu-west-1) and use CloudFormation custom resources to handle certificate creation in us-east-1.
To learn more about CloudFormation custom resources, you can check out this workshop.

Why the first option?

I chose the first option for simplicity and maintainability. Custom resources expand CloudFormation but I love to keep things simple. That means not creating too many resources via custom resources.
I will use custom resources in my solution to "GET" some values (not creating anything).

Stack

Prerequisites:
  • Having your Route53 zone in the same AWS Account.

Let's go and Build !!!
1/ As you can see in the diagram above, the first step is to create the "certificate.yaml" file.
To create an ACM certificate on AWS with DNS as DomainValidationOptions, we need to provide the DomainName and the HostedZoneId. CloudFormation does not get the HostedZoneId dynamically.
I made a custom resource for a dynamic approach, not hardcoded. AWS should provide the support of DomainName only.
To get the ARN of this certificate from the other stack I store it in a ParameterStore.
1
2
3
4
5
6
CertificateARN:
Type: "AWS::SSM::Parameter"
Properties:
Name: !Ref ACMCertificate
Type: "String"
Value: !Ref Certificate
2/ Deploy the main stack with the template named "template.yaml".
Now we need to deploy the main stack, our EDGE API Gateway. We need to get the certificate we created in Step 1 and the HostedZoneId for our domain. To do this we will create a second custom resource.
The stack described in this article is available on my GitHub if you want to test or reuse it.