SNS topic not publishing to SQS
Solution 1
This was posted a while back on the AWS forums: https://forums.aws.amazon.com/thread.jspa?messageID=202798
Then I gave the SNS topic the permission to send messages to the SQS queue. The trick here is to allow all principals. SNS doesn't send from your account ID -- it has its own account ID that it sends from.
Solution 2
Adding to Skyler's answer, if like me you cringe at the idea of allowing any principal (Principal: '*'
), you can restrict the principal to SNS:
Principal:
Service: sns.amazonaws.com
Although this behavior is undocumented, it works.
Solution 3
Here's a full CloudFormation example of Skyler's answer
{
"Resources": {
"MyTopic": {
"Type": "AWS::SNS::Topic"
},
"MyQueue": {
"Type": "AWS::SQS::Queue"
},
"Subscription": {
"Type" : "AWS::SNS::Subscription",
"Properties" : {
"Protocol" : "sqs",
"TopicArn" : {"Ref": "MyTopic"},
"Endpoint": {"Fn::GetAtt": ["MyQueue", "Arn"]}
}
},
"QueuePolicy": {
"Type": "AWS::SQS::QueuePolicy",
"Properties": {
"Queues": [
{"Ref": "MyQueue"}
],
"PolicyDocument": {
"Version": "2012-10-17",
"Statement": [
{
"Sid": "allow-sns-messages",
"Effect": "Allow",
"Principal": {"Service": "sns.amazonaws.com"},
"Action": "sqs:SendMessage",
"Resource": {"Fn::GetAtt": ["MyQueue", "Arn"]},
"Condition": {
"ArnEquals": {
"aws:SourceArn": {"Ref": "MyTopic"}
}
}
}
]
}
}
}
}
}
Amazon has more options in their Sending Amazon SNS Messages to Amazon SQS Queues document.
Solution 4
Most of the answers (beside @spg answer) propose usage of principal: *
- this is very dangerous practice and it will expose your SQS to whole world.
From AWS docs
For resource-based policies, such as Amazon S3 bucket policies, a wildcard (*) in the principal element specifies all users or public access.
We strongly recommend that you do not use a wildcard in the Principal element in a role's trust policy unless you otherwise restrict access through a Condition element in the policy. Otherwise, any IAM user in any account in your partition can access the role.
Therefore it is strongly not recommended to use this principal.
Instead you need to specify sns service as your principal:
"Principal": {
"Service": "sns.amazonaws.com"
},
Example policy:
{
"Version": "2012-10-17",
"Id": "Policy1596186813341",
"Statement": [
{
"Sid": "Stmt1596186812579",
"Effect": "Allow",
"Principal": {
"Service": "sns.amazonaws.com"
},
"Action": [
"sqs:SendMessage",
"sqs:SendMessageBatch"
],
"Resource": "Your-SQS-Arn"
}
]
}
With this policy sns will be able to send messages to your SQSs.
There are more permissions for SQS but from what I see SendMessage
and SendMessageBatch
should be enough for SNS->SQS subscribtion.
Solution 5
Old question but using an AWS SDK version > 1.10
Check out the docs SQS-SNS sendMessage Permission
private static void updateQueuePolicy(AmazonSQS sqs, String queueURL, String topicARN) {
Map<String, String> attributes = new HashMap<String, String>(1);
Action actions = new Action() {
@Override
public String getActionName() {
return "sqs:SendMessage"; // Action name
}
};
Statement mainQueueStatements = new Statement(Statement.Effect.Allow)
.withActions(actions)
.withPrincipals(new Principal("Service", "sns.amazonaws.com"))
.withConditions(
new Condition()
.withType("ArnEquals")
.withConditionKey("aws:SourceArn")
.withValues(topicARN)
);
final Policy mainQueuePolicy = new Policy()
.withId("MainQueuePolicy")
.withStatements(mainQueueStatements);
attributes.put("Policy", mainQueuePolicy.toJson());
updateQueueAttributes(sqs, queueURL, attributes);
}
Which outputs a policy similar to
{
Policy={
"Version":"2012-10-17",
"Id":"MainQueuePolicy",
"Statement":
[
{
"Sid":"1",
"Effect":"Allow",
"Principal": {
"Service": "sns.amazonaws.com"
},
"Action":["sqs:SendMessage"],
"Condition":
{"ArnEquals":
{"aws:SourceArn":["arn:aws:sns:us-east-1:3232:testSubscription"]}
}
}
]
}
}
user427875
Updated on July 09, 2022Comments
-
user427875 almost 2 years
I am trying to prototype a distributed application using SNS and SQS.I have this topic:
arn:aws:sns:us-east-1:574008783416:us-east-1-live-auction
and this queue:
arn:aws:sqs:us-east-1:574008783416:queue4
I created the queue using the JS Scratchpad. I added the subscription using the Console. I AddPermission to the queue using the scratchpad. The queue policy is now:
{ "Version":"2008-10-17", "Id":"arn:aws:sqs:us-east-1:574008783416:queue4/SQSDefaultPolicy", "Statement":[ { "Sid":"RootPerms", "Effect":"Allow", "Principal":{ "AWS":"574008783416" }, "Action":"SQS:*", "Resource":"arn:aws:sqs:us-east-1:574008783416:queue4" } ] }
I have an email subscription on the same topic and the emails arrive fine but the messages never arrive on the queue. I've tried SendMessage directly to the queue - rather than via SNS - using Scratchpad and it works fine. Any ideas why it won't send to the queue?
-
user427875 about 13 yearsThank you, thank you. Had an open ticket with AWS support and have begged them to add this answer to the Policy Examples in the docs.
-
Digitalkapitaen over 5 yearsAs far as I can tell, the Statement needs to include a Resource property: "Resource": { "Fn::GetAtt": ["MyQueue", "Arn" ] },
-
k.liakos about 5 yearsInstead of queueARN you probably meant topicARN.
-
Kris about 4 yearsYou'll want to restrict access to the sourceArn: docs.aws.amazon.com/sns/latest/dg/…
-
Shoter almost 4 yearsThis is very bad answer. By doing that everyone can send messages from this topic. Users should seek policies that are allowing them to do things they desire while being the most restrictive policies they can have - it's safer. i think that your SQS is going to be public after using * as principal.
-
Shoter almost 4 yearsThis is correct answer to the problem. By doing things this way you will not expose your SQS to whole world.
-
Sandeep K Nair about 3 yearsWow this was the working solution for me after hours of trying out others, Thanks a ton :)
-
borjab about 3 years
-
Shoter about 3 yearsThanks for updating your answer to faciliate correct Principal! :)
-
Harshit almost 3 yearsDo you know if SNS uses
SendMessageBatch
to lower cost? -
piggybox over 2 yearsThis is a fine answer. I'm surprised when I connect SNS to SQS in AWS console, it doesn't do the permission part automatically.
-
dnc253 almost 2 yearsI found this documented on step 2 of this guide: docs.aws.amazon.com/sns/latest/dg/…
-
Shadman R almost 2 yearsThe link to the aws forum has been archived, it is always better option to put the context of the answer you are proposing along with the link.