I am trying to create a s3 bucket that sends notification to a SNS topic every time an object is dropped in the s3 bucket. My S3 bucket is called foo-bucket
and my SNS topic is called foo-topic
. I know how to setup this in aws console but i am having trouble when trying to do this via cloudformation.
This is the code i currently have
Resources:
SNSTopic:
Type: AWS::SNS::Topic
Properties:
TopicName: foo-topic
SNSTopicPolicy:
Type: AWS::SNS::TopicPolicy
Properties:
PolicyDocument:
Id: MyTopicPolicy
Version: '2012-10-17'
Statement:
- Sid: Statement-id
Effect: Allow
Principal:
Service: s3.amazonaws.com
Action: sns:Publish
Resource:
Ref: SNSTopic
Condition:
ArnLike:
aws:SourceArn:
Fn::Join:
- ''
- - 'arn:aws:s3:::'
- Ref: S3Bucket
Topics:
- Ref: SNSTopic
S3Bucket:
Type: AWS::S3::Bucket
Properties:
BucketName: foo-bucket
AccessControl: BucketOwnerFullControl
NotificationConfiguration:
TopicConfigurations:
- Topic:
Ref: SNSTopic
Event: s3:ObjectCreated:Put
I try to deploy the above and cfn rollsback due to the following error
Unable to validate the following destination configurations (Service: Amazon S3; Status Code: 400; Error Code: InvalidArgument; Request ID: fooooo; S3 Extended Request ID: foooid; Proxy: null)
I have an example cloudformation creating a bucket, sns topic and a notification configuration. As already mentioned, you need to ensure proper dependency order.
The notification configuration doesn't check for the resource existence, so we need to use the DependsOn
property to do so
As well be aware of potential circular reference, when creating an SNS Topic Policy. I defined the bucket name as a string, not reference. It allows to create an SNS with its policy before the notification config of the bucket.
IngestionBucketDev:
Type: AWS::S3::Bucket
DependsOn:
- IngestionTopicDev
- IngestionTopicPolicy
Properties:
BucketName: "ingestion-codebucket-7832df8b-dev"
NotificationConfiguration:
TopicConfigurations:
- Topic: !Ref IngestionTopicDev
Event: 's3:ObjectCreated:*'
Filter:
S3Key:
Rules:
- Name: suffix
Value: ".json"
PublicAccessBlockConfiguration:
RestrictPublicBuckets: true
BlockPublicPolicy: true
IngestionTopicDev:
Type: AWS::SNS::Topic
Properties:
TopicName: "elearn-ingest-topic"
DisplayName: "elearn-ingest-topic"
IngestionTopicPolicy:
Type: AWS::SNS::TopicPolicy
Properties:
Topics:
- !Ref IngestionTopicDev
PolicyDocument:
Version: 2012-10-17
Statement:
- Action:
- 'sns:Publish'
Effect: Allow
Resource: !Ref IngestionTopicDev
Principal:
Service: "s3.amazonaws.com"
Condition:
ArnEquals:
"aws:SourceArn": "arn:aws:s3:::ingestion-codebucket-7832df8a-dev"