Skip to content

Commit de0f9d7

Browse files
authored
Merge pull request #2749 from jojo786/feature-apigw-lambda-dsql
New serverless pattern: apigw-lambda-dsql
2 parents 1d7e9d8 + 1be3cac commit de0f9d7

File tree

6 files changed

+353
-0
lines changed

6 files changed

+353
-0
lines changed

apigw-lambda-dsql/README.md

Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
# Amazon API Gateway, AWS Lambda and Amazon Aurora DSQL
2+
3+
Amazon Aurora DSQL is the fastest serverless, distributed SQL database with active-active high availability and multi-Region strong consistency. Aurora DSQL enables you to build always available applications with virtually unlimited scalability, the highest availability, and zero infrastructure management. It is designed to make scaling and resilience effortless for your applications and offers the fastest distributed SQL reads and writes.
4+
5+
This pattern deploys a API Gateway REST API, Lambda function and an Aurora DSQL PostgreSQL cluster.
6+
7+
Learn more about this pattern at [Serverless Land Patterns](https://serverlessland.com/patterns/apigw-lambda-dsql)
8+
9+
Important: this application uses various AWS services and there are costs associated with these services after the Free Tier usage - please see the [AWS Pricing page](https://aws.amazon.com/pricing/) for details. You are responsible for any AWS costs incurred. No warranty is implied in this example.
10+
11+
## Requirements
12+
13+
* [Create an AWS account](https://portal.aws.amazon.com/gp/aws/developer/registration/index.html) if you do not already have one and log in. The IAM user that you use must have sufficient permissions to make necessary AWS service calls and manage AWS resources.
14+
* [AWS CLI](https://docs.aws.amazon.com/cli/latest/userguide/install-cliv2.html) installed and configured
15+
* [Git Installed](https://git-scm.com/book/en/v2/Getting-Started-Installing-Git)
16+
* [AWS Serverless Application Model](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/serverless-sam-cli-install.html) (AWS SAM) installed
17+
18+
## Deployment Instructions
19+
20+
1. Create a new directory, navigate to that directory in a terminal and clone the GitHub repository:
21+
```
22+
git clone https://github.com/aws-samples/serverless-patterns
23+
```
24+
1. Change directory to the pattern directory:
25+
```
26+
cd apigw-lambda-dsql
27+
```
28+
1. From the command line, use AWS SAM to deploy the AWS resources for the pattern as specified in the template.yml file:
29+
```
30+
sam build
31+
sam deploy --guided
32+
```
33+
1. During the prompts:
34+
* Enter a stack name
35+
* Enter the desired AWS Region (verify which [regions Aurora DSQL is available in](https://aws.amazon.com/rds/aurora/dsql/faqs/))
36+
* Allow SAM CLI to create IAM roles with the required permissions.
37+
38+
Once you have run `sam deploy --guided` mode once and saved arguments to a configuration file (samconfig.toml), you can use `sam deploy` in future to use these defaults.
39+
40+
1. Note the outputs from the SAM deployment process. These contain the resource names and/or ARNs which are used for testing.
41+
42+
## How it works
43+
44+
This sample project demonstrates how to use a Lambda function (invoked by API Gateway), that stores and retrieves data from an Amazon Aurora DSQL PostgreSQL cluster.
45+
46+
## Testing
47+
48+
Use the `Value` from `UsersApi` URL output from the above `sam deploy` command to invoke the API Gateway API, e.g:
49+
`curl https://abc123.execute-api.eu-west-1.amazonaws.com/Prod/users/`
50+
which should return with
51+
`{"id": "e3ce23b5-c6a1-4289-bb02-2f34a2f7b956", "name": "John", "city": "LA", "telephone": "555-555-0150"}`
52+
53+
## Cleanup
54+
55+
1. Delete the stack
56+
```bash
57+
sam delete
58+
```
59+
1. Confirm the stack has been deleted
60+
```bash
61+
aws cloudformation list-stacks --query "StackSummaries[?contains(StackName,'STACK_NAME')].StackStatus"
62+
```
63+
----
64+
Copyright 2025 Amazon.com, Inc. or its affiliates. All Rights Reserved.
65+
66+
SPDX-License-Identifier: MIT-0
Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
{
2+
"title": "Amazon API Gateway, AWS Lambda and Amazon Aurora DSQL",
3+
"description": "Creates an API Gateway REST API integrated with an AWS Lambda function that connects to an Amazon Aurora DSQL PostgreSQL cluster",
4+
"language": "Python",
5+
"level": "200",
6+
"framework": "AWS SAM",
7+
"introBox": {
8+
"headline": "How it works",
9+
"text": [
10+
"This sample project demonstrates how to use a Lambda function (invoked by API Gateway), that stores and retrieves data from an Amazon Aurora DSQL PostgreSQL cluster.",
11+
"Aurora DSQL enables you to build always available applications with virtually unlimited scalability, the highest availability, and zero infrastructure management.",
12+
"This pattern deploys a API Gateway REST API, Lambda function and an Aurora DSQL PostgreSQL cluster."
13+
]
14+
},
15+
"gitHub": {
16+
"template": {
17+
"repoURL": "https://github.com/aws-samples/serverless-patterns/tree/main/apigw-lambda-dsql",
18+
"templateURL": "serverless-patterns/apigw-lambda-dsql",
19+
"projectFolder": "apigw-lambda-dsql",
20+
"templateFile": "template.yaml"
21+
}
22+
},
23+
"resources": {
24+
"bullets": [
25+
{
26+
"text": "Amazon Aurora DSQL, the fastest serverless distributed SQL database is now generally available",
27+
"link": "https://aws.amazon.com/blogs/aws/amazon-aurora-dsql-is-now-generally-available/"
28+
},
29+
{
30+
"text": "DSQL Vignette: Aurora DSQL, and A Personal Story",
31+
"link": "https://brooker.co.za/blog/2024/12/03/aurora-dsql.html/"
32+
},
33+
{
34+
"text": "Amazon Aurora DSQL samples",
35+
"link": "https://github.com/aws-samples/aurora-dsql-samples/tree/main/python"
36+
}
37+
]
38+
},
39+
"deploy": {
40+
"text": [
41+
"sam deploy"
42+
]
43+
},
44+
"testing": {
45+
"text": [
46+
"See the GitHub repo for detailed testing instructions."
47+
]
48+
},
49+
"cleanup": {
50+
"text": [
51+
"sam delete"
52+
]
53+
},
54+
"authors": [
55+
{
56+
"name": "Yusuf Mayet",
57+
"image": "https://d2908q01vomqb2.cloudfront.net/9e6a55b6b4563e652a23be9d623ca5055c356940/2021/11/24/Yusuf-mayet-aws.jpg",
58+
"bio": "I am a Solutions Architect at AWS, where I help customers realise that true transformation lies at the intersection of Cloud, DevOps cultural practices, Agile principles, modular and scalable architectures, and efficient team structures.",
59+
"linkedin": "yusufmayet"
60+
}
61+
],
62+
"patternArch": {
63+
"icon1": {
64+
"x": 20,
65+
"y": 50,
66+
"service": "apigw",
67+
"label": "API Gateway REST API"
68+
},
69+
"icon2": {
70+
"x": 50,
71+
"y": 50,
72+
"service": "lambda",
73+
"label": "AWS Lambda"
74+
},
75+
"icon3": {
76+
"x": 80,
77+
"y": 50,
78+
"service": "aurora",
79+
"label": "Amazon Aurora DSQL"
80+
},
81+
"line1": {
82+
"from": "icon1",
83+
"to": "icon2"
84+
},
85+
"line2": {
86+
"from": "icon2",
87+
"to": "icon3"
88+
}
89+
}
90+
}
Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,62 @@
1+
{
2+
"title": "Amazon API Gateway, AWS Lambda and Amazon Aurora DSQL",
3+
"description": "Creates an API Gateway REST API integrated with an AWS Lambda function that connects to an Amazon Aurora DSQL PostgreSQL cluster",
4+
"language": "Python",
5+
"level": "200",
6+
"framework": "AWS SAM",
7+
"introBox": {
8+
"headline": "How it works",
9+
"text": [
10+
"This sample project demonstrates how to use a Lambda function (invoked by API Gateway), that stores and retrieves data from an Amazon Aurora DSQL PostgreSQL cluster.",
11+
"Aurora DSQL enables you to build always available applications with virtually unlimited scalability, the highest availability, and zero infrastructure management.",
12+
"This pattern deploys a API Gateway REST API, Lambda function and an Aurora DSQL PostgreSQL cluster."
13+
]
14+
},
15+
"gitHub": {
16+
"template": {
17+
"repoURL": "https://github.com/aws-samples/serverless-patterns/tree/main/apigw-lambda-dsql",
18+
"templateURL": "serverless-patterns/apigw-lambda-dsql",
19+
"projectFolder": "apigw-lambda-dsql",
20+
"templateFile": "template.yaml"
21+
}
22+
},
23+
"resources": {
24+
"bullets": [
25+
{
26+
"text": "Amazon Aurora DSQL, the fastest serverless distributed SQL database is now generally available",
27+
"link": "https://aws.amazon.com/blogs/aws/amazon-aurora-dsql-is-now-generally-available/"
28+
},
29+
{
30+
"text": "DSQL Vignette: Aurora DSQL, and A Personal Story",
31+
"link": "https://brooker.co.za/blog/2024/12/03/aurora-dsql.html/"
32+
},
33+
{
34+
"text": "Amazon Aurora DSQL samples",
35+
"link": "https://github.com/aws-samples/aurora-dsql-samples/tree/main/python"
36+
}
37+
]
38+
},
39+
"deploy": {
40+
"text": [
41+
"sam deploy"
42+
]
43+
},
44+
"testing": {
45+
"text": [
46+
"See the GitHub repo for detailed testing instructions."
47+
]
48+
},
49+
"cleanup": {
50+
"text": [
51+
"sam delete"
52+
]
53+
},
54+
"authors": [
55+
{
56+
"name": "Yusuf Mayet",
57+
"image": "https://d2908q01vomqb2.cloudfront.net/9e6a55b6b4563e652a23be9d623ca5055c356940/2021/11/24/Yusuf-mayet-aws.jpg",
58+
"bio": "I am a Solutions Architect at AWS, where I help customers realise that true transformation lies at the intersection of Cloud, DevOps cultural practices, Agile principles, modular and scalable architectures, and efficient team structures.",
59+
"linkedin": "yusufmayet"
60+
}
61+
]
62+
}

apigw-lambda-dsql/src/app.py

Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
#Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
2+
#SPDX-License-Identifier: MIT-0
3+
4+
import json
5+
import boto3
6+
import psycopg2
7+
import psycopg2.extensions
8+
import os
9+
10+
cluster_endpoint = os.environ['cluster_endpoint']
11+
region = os.environ['AWS_REGION']
12+
13+
client = boto3.client("dsql", region_name=region)
14+
15+
def lambda_handler(event, context):
16+
# Generate a fresh password token for each connection, to ensure the token is not expired when the connection is established
17+
password_token = client.generate_db_connect_admin_auth_token(cluster_endpoint, region)
18+
19+
conn_params = {
20+
"dbname": "postgres",
21+
"user": "admin",
22+
"host": cluster_endpoint,
23+
"port": "5432",
24+
"sslmode": "require",
25+
"password": password_token
26+
}
27+
28+
# Use the more efficient connection method if it's supported.
29+
if psycopg2.extensions.libpq_version() >= 170000:
30+
conn_params["sslnegotiation"] = "direct"
31+
32+
# Make a connection to the cluster
33+
conn = psycopg2.connect(**conn_params)
34+
35+
try:
36+
with conn.cursor() as cur:
37+
conn.commit()
38+
except Exception as e:
39+
conn.close()
40+
raise e
41+
42+
conn.set_session(autocommit=True)
43+
44+
cur = conn.cursor()
45+
46+
cur.execute("DROP TABLE IF EXISTS users")
47+
48+
cur.execute(b"""
49+
CREATE TABLE IF NOT EXISTS users(
50+
id uuid NOT NULL DEFAULT gen_random_uuid(),
51+
name varchar(30) NOT NULL,
52+
city varchar(80) NOT NULL,
53+
telephone varchar(20) DEFAULT NULL,
54+
PRIMARY KEY (id))"""
55+
)
56+
57+
# Insert some rows
58+
cur.execute("INSERT INTO users(name, city, telephone) VALUES('John', 'LA', '555-555-0150')")
59+
60+
# Read back what we have inserted
61+
cur.execute("SELECT * FROM users")
62+
row = cur.fetchone()
63+
print(row)
64+
65+
# return JSON back to API Gateway
66+
return {
67+
'statusCode': 200,
68+
'body': json.dumps({
69+
'id': str(row[0]),
70+
'name': row[1],
71+
'city': row[2],
72+
'telephone': row[3]
73+
})
74+
}
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
psycopg2-binary>=2.9
2+
botocore>=1.35.74
3+
boto3>=1.35.74

apigw-lambda-dsql/template.yaml

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
AWSTemplateFormatVersion: '2010-09-09'
2+
Transform: AWS::Serverless-2016-10-31
3+
Description: Serverless patterns - Amazon API Gateway, AWS Lambda and Amazon Aurora DSQL
4+
5+
# More info about Globals: https://github.com/awslabs/serverless-application-model/blob/master/docs/globals.rst
6+
# Global values that are applied to all applicable resources in this template
7+
Globals:
8+
Function:
9+
CodeUri: ./src
10+
Runtime: python3.13
11+
MemorySize: 128
12+
Timeout: 3
13+
LoggingConfig:
14+
LogGroup: !Sub /aws/lambda/${AWS::StackName}
15+
LogFormat: JSON
16+
Architectures:
17+
- arm64
18+
Tags:
19+
project: "apigw-lambda-dsql"
20+
21+
Resources:
22+
UsersFunction:
23+
Type: AWS::Serverless::Function # More info about Function Resource: https://github.com/awslabs/serverless-application-model/blob/master/versions/2016-10-31.md#awsserverlessfunction
24+
Properties:
25+
Handler: app.lambda_handler
26+
Policies: # Creates an IAM Role that defines the services the function can access and which actions the function can perform
27+
- Statement:
28+
- Effect: Allow
29+
Action:
30+
- dsql:DbConnectAdmin
31+
Resource:
32+
- !Sub arn:${AWS::Partition}:dsql:${AWS::Region}:${AWS::AccountId}:cluster/${DSQL}
33+
Environment: # Function environment variables
34+
Variables:
35+
REGION: !Sub ${AWS::Region}
36+
cluster_endpoint: !Sub ${DSQL}.dsql.${AWS::Region}.on.aws
37+
Events:
38+
Users:
39+
Type: Api # More info about API Event Source: https://github.com/awslabs/serverless-application-model/blob/master/versions/2016-10-31.md#api
40+
Properties:
41+
Path: /users
42+
Method: get
43+
44+
DSQL:
45+
Type: AWS::DSQL::Cluster
46+
Properties:
47+
DeletionProtectionEnabled: false
48+
Tags:
49+
- Key: project
50+
Value: "apigw-lambda-dsql"
51+
52+
Outputs:
53+
# ServerlessRestApi is an implicit API created out of Events key under Serverless::Function
54+
# Find out more about other implicit resources you can reference within SAM
55+
# https://github.com/awslabs/serverless-application-model/blob/master/docs/internals/generated_resources.rst#api
56+
UsersApi:
57+
Description: API Gateway endpoint URL for Prod stage for Users function
58+
Value: !Sub "https://${ServerlessRestApi}.execute-api.${AWS::Region}.amazonaws.com/Prod/users/"

0 commit comments

Comments
 (0)