In this post, we are going to use the AWS CDK to build an AWS Lambda Function that triggers from DynamoDB Stream Events.
All of the code can be found in this repository.
Setup
We need to run a few commands to set up our CDK app.
mkdir how-to-trigger-lambda-from-ddb-stream
cd how-to-trigger-lambda-from-ddb-stream
npx cdk init app --language typescript
This should give you the following directory structure.
Also, make sure you have your AWS CLI configured. For more information follow the AWS CLI quickstart guide.
DynamoDB
Install the DynamoDB CDK package.
npm i @aws-cdk/aws-dynamodb
Open lib/how-to-trigger-lambda-from-ddb-stream-stack.ts
, add a new DynamoDB table, and deploy.
import * as cdk from '@aws-cdk/core';
import * as dynamodb from '@aws-cdk/aws-dynamodb';
export class HowToTriggerLambdaFromDdbStreamStack extends cdk.Stack {
constructor(scope: cdk.Construct, id: string, props?: cdk.StackProps) {
super(scope, id, props);
const table = new dynamodb.Table(this, 'Table', {
billingMode: dynamodb.BillingMode.PAY_PER_REQUEST,
partitionKey: { name: 'id', type: dynamodb.AttributeType.STRING },
stream: dynamodb.StreamViewType.NEW_AND_OLD_IMAGES,
tableName: 'Table',
});
}
}
npm run cdk deploy
Lambda
Install the Lambda CDK package.
npm i @aws-cdk/aws-lambda
Deploying Lambda functions requires bootstrapping your CDK app which gives us an S3 bucket where our Lambda's source code will live.
npm run cdk bootstrap
Create src/index.js
and paste the following code
exports.handler = async (event) => {
event.Records.forEach((record) => {
console.log('Event Id: %s', record.eventID);
console.log('Event Id: %s', record.eventName);
console.log('DynamoDB Record: %j', record.dynamodb);
});
};
Open lib/how-to-trigger-lambda-from-ddb-stream-stack.ts
, add a new Lambda function and deploy.
import * as cdk from '@aws-cdk/core';
import * as dynamodb from '@aws-cdk/aws-dynamodb';
import * as lambda from '@aws-cdk/aws-lambda';
export class HowToTriggerLambdaFromDdbStreamStack extends cdk.Stack {
constructor(scope: cdk.Construct, id: string, props?: cdk.StackProps) {
super(scope, id, props);
const table = new dynamodb.Table(this, 'Table', {
billingMode: dynamodb.BillingMode.PAY_PER_REQUEST,
partitionKey: { name: 'id', type: dynamodb.AttributeType.STRING },
tableName: 'Table',
});
const lambdaFunction = new lambda.Function(this, 'Function', {
code: lambda.Code.fromAsset('src'),
handler: 'index.handler',
functionName: 'TableStreamHandler',
runtime: lambda.Runtime.NODEJS_12_X,
});
}
}
npm run cdk deploy
Event Source
Install the Lambda Event Sources CDK package.
npm i @aws-cdk/aws-lambda-event-sources
Open lib/how-to-trigger-lambda-from-ddb-stream-stack.ts
, add a new DynamoEventSource to the Lambda Function.
import * as cdk from '@aws-cdk/core';
import * as dynamodb from '@aws-cdk/aws-dynamodb';
import * as lambda from '@aws-cdk/aws-lambda';
import { DynamoEventSource } from '@aws-cdk/aws-lambda-event-sources';
export class HowToTriggerLambdaFromDdbStreamStack extends cdk.Stack {
constructor(scope: cdk.Construct, id: string, props?: cdk.StackProps) {
super(scope, id, props);
const table = new dynamodb.Table(this, 'Table', {
billingMode: dynamodb.BillingMode.PAY_PER_REQUEST,
partitionKey: { name: 'id', type: dynamodb.AttributeType.STRING },
stream: dynamodb.StreamViewType.NEW_AND_OLD_IMAGES,
tableName: 'Table',
});
const lambdaFunction = new lambda.Function(this, 'Function', {
code: lambda.Code.fromAsset('src'),
handler: 'index.handler',
functionName: 'TableStreamHandler',
runtime: lambda.Runtime.NODEJS_12_X,
});
lambdaFunction.addEventSource(new DynamoEventSource(table, {
startingPosition: lambda.StartingPosition.LATEST,
}));
}
}
npm run cdk deploy
Testing
Using the AWS CLI, insert a new item into the DynamoDB table.
aws dynamodb put-item \
--table-name Table \
--item '{
"id": {"S": "test123"}
}'
Verify that the Lambda executed by looking in CloudWatch. Find the LogGroup named /aws/lambda/TableStreamHandler
and open up the latest LogStream. You should see some log messages that look similar to this.
2021-05-14T19:08:55.487Z ffba16f2-846b-4c6e-9ff5-189c3293116e INFO Event Id: e6db4f872fd1997f0f459bcebb8163e8
2021-05-14T19:08:55.527Z ffba16f2-846b-4c6e-9ff5-189c3293116e INFO Event Id: INSERT
2021-05-14T19:08:55.527Z ffba16f2-846b-4c6e-9ff5-189c3293116e INFO DynamoDB Record: {
"ApproximateCreationDateTime": 1621019335,
"Keys": {
"id": {
"S": "test123"
}
},
"NewImage": {
"id": {
"S": "test123"
}
},
"SequenceNumber": "733400000000008471956488",
"SizeBytes": 18,
"StreamViewType": "NEW_AND_OLD_IMAGES"
}
Summary
Congratulations. If you've made it this far then you successfully ...
-
Scaffolded a new CDK app
-
Created a DynamoDB table
-
Created a Lambda Function
-
Created a DynamoEventSource for the Lambda Function