Skip to content

Commit 943612c

Browse files
authored
Merge pull request #3053 from NithinChandranR-AWS/NithinChandranR-AWS-feature-lambda-durable-bedrock-cdk
New serverless pattern - lambda-durable-bedrock-cdk
2 parents 2cfcc4e + 9fddf04 commit 943612c

10 files changed

Lines changed: 449 additions & 0 deletions

File tree

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
node_modules
2+
cdk.out
3+
*.js
4+
!src/**/*.js
5+
*.d.ts
6+
package-lock.json
Lines changed: 114 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,114 @@
1+
# AWS Lambda durable functions with Amazon Bedrock
2+
3+
This pattern deploys a Lambda durable function that orchestrates a multi-step AI content pipeline using Amazon Bedrock. Each step is automatically checkpointed, so the workflow resumes from the last completed step after any interruption — without re-invoking Bedrock.
4+
5+
Learn more about this pattern at Serverless Land Patterns: https://serverlessland.com/patterns/lambda-durable-bedrock-cdk
6+
7+
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.
8+
9+
## Requirements
10+
11+
* [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.
12+
* [AWS CLI](https://docs.aws.amazon.com/cli/latest/userguide/install-cliv2.html) installed and configured
13+
* [Git Installed](https://git-scm.com/book/en/v2/Getting-Started-Installing-Git)
14+
* [Node.js 18+](https://nodejs.org/en/download/) installed
15+
* [AWS CDK v2](https://docs.aws.amazon.com/cdk/v2/guide/getting-started.html) installed
16+
* [Amazon Bedrock model access](https://docs.aws.amazon.com/bedrock/latest/userguide/model-access.html) enabled for Anthropic Claude Sonnet in your target region
17+
18+
## Architecture
19+
20+
```
21+
┌─────────────┐ ┌──────────────────────────────────────────────────┐
22+
│ Invoke │────▶│ Lambda Durable Function │
23+
│ (CLI/SDK) │ │ │
24+
└─────────────┘ │ Step 1: Generate Outline ──▶ Bedrock (Claude) │
25+
│ ✓ checkpoint │
26+
│ Wait: 5s (simulate review) │
27+
│ ✓ checkpoint │
28+
│ Step 2: Expand Draft ──▶ Bedrock (Claude) │
29+
│ ✓ checkpoint │
30+
│ Step 3: Summarize ──▶ Bedrock (Claude) │
31+
│ ✓ checkpoint │
32+
└──────────────────────────────────────────────────┘
33+
```
34+
35+
## How it works
36+
37+
1. The Lambda durable function receives a topic as input.
38+
2. **Step 1** calls Amazon Bedrock (Claude Sonnet) to generate a blog outline from the topic. The result is checkpointed.
39+
3. The function **waits** 5 seconds (simulating an editorial review pause). During the wait, no compute charges are incurred.
40+
4. **Step 2** calls Bedrock to expand the outline into a full blog draft. Checkpointed.
41+
5. **Step 3** calls Bedrock to generate a concise summary. Checkpointed.
42+
6. If the function is interrupted at any point, it replays from the last checkpoint — completed Bedrock calls are not re-executed.
43+
44+
## Deployment Instructions
45+
46+
1. Clone the repository:
47+
```bash
48+
git clone https://github.com/aws-samples/serverless-patterns
49+
cd serverless-patterns/lambda-durable-bedrock-cdk
50+
```
51+
52+
2. Install dependencies:
53+
```bash
54+
npm install
55+
```
56+
57+
3. Deploy the stack:
58+
```bash
59+
cdk deploy
60+
```
61+
62+
4. Note the outputs printed after deployment. You will need `FunctionName` and `FunctionVersion` for testing.
63+
64+
Example output:
65+
```
66+
Outputs:
67+
LambdaDurableBedrockStack.FunctionName = LambdaDurableBedrockStack-DurableBedrockFn3CE0D50D-AbCdEfGh
68+
LambdaDurableBedrockStack.FunctionVersion = 1
69+
```
70+
71+
## Testing
72+
73+
1. Invoke the durable function. Replace `<FunctionName>` with the `FunctionName` value from the deploy output, and `<Version>` with the `FunctionVersion` value:
74+
```bash
75+
aws lambda invoke \
76+
--function-name <FunctionName> \
77+
--qualifier <Version> \
78+
--payload '{"topic": "Serverless AI workflows with Lambda durable functions"}' \
79+
--cli-binary-format raw-in-base64-out \
80+
output.json
81+
```
82+
83+
For example, if your deploy output showed `FunctionName = MyStack-DurableBedrockFn-AbCdEfGh` and `FunctionVersion = 1`:
84+
```bash
85+
aws lambda invoke \
86+
--function-name MyStack-DurableBedrockFn-AbCdEfGh \
87+
--qualifier 1 \
88+
--payload '{"topic": "Serverless AI workflows with Lambda durable functions"}' \
89+
--cli-binary-format raw-in-base64-out \
90+
output.json
91+
```
92+
93+
2. The function includes a durable wait, so the initial invocation returns quickly with a `"PENDING"` status. Check the durable execution status using the same `<FunctionName>` and `<Version>`:
94+
```bash
95+
aws lambda list-durable-executions-by-function \
96+
--function-name <FunctionName> \
97+
--qualifier <Version>
98+
```
99+
100+
3. Once the execution status shows `"SUCCEEDED"`, view the result:
101+
```bash
102+
cat output.json | jq .
103+
```
104+
105+
## Cleanup
106+
107+
```bash
108+
cdk destroy
109+
```
110+
111+
----
112+
Copyright 2026 Amazon.com, Inc. or its affiliates. All Rights Reserved.
113+
114+
SPDX-License-Identifier: MIT-0
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
#!/usr/bin/env node
2+
import "source-map-support/register";
3+
import * as cdk from "aws-cdk-lib";
4+
import { LambdaDurableBedrockStack } from "../lib/lambda-durable-bedrock-stack";
5+
6+
const app = new cdk.App();
7+
new LambdaDurableBedrockStack(app, "LambdaDurableBedrockStack");
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
{
2+
"app": "npx ts-node --prefer-ts-exts bin/app.ts",
3+
"watch": {
4+
"include": ["**"],
5+
"exclude": ["README.md", "cdk*.json", "**/*.d.ts", "**/*.js", "node_modules", "src"]
6+
},
7+
"context": {
8+
"@aws-cdk/aws-lambda:recognizeLayerVersion": true,
9+
"@aws-cdk/core:checkSecretUsage": true
10+
}
11+
}
Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
{
2+
"title": "AWS Lambda durable functions with Amazon Bedrock",
3+
"description": "AWS Lambda durable functions with Amazon Bedrock for a multi-step AI pipeline with automatic checkpointing and failure recovery.",
4+
"language": "TypeScript",
5+
"level": "300",
6+
"framework": "AWS CDK",
7+
"introBox": {
8+
"headline": "How it works",
9+
"text": [
10+
"This pattern deploys a Lambda durable function that orchestrates a multi-step AI content pipeline using Amazon Bedrock. The function uses the Durable Execution SDK to automatically checkpoint progress at each step.",
11+
"The workflow: (1) generates a blog outline from a topic using Claude, (2) waits 5 seconds to simulate editorial review, (3) expands the outline into a full draft, (4) generates a summary of the draft. Each step is checkpointed, so if the function is interrupted, it resumes from the last completed step without re-invoking Bedrock.",
12+
"This pattern demonstrates how durable functions eliminate the need for Step Functions in tightly-coupled AI workflows while providing built-in resilience."
13+
]
14+
},
15+
"gitHub": {
16+
"template": {
17+
"repoURL": "https://github.com/aws-samples/serverless-patterns/tree/main/lambda-durable-bedrock-cdk",
18+
"templateURL": "serverless-patterns/lambda-durable-bedrock-cdk",
19+
"projectFolder": "lambda-durable-bedrock-cdk",
20+
"templateFile": "lib/lambda-durable-bedrock-stack.ts"
21+
}
22+
},
23+
"resources": {
24+
"bullets": [
25+
{
26+
"text": "Lambda Durable Functions Documentation",
27+
"link": "https://docs.aws.amazon.com/lambda/latest/dg/durable-functions.html"
28+
},
29+
{
30+
"text": "Build multi-step applications and AI workflows with Lambda durable functions",
31+
"link": "https://aws.amazon.com/blogs/aws/build-multi-step-applications-and-ai-workflows-with-aws-lambda-durable-functions/"
32+
},
33+
{
34+
"text": "Amazon Bedrock",
35+
"link": "https://aws.amazon.com/bedrock/"
36+
}
37+
]
38+
},
39+
"deploy": {
40+
"text": [
41+
"cdk deploy"
42+
]
43+
},
44+
"testing": {
45+
"text": [
46+
"See the GitHub repo for detailed testing instructions."
47+
]
48+
},
49+
"cleanup": {
50+
"text": [
51+
"Delete the stack: <code>cdk destroy</code>."
52+
]
53+
},
54+
"authors": [
55+
{
56+
"name": "Nithin Chandran R",
57+
"bio": "Technical Account Manager at AWS",
58+
"linkedin": "nithin-chandran-r"
59+
}
60+
]
61+
}
Lines changed: 80 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,80 @@
1+
{
2+
"title": "AWS Lambda durable functions with Amazon Bedrock",
3+
"description": "AWS Lambda durable functions with Amazon Bedrock for a multi-step AI pipeline with automatic checkpointing and failure recovery.",
4+
"language": "TypeScript",
5+
"level": "300",
6+
"framework": "AWS CDK",
7+
"introBox": {
8+
"headline": "How it works",
9+
"text": [
10+
"This pattern deploys a Lambda durable function that orchestrates a multi-step AI content pipeline using Amazon Bedrock. The function uses the Durable Execution SDK to automatically checkpoint progress at each step.",
11+
"The workflow: (1) generates a blog outline from a topic using Claude, (2) waits 5 seconds to simulate editorial review, (3) expands the outline into a full draft, (4) generates a summary of the draft. Each step is checkpointed, so if the function is interrupted, it resumes from the last completed step without re-invoking Bedrock.",
12+
"This pattern demonstrates how durable functions eliminate the need for Step Functions in tightly-coupled AI workflows while providing built-in resilience."
13+
]
14+
},
15+
"gitHub": {
16+
"template": {
17+
"repoURL": "https://github.com/aws-samples/serverless-patterns/tree/main/lambda-durable-bedrock-cdk",
18+
"templateURL": "serverless-patterns/lambda-durable-bedrock-cdk",
19+
"projectFolder": "lambda-durable-bedrock-cdk",
20+
"templateFile": "lib/lambda-durable-bedrock-stack.ts"
21+
}
22+
},
23+
"resources": {
24+
"bullets": [
25+
{
26+
"text": "Lambda Durable Functions Documentation",
27+
"link": "https://docs.aws.amazon.com/lambda/latest/dg/durable-functions.html"
28+
},
29+
{
30+
"text": "Build multi-step applications and AI workflows with Lambda durable functions",
31+
"link": "https://aws.amazon.com/blogs/aws/build-multi-step-applications-and-ai-workflows-with-aws-lambda-durable-functions/"
32+
},
33+
{
34+
"text": "Amazon Bedrock",
35+
"link": "https://aws.amazon.com/bedrock/"
36+
}
37+
]
38+
},
39+
"deploy": {
40+
"text": [
41+
"cdk deploy"
42+
]
43+
},
44+
"testing": {
45+
"text": [
46+
"See the GitHub repo for detailed testing instructions."
47+
]
48+
},
49+
"cleanup": {
50+
"text": [
51+
"Delete the stack: <code>cdk destroy</code>."
52+
]
53+
},
54+
"authors": [
55+
{
56+
"name": "Nithin Chandran R",
57+
"bio": "Technical Account Manager at AWS",
58+
"linkedin": "nithin-chandran-r"
59+
}
60+
],
61+
"patternArch": {
62+
"icon1": {
63+
"x": 20,
64+
"y": 50,
65+
"service": "lambda",
66+
"label": "AWS Lambda durable function"
67+
},
68+
"icon2": {
69+
"x": 80,
70+
"y": 50,
71+
"service": "bedrock",
72+
"label": "Amazon Bedrock"
73+
},
74+
"line1": {
75+
"from": "icon1",
76+
"to": "icon2",
77+
"label": "Request ANY {proxy+}"
78+
}
79+
}
80+
}
Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
import * as cdk from "aws-cdk-lib";
2+
import * as lambda from "aws-cdk-lib/aws-lambda";
3+
import * as iam from "aws-cdk-lib/aws-iam";
4+
import { Construct } from "constructs";
5+
6+
export class LambdaDurableBedrockStack extends cdk.Stack {
7+
constructor(scope: Construct, id: string, props?: cdk.StackProps) {
8+
super(scope, id, props);
9+
10+
const modelId = new cdk.CfnParameter(this, "BedrockModelId", {
11+
type: "String",
12+
default: "us.anthropic.claude-sonnet-4-20250514-v1:0",
13+
description: "Bedrock model ID (inference profile) to use",
14+
});
15+
16+
// Lambda function with durable execution enabled
17+
const fn = new lambda.Function(this, "DurableBedrockFn", {
18+
runtime: lambda.Runtime.NODEJS_20_X,
19+
handler: "index.handler",
20+
code: lambda.Code.fromAsset("src"),
21+
timeout: cdk.Duration.minutes(15),
22+
memorySize: 256,
23+
environment: {
24+
MODEL_ID: modelId.valueAsString,
25+
},
26+
});
27+
28+
// Enable durable execution via CfnFunction escape hatch
29+
const cfnFn = fn.node.defaultChild as lambda.CfnFunction;
30+
cfnFn.addOverride("Properties.Runtime", "nodejs24.x");
31+
cfnFn.addOverride("Properties.DurableConfig", {
32+
ExecutionTimeout: 900, // 15 minutes max durable execution
33+
RetentionPeriodInDays: 14,
34+
});
35+
36+
// Bedrock InvokeModel — scoped to the specific inference profile and its
37+
// underlying foundation model rather than a wildcard resource.
38+
fn.addToRolePolicy(
39+
new iam.PolicyStatement({
40+
actions: ["bedrock:InvokeModel"],
41+
resources: [
42+
`arn:aws:bedrock:${this.region}:${this.account}:inference-profile/${modelId.valueAsString}`,
43+
"arn:aws:bedrock:*::foundation-model/*",
44+
],
45+
})
46+
);
47+
48+
// Durable execution + CloudWatch Logs permissions via AWS managed policy
49+
// https://docs.aws.amazon.com/aws-managed-policy/latest/reference/AWSLambdaBasicDurableExecutionRolePolicy.html
50+
fn.role!.addManagedPolicy(
51+
iam.ManagedPolicy.fromAwsManagedPolicyName(
52+
"service-role/AWSLambdaBasicDurableExecutionRolePolicy"
53+
)
54+
);
55+
56+
// Publish a version via L1 — fn.currentVersion doesn't recognise the
57+
// DurableConfig escape-hatch property on CDK 2.180.
58+
const cfnVersion = new lambda.CfnVersion(this, "DurableBedrockFnVersion", {
59+
functionName: fn.functionName,
60+
description: "Durable execution version",
61+
});
62+
63+
new cdk.CfnOutput(this, "FunctionName", { value: fn.functionName });
64+
new cdk.CfnOutput(this, "FunctionArn", { value: fn.functionArn });
65+
new cdk.CfnOutput(this, "FunctionVersion", {
66+
value: cfnVersion.attrVersion,
67+
description: "Published version number — use as --qualifier value",
68+
});
69+
}
70+
}
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
{
2+
"name": "lambda-durable-bedrock-cdk",
3+
"version": "1.0.0",
4+
"bin": {
5+
"app": "bin/app.ts"
6+
},
7+
"scripts": {
8+
"build": "tsc",
9+
"cdk": "cdk"
10+
},
11+
"dependencies": {
12+
"aws-cdk-lib": "2.180.0",
13+
"constructs": "10.4.2"
14+
},
15+
"devDependencies": {
16+
"@types/node": "^22.0.0",
17+
"ts-node": "^10.9.0",
18+
"typescript": "~5.7.0"
19+
}
20+
}

0 commit comments

Comments
 (0)