Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

New serverless pattern - s3-lambda-bedrock-js-sam #2285

Open
wants to merge 3 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions s3-lambda-bedrock-js-sam/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
.aws-sam
samconfig.toml
72 changes: 72 additions & 0 deletions s3-lambda-bedrock-js-sam/README.md

Large diffs are not rendered by default.

69 changes: 69 additions & 0 deletions s3-lambda-bedrock-js-sam/example-pattern.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
{
"title": "Amazon S3 to AWS Lambda to Amazon Bedrock using AWS SAM",
"description": "This pattern facilitates generating vector embeddings for text data uploaded to S3.",
"language": "Node.js",
"level": "200",
"framework": "SAM",
"introBox": {
"headline": "How it works",
"text": [
"When a new object is uploaded to an S3 bucket, S3 detects the putObject event and invokes a Lambda function asynchronously, passing details about the uploaded object. The Lambda function then retrieves the object's content and sends it to the Amazon Bedrock Titan Embedding service, which generates vector embeddings representing the content's meaning and context."
]
},
"gitHub": {
"template": {
"repoURL": "https://github.com/aws-samples/serverless-patterns/tree/main/s3-lambda-bedrock-js-sam",
"templateURL": "serverless-patterns/s3-lambda-bedrock-js-sam",
"projectFolder": "s3-lambda-bedrock-js-sam",
"templateFile": "template.yaml"
}
},
"resources": {
"bullets": [
{
"text": "Amazon S3",
"link": "https://docs.aws.amazon.com/AmazonS3/latest/userguide/Welcome.html"
},
{
"text": "AWS Lambda",
"link": "https://docs.aws.amazon.com/lambda/latest/dg/welcome.html"
},
{
"text": "Amazon Bedrock",
"link": "https://docs.aws.amazon.com/bedrock/latest/userguide/what-is-bedrock.html"
}
]
},
"deploy": {
"text": [
"sam build",
"sam deploy --guided"
]
},
"testing": {
"text": [
"See the GitHub repo for detailed testing instructions."
]
},
"cleanup": {
"text": [
"sam delete"
]
},
"authors": [
{
"name": "Achintya Veer Singh",
"image": "https://avatars.githubusercontent.com/u/55053737?v=4",
"bio": "Solutions Architect @ AWS",
"linkedin": "www.linkedin.com/in/achintya-veer-singh-493403193",
"twitter": "achintya_veer"
},
{
"name": "Rohit Raj",
"image": "https://avatars.githubusercontent.com/u/69171887?v=4",
"bio": "Solutions Architect @ AWS",
"linkedin": "https://www.linkedin.com/in/rohitraj-11",
"twitter": "RohitRaj_11"
}
]
}
97 changes: 97 additions & 0 deletions s3-lambda-bedrock-js-sam/s3-lambda-bedrock-js-sam.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
{
"title": "Amazon S3 to AWS Lambda to Amazon Bedrock using AWS SAM",
"description": "This pattern facilitates generating vector embeddings for text data uploaded to S3.",
"language": "Node.js",
"level": "200",
"framework": "SAM",
"introBox": {
"headline": "How it works",
"text": [
"When a new object is uploaded to an S3 bucket, S3 detects the putObject event and invokes a Lambda function asynchronously, passing details about the uploaded object. The Lambda function then retrieves the object's content and sends it to the Amazon Bedrock Titan Embedding service, which generates vector embeddings representing the content's meaning and context."
]
},
"gitHub": {
"template": {
"repoURL": "https://github.com/aws-samples/serverless-patterns/tree/main/s3-lambda-bedrock-js-sam",
"templateURL": "serverless-patterns/s3-lambda-bedrock-js-sam",
"projectFolder": "s3-lambda-bedrock-js-sam",
"templateFile": "template.yaml"
}
},
"resources": {
"bullets": [
{
"text": "Amazon S3",
"link": "https://docs.aws.amazon.com/AmazonS3/latest/userguide/Welcome.html"
},
{
"text": "AWS Lambda",
"link": "https://docs.aws.amazon.com/lambda/latest/dg/welcome.html"
},
{
"text": "Amazon Bedrock",
"link": "https://docs.aws.amazon.com/bedrock/latest/userguide/what-is-bedrock.html"
}
]
},
"deploy": {
"text": [
"sam build",
"sam deploy --guided"
]
},
"testing": {
"text": [
"See the GitHub repo for detailed testing instructions."
]
},
"cleanup": {
"text": [
"sam delete"
]
},
"authors": [
{
"name": "Achintya Veer Singh",
"image": "https://avatars.githubusercontent.com/u/55053737?v=4",
"bio": "Solutions Architect @ AWS",
"linkedin": "achintya-veer-singh-493403193",
"twitter": "achintya_veer"
},
{
"name": "Rohit Raj",
"image": "https://avatars.githubusercontent.com/u/69171887?v=4",
"bio": "Solutions Architect @ AWS",
"linkedin": "rohitraj-11",
"twitter": "RohitRaj_11"
}
],
"patternArch": {
"icon1": {
"x": 20,
"y": 50,
"service": "s3",
"label": "Amazon S3"
},
"icon2": {
"x": 50,
"y": 50,
"service": "lambda",
"label": "AWS Lambda"
},
"icon3": {
"x": 80,
"y": 50,
"service": "bedrock",
"label": "Amazon Bedrock"
},
"line1": {
"from": "icon1",
"to": "icon2"
},
"line2": {
"from": "icon2",
"to": "icon3"
}
}
}
3 changes: 3 additions & 0 deletions s3-lambda-bedrock-js-sam/sample.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
Peace is a state of tranquility, calm, and harmony, free from violence, conflict, or hostility.
It is a fundamental human aspiration, as it allows for the flourishing of individuals, communities, and nations.
Achieving lasting peace requires a concerted effort to address the root causes of violence, foster understanding and respect among diverse groups, and promote justice, equality, and sustainable development.
53 changes: 53 additions & 0 deletions s3-lambda-bedrock-js-sam/src/index.mjs
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
import { S3Client, GetObjectCommand } from "@aws-sdk/client-s3";
import {
BedrockRuntimeClient,
InvokeModelCommand,
} from "@aws-sdk/client-bedrock-runtime";

const awsS3Client = new S3Client();
const awsBedrockClient = new BedrockRuntimeClient();

const fetchFileFromS3 = async (bucketName, fileKey) => {
const command = new GetObjectCommand({
Bucket: bucketName,
Key: fileKey,
});
const response = await awsS3Client.send(command);
const fileContent = response.Body
? await response.Body.transformToString()
: "";
return fileContent;
};

export const handler = async (event) => {
if (!event || !event.Records) {
return {
statusCode: 200,
body: JSON.stringify({ message: "No S3 event detected" }),
};
}

const eventRecord = event.Records[0];
const bucketName = eventRecord.s3.bucket.name;
const fileName = decodeURIComponent(eventRecord.s3.object.key);
const fileContent = await fetchFileFromS3(bucketName, fileName);

const bedrockModelInput = {
modelId: "amazon.titan-embed-text-v1",
contentType: "application/json",
accept: "*/*",
body: JSON.stringify({ inputText: JSON.stringify(fileContent) }),
};
console.log("Input provided to Bedrock", bedrockModelInput);

const bedrockCommand = new InvokeModelCommand(bedrockModelInput);
const bedrockResponse = await awsBedrockClient.send(bedrockCommand);

const responseData = Buffer.from(bedrockResponse.body).toString();
console.log("Response data: ", responseData);

return {
statusCode: 200,
body: JSON.stringify(responseData),
};
};
76 changes: 76 additions & 0 deletions s3-lambda-bedrock-js-sam/template.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
AWSTemplateFormatVersion: "2010-09-09"
Transform: AWS::Serverless-2016-10-31

Description: This pattern facilitates intelligent document processing by generating vector embeddings for text data uploaded to S3.

Parameters:
DocumentBucketName:
Type: String

Resources:
DocumentBucket:
Type: AWS::S3::Bucket
Properties:
BucketName: !Ref DocumentBucketName

DocumentEmbeddingFunction:
Type: AWS::Serverless::Function
Properties:
CodeUri: src/
Handler: index.handler
FunctionName: DocumentEmbedding
Description: Lambda function to generate embeddings for uploaded documents
Runtime: nodejs18.x
Timeout: 10
MemorySize: 128
Role: !GetAtt DocumentEmbeddingFunctionExecutionRole.Arn
Events:
FileUpload:
Type: S3
Properties:
Bucket: !Ref DocumentBucket
Events: s3:ObjectCreated:*
Filter:
S3Key:
Rules:
- Name: prefix
Value: "content/"

DocumentEmbeddingFunctionExecutionRole:
Type: AWS::IAM::Role
Properties:
AssumeRolePolicyDocument:
Version: "2012-10-17"
Statement:
- Effect: Allow
Principal:
Service:
- lambda.amazonaws.com
Action:
- "sts:AssumeRole"
ManagedPolicyArns:
- arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole
Policies:
- PolicyName: CustomPolicy
PolicyDocument:
Version: "2012-10-17"
Statement:
- Effect: Allow
Action:
- s3:GetObject
- s3:ListBucket
Resource:
- !Sub "arn:aws:s3:::${DocumentBucketName}/*"
- !Sub "arn:aws:s3:::${DocumentBucketName}"
- Effect: Allow
Action:
- bedrock:InvokeModel
Resource: "*"

Outputs:
DocumentBucket:
Description: S3 bucket for storing documents
Value: !Ref DocumentBucket
DocumentEmbeddingFunction:
Value: !Ref DocumentEmbeddingFunction
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This would not return an ARN but Function Name

Description: Lambda Function ARN for generating document embeddings