I created a Lambda function which takes data from one SQS queue, perform some modifications and should put the output data to another SQS queue. But trying to specify the Destination, I'm getting the empty list of SQS queues:
Could you please help me?
Permissions for Lambda function are provided:
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"sqs:SendMessage",
"sqs:DeleteMessage",
"sqs:ChangeMessageVisibility",
"sqs:ReceiveMessage",
"sqs:TagQueue",
"sqs:UntagQueue",
"sqs:PurgeQueue"
],
"Resource": "arn:aws:sqs:eu-west-1:myaccountid:my-queue.fifo"
}
]
}
Tried two configurations of Access Policy for SQS queue. With VPC:
{
"Version": "2008-10-17",
"Id": "__default_policy_ID",
"Statement": [
{
"Sid": "__owner_statement",
"Effect": "Allow",
"Principal": {
"AWS": "*"
},
"Action": "SQS:*",
"Resource": "arn:aws:sqs:eu-west-1:myacy-queuecountid:m.fifo",
"Condition": {
"StringEquals": {
"aws:SourceVpc": "my-vpc"
}
}
}
]
}
and Principal Account:
{
"Version": "2008-10-17",
"Id": "__default_policy_ID",
"Statement": [
{
"Sid": "__owner_statement",
"Effect": "Allow",
"Principal": {
"AWS": "*"
},
"Action": "SQS:*",
"Resource": "arn:aws:sqs:eu-west-1:myaccountid:my-queue.fifo",
"Condition": {
"StringEquals": {
"aws:PrincipalAccount": [
"myaccountid"
]
}
}
}
]
}
(myaccountid, myqueue, my-vpc are the masks for valid values)
But result is the same - list of available SQS queues is empty
Destinations are only for asynchronous invocations of lambda. SQS invokes lambda synchronously, thus Destinations do not apply. This is not the cause why it does not show up in your list, but you would never be able to use in the first place due to Destinations with SQS invoking lambda.
AWS Asynchronous invocation
You can also configure Lambda to send an invocation record to another service. Lambda supports the following destinations for asynchronous invocation.
Amazon SQS – A standard SQS queue.
Amazon SNS – An SNS topic.
AWS Lambda – A Lambda function.
Amazon EventBridge – An EventBridge event bus.
The invocation record contains details about the request and response in JSON forma.
The SQS queue must be standard, your queue is fifo.
You can send a message to a fifo queue using an SDK.
Related
I want to allow only ONE lambda (arn:aws:lambda:ap-southeast-2:444455556666:function:source-lambda) function to send messages to my SQS queue (arn:aws:sqs:ap-southeast-2:444455556666:target-sqs). So I attached the below Access Policy to my SQS queue. However, this policy is not allowing the specified Lambda to send messages to the SQS queue, and returning AccessDenied exception.
{
"Version": "2012-10-17",
"Id": "Policy1666948352567",
"Statement": [
{
"Sid": "Stmt1666948347116",
"Effect": "Deny",
"Principal": "*",
"Action": "sqs:SendMessage",
"Resource": "arn:aws:sqs:ap-southeast-2:444455556666:target-sqs",
"Condition": {
"ArnNotEquals": {
"aws:SourceArn": "arn:aws:lambda:ap-southeast-2:444455556666:function:source-lambda"
}
}
}
]
}
Problem :
Policy rules follow, this Priority
Explicit Deny ( Highest ) --> Explicit Allow --> Implicit Deny ( Default )
Here in your policy, you have defined explicit denied for all other resources which are not arn:aws:lambda:ap-southeast-2:444455556666:function:source-lambda
But you haven't explicitly allowed the lambda to send a message to that SQS, so Implicit deny applied and hence you are receiving Access Denied
Solution :
Why don't you use "Effect": "Allow", and "ArnEquals":, this will satisfy your use case by only allowing that specific lambda to send a message.
{
"Version": "2012-10-17",
"Id": "Policy1666948352567",
"Statement": [
{
"Sid": "Stmt1666948347116",
"Effect": "Allow", // <---- HERE
"Principal": "*",
"Action": "sqs:SendMessage",
"Resource": "arn:aws:sqs:ap-southeast-2:444455556666:target-sqs",
"Condition": {
"ArnEquals": { // <--- HERE
"aws:SourceArn": "arn:aws:lambda:ap-southeast-2:444455556666:function:source-lambda"
}
}
}
]
}
I have a scenario whereby I want to create an SNS topic but apply resource policy such that only certain endpoints are allowed to subscribe to it. e.g
{
"Version": "2008-10-17",
"Id": "__default_policy_ID",
"Statement": [
{
"Sid": "__console_pub_0",
"Effect": "Allow",
"Principal": {
"AWS": "arn:aws:iam::555555555:root"
},
"Action": "SNS:Publish",
"Resource": "arn:aws:sns:eu-west-1:555555555:hafiz-test"
},
{
"Sid": "__console_sub_0",
"Effect": "Allow",
"Principal": {
"AWS": "arn:aws:iam::555555554:root"
},
"Action": [
"SNS:Subscribe",
"SNS:Receive"
],
"Resource": "arn:aws:sns:eu-west-1:555555555:hafiz-test",
"Condition": {
"StringLike": {
"SNS:Endpoint": "arn:aws:sqs:eu-west-1:555555554:hafiz-test"
}
}
}
]
}
This scenario works perfectly in a scenario where the SQS subscribing to the SNS topic is across another account so unless I list the SQS arn "SNS:Endpoint": "arn:aws:sqs:eu-west-1:555555554:hafiz-test" in the condition subscription fails with permissions.
I want to achieve the same thing for any SQS queues that are in the SNS owner account. At the moment any SQS resource in the same account as SNS can subscribe to the SNS topic
Thanks much appreciated.
I've a encrypted SQS queue and SNS topic by custom managed KMS key. Currently I'm using a similar kind of SQS policy stated in the below link where it is working fine SQS Policy
But if i use the below SQS policy it's not working. I don't want to have Principal as '*' due to security reasons. Can someone explain me why is this happening
{
"Version":"2012-10-17",
"Statement":[
{
"Sid":"MySQSPolicy001",
"Effect":"Allow",
"Principal":{
"AWS": "arn:aws:iam::123456789012:root"
},
"Action":"sqs:SendMessage",
"Resource":"arn:aws:sqs:us-east-1:123456789012:MyQueue"
}
]
}
So if you've a condition with SNS arn in your queue policy when more than one topic needs to publish to same queue you might need to add the ARN again & again.
So the workaround will be the below policy.
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "Queue1_SendMessage",
"Effect": "Allow",
"Principal": {
"Service": "sns.amazonaws.com",
"AWS": "arn:aws:iam::1234567890:root"
},
"Action": [
"sqs:SendMessage",
"sqs:ReceiveMessage",
"sqs:DeleteMessage"
],
"Resource": "arn:aws:sqs:eu-central-1:1234567890:test-queue",
"Condition": {
"StringEquals": {
"aws:SourceAccount": "1234567890"
}
}
}
]
}
I have a NodeJS application that publishes message to AWS SNS topic string and a AWS SQS subscription for the same. On the SQS console, I can see the published message. However, I am not clear with the access policy of the SQS queue.
This answer mentions the use of "Principal": "*" - but, that is very broad. One could probably use "Principal" : {"AWS": "*"}; but, that isn't narrow either.
{
"Version": "2012-10-17",
"Id": "Policy1607949016538",
"Statement": [
{
"Sid": "Stmt1607949012567",
"Effect": "Allow",
"Principal": "*",
"Action": [
"sqs:ReceiveMessage",
"sqs:SendMessage"
],
"Resource": "arn:aws:sqs:ap-south-1:463113000000:orders"
}
]
}
Questions
While delivering a message to SQS queue, as a result of subscription, which user is in effect? Same as the one who published to the topic?
I could get the messages to flow into the queue only when I used "Principal" : {"AWS": "*"}. So, how should I define a restrictive policy such that messages are written to queues only as a result of subscription?
What is the equivalent in the AWS SQS CLI to create a queue with "Principal" : {"AWS": "*"} permissions?
The only user that matters is the one that qualifies for the policy as defined for subscription and SQS access policy.
The Condition in policy document can make the overall policy restrictive. See example below.
Adding SQS Permissions with conditions using AWS CLI Command
Example policy document restricting access to account ID.
{
"Version": "2012-10-17",
"Id": "Policy1607960702002",
"Statement": [
{
"Sid": "Stmt1607960701004",
"Effect": "Allow",
"Principal": {
"AWS": "*"
},
"Action": [
"sqs:ReceiveMessage",
"sqs:SendMessage"
],
"Resource": "arn:aws:sqs:ap-south-1:463113000000:orders",
"Condition": {
"StringEquals": {
"aws:SourceAccount": "463113000000"
}
}
}
]
}
I have an SNS topic TestTopic, I have an SQS queue newtestqueue-ev, I have a java application that will push messages to either the topic or the queue. I have a Java application that reads from the queue.
When I push to the queue via java app / aws console I receive the message in my application. When I push a message to the topic which has the SQS queue as a subscriber I do not receive any message.
Here is permission added to the SQS queue
{
"Version": "2012-10-17",
"Id": "arn:aws:sqs:eu-west-1:<accountnum>:newtestqueue-ev/SQSDefaultPolicy",
"Statement": [
{
"Sid": "sidNum",
"Effect": "Allow",
"Principal": {
"AWS": "*"
},
"Action": "SQS:SendMessage",
"Resource": "arn:aws:sqs:eu-west-1:<accountNum>:newtestqueue-ev",
"Condition": {
"ArnEquals": {
"aws:SourceArn": "arn:aws:sns:eu-west-1:<accountNum>:TestTopic"
}
}
}
]
}
I have encryption enabled on the queue using the default key alias/aws/sqs and encryption on the sns topic using the default alias/aws/sns
You can not use the default kms key on the SNS queue, you need to create a new one and add this to it
{
"Effect": "Allow",
"Principal": {
"Service": "sns.amazonaws.com"
},
"Action": [
"kms:GenerateDataKey*",
"kms:Decrypt"
],
"Resource": "*"
}