I would like to use the below cloudformation template to create multiple event notifications on a single existing S3 bucket. However, even if I specify another "LambdaFunctionConfigurations" under the BucketConfiguration resource I only see one event created on the S3 bucket. I've also tried creating another BucketConfiguration resource with a separate event configured without any luck. I'm looking for any tips or advice that would help point me in the right direction. From what I gather the s3.putBucketNotification method will clear any existing event notification configuration. Please keep in mind that the CF template does create a single event notification (I'm looking to create multiple event notifications).
Model for below template: Create a Lambda notification in an S3 bucket with CloudFormation
Description: >-
Create an event notification for an existing S3 bucket
Parameters:
BucketName:
Description: S3 Bucket name (must already exist)
Type: String
Resources:
BucketConfiguration:
Type: 'Custom::S3BucketConfiguration'
DependsOn:
- BucketPermission
- NotificationBucketPolicy
Properties:
ServiceToken: !GetAtt S3BucketConfiguration.Arn
Bucket: !Ref BucketName
NotificationConfiguration:
LambdaFunctionConfigurations:
- Events:
- 's3:ObjectCreated:*'
LambdaFunctionArn: MyLambdaArn
Metadata:
'AWS::CloudFormation::Designer':
id: 606b322f-42fa-4d20-bae4-53374d7ad7ba
S3BucketConfiguration:
Type: 'AWS::Lambda::Function'
Properties:
Description: S3 Object Custom Resource
Handler: index.handler
Role: !GetAtt LambdaExecutionRole.Arn
Code:
ZipFile: !Sub |
var response = require('cfn-response');
var AWS = require('aws-sdk');
var s3 = new AWS.S3();
exports.handler = function(event, context) {
var respond = (e) => response.send(event, context, e ? response.FAILED : response.SUCCESS, e ? e : {});
process.on('uncaughtException', e=>failed(e));
var params = event.ResourceProperties;
delete params.ServiceToken;
if (event.RequestType === 'Delete') {
params.NotificationConfiguration = {};
s3.putBucketNotificationConfiguration(params).promise()
.then((data)=>respond())
.catch((e)=>respond());
} else {
s3.putBucketNotificationConfiguration(params).promise()
.then((data)=>respond())
.catch((e)=>respond(e));
}
};
Timeout: 30
Runtime: nodejs6.10
Metadata:
'AWS::CloudFormation::Designer':
id: 1cefd553-f888-4b3b-8184-d96932a29227
BucketPermission:
Type: 'AWS::Lambda::Permission'
Properties:
Action: 'lambda:InvokeFunction'
Principal: s3.amazonaws.com
SourceAccount: !Ref 'AWS::AccountId'
SourceArn: !Sub 'arn:aws:s3:::${BucketName}'
Metadata:
'AWS::CloudFormation::Designer':
id: 29f90f84-cfd0-43d2-8c2b-c173ec96c409
LambdaExecutionRole:
Type: 'AWS::IAM::Role'
Properties:
AssumeRolePolicyDocument:
Version: 2012-10-17
Statement:
- Effect: Allow
Principal:
Service:
- lambda.amazonaws.com
Action:
- 'sts:AssumeRole'
Path: /
ManagedPolicyArns:
- 'arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole'
Policies:
- PolicyName: S3Policy
PolicyDocument:
Version: 2012-10-17
Statement:
- Effect: Allow
Action:
- 's3:PutObject'
- 'S3:DeleteObject'
Resource: !Sub 'arn:aws:s3:::${BucketName}'
Metadata:
'AWS::CloudFormation::Designer':
id: 3556f770-b7cd-4ac1-8afa-62a0319721b8
NotificationBucketPolicy:
Type: 'AWS::S3::BucketPolicy'
Properties:
Bucket: !Ref BucketName
PolicyDocument:
Statement:
- Effect: Allow
Action:
- 's3:PutBucketNotification'
Resource: !Sub 'arn:aws:s3:::${BucketName}'
Principal:
AWS: !GetAtt LambdaExecutionRole.Arn
Metadata:
'AWS::CloudFormation::Designer':
id: 1f82086e-0d71-4731-8173-e3b8ee0da4dd
Metadata:
'AWS::CloudFormation::Designer':
3556f770-b7cd-4ac1-8afa-62a0319721b8:
size:
width: 60
height: 60
position:
x: 60
'y': 90
z: 1
embeds: []
1f82086e-0d71-4731-8173-e3b8ee0da4dd:
size:
width: 60
height: 60
position:
x: 180
'y': 90
z: 1
embeds: []
29f90f84-cfd0-43d2-8c2b-c173ec96c409:
size:
width: 60
height: 60
position:
x: 410
'y': 90
z: 1
embeds: []
1cefd553-f888-4b3b-8184-d96932a29227:
size:
width: 60
height: 60
position:
x: 300
'y': 190
z: 1
embeds: []
606b322f-42fa-4d20-bae4-53374d7ad7ba:
size:
width: 60
height: 60
position:
x: 300
'y': 90
z: 1
embeds: []
dependson:
- 29f90f84-cfd0-43d2-8c2b-c173ec96c409
- 1f82086e-0d71-4731-8173-e3b8ee0da4dd
You are correct that it is not possible to have multiple Events defined for the same 'triggers'.
For example, in the S3 console I was successfully able to define:
However, I could not define multiple rules for the same event and same prefix. The error message was:
Configuration is ambiguously defined. Cannot have overlapping suffixes in two rules if the prefixes are overlapping for the same event type.
Based on your question, it appears you want to trigger multiple Lambda functions for the same event within the same prefix (which includes 'the whole bucket'). For that, I would recommend:
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With