Skip to content

Commit a20710d

Browse files
authored
implement tgtm suggestions to apigw custom domain sample (#246)
* implement tgtm suggestions to apigw custom domain sample * upgrade serverless localstack plugin version * implement suggestions * make suggested changes * skip auth token check * make all changes
1 parent d308c5f commit a20710d

File tree

7 files changed

+148
-109
lines changed

7 files changed

+148
-109
lines changed

apigw-custom-domain/Makefile

Lines changed: 52 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -2,57 +2,74 @@ export AWS_ACCESS_KEY_ID ?= test
22
export AWS_SECRET_ACCESS_KEY ?= test
33
export AWS_DEFAULT_REGION ?= us-east-1
44

5-
65
usage: ## Show this help
76
@fgrep -h "##" $(MAKEFILE_LIST) | fgrep -v fgrep | sed -e 's/\\$$//' | sed -e 's/##//'
87

8+
check: ## Check if all required prerequisites are installed
9+
@command -v docker > /dev/null 2>&1 || { echo "Docker is not installed. Please install Docker and try again."; exit 1; }
10+
@command -v node > /dev/null 2>&1 || { echo "Node.js is not installed. Please install Node.js and try again."; exit 1; }
11+
@command -v aws > /dev/null 2>&1 || { echo "AWS CLI is not installed. Please install AWS CLI and try again."; exit 1; }
12+
@command -v python > /dev/null 2>&1 || { echo "Python is not installed. Please install Python and try again."; exit 1; }
13+
@command -v openssl > /dev/null 2>&1 || { echo "OpenSSL is not installed. Please install OpenSSL and try again."; exit 1; }
14+
@command -v localstack > /dev/null 2>&1 || { echo "LocalStack is not installed. Please install LocalStack and try again."; exit 1; }
15+
@echo "All required prerequisites are available."
16+
917
install: ## Install dependencies
10-
@npm install
1118
@which serverless || npm install -g serverless
12-
@which localstack || pip install localstack
1319
@which awslocal || pip install awscli-local
20+
@if [ ! -d "node_modules" ]; then \
21+
echo "node_modules not found. Running npm install..."; \
22+
npm install; \
23+
else \
24+
echo "node_modules already installed."; \
25+
fi
26+
@echo "All required dependencies are available."
1427

1528
cert: ## Create test SSL certificate
16-
mkdir -p sslcert
17-
cd sslcert; \
18-
which openssl || exit; \
19-
openssl req -new -newkey RSA:2048 -nodes -keyout ssl.key -out ssl.csr -subj '/CN=test.example.com'; \
20-
openssl genrsa -out rootCA.key 2048; \
21-
openssl req -x509 -new -nodes -key rootCA.key -sha256 -days 3650 -out rootCA.pem -subj /CN=TestCA; \
29+
@echo "Creating SSL certificates directory..."
30+
@mkdir -p sslcert
31+
@echo "Generating SSL certificate..."
32+
@cd sslcert; \
33+
which openssl || { echo "OpenSSL is not installed. Please install OpenSSL and try again."; exit 1; }; \
34+
openssl req -new -newkey RSA:2048 -nodes -keyout ssl.key -out ssl.csr -subj '/CN=test.example.com' && \
35+
openssl genrsa -out rootCA.key 2048 && \
36+
openssl req -x509 -new -nodes -key rootCA.key -sha256 -days 3650 -out rootCA.pem -subj /CN=TestCA && \
2237
openssl x509 -req -in ssl.csr -CAcreateserial -out server.crt -sha256 -CAkey rootCA.key -CA rootCA.pem
38+
@echo "SSL certificate generated successfully."
39+
40+
deploy: ## Deploy Serverless app to local environment with SSL setup for Route53
41+
@echo "Generating and importing test SSL certificate to ACM for Route53 domain test.example.com"
42+
@make cert
43+
@echo "Importing local test certificate into ACM API ..."
44+
@awslocal acm import-certificate --certificate fileb://sslcert/server.crt --private-key fileb://sslcert/ssl.key
45+
@echo "Creating Route53 hosted zone for test domain 'test.example.com' ..."
46+
@awslocal route53 create-hosted-zone --name test.example.com --caller-reference r1
47+
@echo "Deploying Serverless app to local environment"
48+
@SLS_DEBUG=1 npm run deploy
49+
@echo "Serverless app successfully deployed."
50+
51+
run: ## Run the app locally and show test invocations
52+
./run.sh
2353

24-
run: ## Deploy the app locally and run an API GW test invocation
25-
echo "Generating and importing test SSL certificate to ACM for Route53 domain test.example.com"; \
26-
make cert; \
27-
echo "Importing local test certificate into ACM API ..."; \
28-
awslocal acm import-certificate --certificate fileb://sslcert/server.crt --private-key fileb://sslcert/ssl.key && \
29-
echo "Creating Route53 hosted zone for test domain 'test.example.com' ..."; \
30-
awslocal route53 create-hosted-zone --name test.example.com --caller-reference r1 && \
31-
echo "Deploying Serverless app to local environment"; \
32-
SLS_DEBUG=1 npm run deploy && \
33-
echo "Serverless app successfully deployed. Now trying to invoke the API Gateway endpoints with custom domains." && \
34-
echo && echo "Invoking endpoint 1: http://test.example.com:4566/hello" && \
35-
response1=`curl -H 'Host: test.example.com' http://localhost:4566/hello` && \
36-
../assert "$$response1" = "hello world" && \
37-
echo && echo && echo "Invoking endpoint 2: http://test.example.com:4566/goodbye" && \
38-
response2=`curl -H 'Host: test.example.com' http://localhost:4566/goodbye` && \
39-
../assert "$$response2" = "goodbye"
40-
41-
start:
42-
localstack start -d
43-
44-
stop:
54+
test: ## Run tests
55+
make deploy run target=ci
56+
57+
start: ## Start LocalStack
58+
ACTIVATE_PRO=1 localstack start -d
59+
60+
stop: ## Stop LocalStack
4561
@echo
4662
localstack stop
47-
ready:
63+
64+
ready: ## Wait until LocalStack is ready
4865
@echo Waiting on the LocalStack container...
4966
@localstack wait -t 30 && echo Localstack is ready to use! || (echo Gave up waiting on LocalStack, exiting. && exit 1)
5067

51-
logs:
68+
logs: ## Retrieve LocalStack logs
5269
@localstack logs > logs.txt
5370

54-
test-ci:
55-
make start install ready run; return_code=`echo $$?`;\
71+
test-ci: ## Run CI tests
72+
make check start install ready test; return_code=`echo $$?`;\
5673
make logs; make stop; exit $$return_code;
5774

58-
.PHONY: usage install run cert ready stop logs test-ci
75+
.PHONY: usage check install run cert start stop ready logs test-ci

apigw-custom-domain/README.md

Lines changed: 40 additions & 47 deletions
Original file line numberDiff line numberDiff line change
@@ -1,68 +1,61 @@
1-
# LocalStack Demo: API Gateway with Custom Domains
1+
# API Gateway with Custom Domains
22

3-
Simple demo application illustrating API Gateway (v2) endpoints using custom domain names (via Route53, ACM), deployed locally in LocalStack using the Serverless framework.
3+
| Key | Value |
4+
| ------------ | --------------------------------- |
5+
| Environment | LocalStack |
6+
| Services | API Gateway, Lambda, Route53, ACM |
7+
| Integrations | Serverless Framework |
8+
| Categories | Serverless; REST API |
9+
10+
## Introduction
11+
12+
A demo application showcasing API Gateway (v2) endpoints with custom domain names configured through Route53 and ACM, deployed locally using LocalStack and the Serverless framework. For more details, refer to the [documentation](https://docs.localstack.cloud/user-guide/aws/apigateway/#custom-domain-names-with-api-gateway).
13+
14+
Under the hood, the Serverless framework uses the [`serverless-localstack`](https://github.com/localstack/serverless-localstack) plugin to deploy the application to LocalStack. The plugin is configured in the `serverless.yml` file to use the LocalStack endpoint and the custom domain name.
415

516
## Prerequisites
617

7-
* LocalStack
8-
* Docker
9-
* Node.js / `npm`
10-
* `make`
18+
* [Node.js 18.x](https://nodejs.org/en/download/package-manager) with `npm`
19+
* [Serverless Framework](https://www.serverless.com/framework/docs/getting-started) 3.x
20+
* `openssl`
1121

12-
## Installing
22+
## Check prerequisites
1323

14-
To install the dependencies:
24+
```bash
25+
make check
1526
```
27+
28+
## Installation
29+
30+
```bash
1631
make install
1732
```
1833

19-
## Running
34+
## Start LocalStack
2035

21-
Make sure that LocalStack is started:
22-
```
23-
LOCALSTACK_AUTH_TOKEN=... DEBUG=1 localstack start
36+
```bash
37+
make start
2438
```
2539

26-
Deploy the app locally and run a test invocation via:
27-
```
28-
make run
29-
```
40+
## Deploy the Application
3041

31-
The script first generates an SSL certificate for local testing (in case the `openssl` command is not available, it will use an existing, predefined certificate), and then adds it to Amazon Certificate Manager (ACM), and finally creates a Route53 hosted zone for the domain name `test.example.com`:
32-
```
33-
Generating a 2048 bit RSA private key
34-
...
35-
subject=/CN=test.example.com
36-
...
37-
Importing local test certificate into ACM API ...
38-
{
39-
"CertificateArn": "arn:aws:acm:us-east-1:000000000000:certificate/9cbc69d6-abf9-412e-9e2b-36f99fcbf251"
40-
}
41-
Creating Route53 hosted zone for test domain 'test.example.com' ...
42-
{
43-
"HostedZone": {
44-
"Id": "/hostedzone/SU1TPRNX6CL3OE0",
45-
"Name": "test.example.com.",
46-
...
42+
```bash
43+
make deploy
4744
```
4845

49-
Next, you should see some output with the deployment logs of the Serverless application, and some details in the output section towards the bottom:
50-
```
51-
...
52-
Serverless Domain Manager: Info: Created API mapping '(none)' for test.example.com
53-
Serverless Domain Manager: Summary: Distribution Domain Name
54-
Serverless Domain Manager: Domain Name: test.example.com
55-
Serverless Domain Manager: Target Domain: test.example.com
56-
Serverless Domain Manager: Hosted Zone Id: Z2FDTNDATAQYW2
57-
```
46+
The script:
5847

59-
Finally, the script runs two invocations of the new API GW API deployed under the custom domain name `test.example.com`:
60-
```
61-
Invoking endpoint 1: http://test.example.com:4566/hello
62-
...
48+
- Generates an SSL certificate for local testing using `openssl`.
49+
- Uses a predefined certificate if `openssl` is unavailable.
50+
- Adds the certificate to Amazon Certificate Manager (ACM).
51+
- Creates a Route53 hosted zone for `test.example.com`.
52+
- Displays deployment logs of the Serverless application in the output section.
53+
- Showcases API Gateway endpoints and custom domain configuration.
54+
55+
## Run the application
6356

64-
Invoking endpoint 2: http://test.example.com:4566/goodbye
65-
...
57+
```bash
58+
make run
6659
```
6760

6861
## License

apigw-custom-domain/package-lock.json

Lines changed: 23 additions & 19 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

apigw-custom-domain/package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
"serverless": "^3.0.0",
77
"serverless-deployment-bucket": "^1.6.0",
88
"serverless-domain-manager": "^6.4.4",
9-
"serverless-localstack": "^1.0.6"
9+
"serverless-localstack": "^1.2.0"
1010
},
1111
"scripts": {
1212
"deploy": "sls deploy --stage local"

apigw-custom-domain/run.sh

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
#!/bin/bash
2+
set -euo pipefail
3+
4+
invoke_endpoints() {
5+
echo "Invoking endpoint 1: http://test.example.com:4566/hello"
6+
response1=$(curl -H 'Host: test.example.com' http://localhost:4566/hello)
7+
if [ "$response1" != "hello world" ]; then
8+
echo "Error: Response from endpoint 1 does not match expected output."
9+
exit 1
10+
fi
11+
12+
echo "Invoking endpoint 2: http://test.example.com:4566/goodbye"
13+
response2=$(curl -H 'Host: test.example.com' http://localhost:4566/goodbye)
14+
if [ "$response2" != "goodbye" ]; then
15+
echo "Error: Response from endpoint 2 does not match expected output."
16+
exit 1
17+
fi
18+
}
19+
20+
target="${target:-default}"
21+
22+
if [[ "$target" == "ci" ]]; then
23+
invoke_endpoints
24+
else
25+
echo "Now trying to invoke the API Gateway endpoints with custom domains."
26+
echo "Sample command to invoke endpoint 1:"
27+
echo "curl -H 'Host: test.example.com' http://localhost:4566/hello"
28+
echo "Sample command to invoke endpoint 2:"
29+
echo "curl -H 'Host: test.example.com' http://localhost:4566/goodbye"
30+
fi

apigw-custom-domain/serverless.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,9 @@ service: sls-apigw-domain
22

33
provider:
44
name: aws
5-
runtime: nodejs16.x
5+
runtime: nodejs18.x
66
stage: local
7-
region: ${env:AWS_DEFAULT_REGION, 'us-east-1'}
7+
region: ${env:AWS_DEFAULT_REGION}
88

99
custom:
1010
customDomain:

lambda-hot-reloading/javascript-terraform-layers/layer_src/nodejs/node_modules/test-dep/index.js

Lines changed: 0 additions & 5 deletions
This file was deleted.

0 commit comments

Comments
 (0)