Terraform: Is it possible to actually use the aws_sqs_queue's "policy" attribute?

Created on 19 Oct 2015  ·  17Comments  ·  Source: hashicorp/terraform

I'm trying to use this and I keep getting an InvalidAttributeValue from the AWS api. I think the problem is that, the policy requires a "Resource" identifier with the queue's ARN and we can't do that within Terraform directly as it creates dependency on itself. So I tried removing the Resource identifier to see if perhaps Terraform would magically add it. No joy there either. I think the ultimate solution for this would be to 1) implement said magic, that might not be the cleanest approach, 2) make something like a separate 'aws_sqs_policy' resource such that the references could work and the policy would be applied after the queue actually exists, 3) have terraform do some sort of deferred resolution when it sees a nested reference.

I guess 2 is probably the most inline with the way TF works now. TF would need something similar for say future support of s3 bucket notifications, they don't even work properly in CloudFormation as they're defined on the s3 resource, but CF doesn't wait for the bucket to actually exist prior to applying the notification. For now I'm just wrapping TF in a ruby script, that runs TF, then reads the state file and applies the policy,etc

enhancement new-resource provideaws

Most helpful comment

it finally works for me, here is my template for the sqs queue:

resource "aws_sqs_queue" "my-queue" {
    name = "${var.sqs_queue_name}"
    policy = <<EOF
{
    "Version": "2012-10-17",
    "Id": "arn:aws:sqs:${var.region}:${var.account_number}:${var.sqs_queue_name}/SQSPolicy",
    "Statement": [
        {
            "Sid": "1234567890",
            "Effect": "Allow",
            "Principal": {
                "AWS": "*"
            },
            "Action": "SQS:SendMessage",
            "Resource": "arn:aws:sqs:${var.region}:${var.account_number}:${var.sqs_queue_name}",
            "Condition": {
                "ArnLike": {
                    "aws:SourceArn": "arn:aws:s3:*:*:${var.s3_bucket}"
                }
            }
        }
    ]
}
EOF
}

All 17 comments

Hey @eoliphan – can you help me understand what you're looking for here? SQS does have a policy attribute, and it should be available for reference from another resource. Perhaps you have a configuration file that demonstrates what you're attempting?

Hi, here's an example. I want 'my queue' to accept bucket notifications from 'my bucket'. AFAIK, the 'Resource' key has to be defined when I'm adding this policy to 'my queue'. Since it's an ARN, it needs to 'my queue' needs to have already been created in order for this to work. And as I mentioned, I get errors to that effect. TF doesn't like it, when I set the Resource based on the ARN variable as I'm referring to 'myself' at that point, inside the resource block for 'my queue'

{
  "Version": "2012-10-17",
  "Id": "arn:aws:sqs:us-east-1:963129205572:myqueue/SQSDefaultPolicy",
  "Statement": [
    {
      "Sid": "",
      "Effect": "Allow",
      "Principal": {
        "AWS": "*"
      },
      "Action": "SQS:SendMessage",
      "Resource": "arn:aws:sqs:us-east-1:963129205572:myqueue",
      "Condition": {
        "ArnLike": {
          "aws:SourceArn": "arn:aws:s3:*:*:mybucket"
        }
      }
    }
  ]
}

+1
I also cannot see how one generates a policy with a valid "Resource" entry for the current queue instance.

Can we move the policy to it's own TF resource aws_sqs_queue_policy? That way we can reference the queue ARN. This would make it a 2 step operation but I think that's the only way. It's 2 steps via the console or API anyway.

Is it actually necessary to include the explicit Resource attribute in the inline queue policy? I don't have any experience with SQS in particular, but with other similar inline policies I've found that the resource attribute is automatically implied to be the resource the policy is attached to, and that the explicit Resource attribute is only needed for standalone policies that are used with e.g. aws_iam_policy_attachment.

In the underlying API the policy is a part of the attribute set provided to CreateQueue, rather than a distinct API operation, so I expect separating it into its own resource would be tricky.

@apparentlymart it seems so. I couldn't find documentation on it, but I ran a little functional test. Without theResource, a message I published to SNS never reached the queue. Once I added the resource in, new messages were passed onto the queue.

+1

I wonder then if Terraform has enough information to synthesize the Resource ARN itself... looks like we'd need the region, account id and queue name. The region and queue name shouldn't be a problem... account id might be harder, but I believe we have it in at least _some_ cases since we are able to implement the account id restriction attributes on the provider.

Is there any use-case for the policy on a given queue having a Resource other than the queue itself?

+1

Just ran into this. Looking for workaround.

+1

+1

it finally works for me, here is my template for the sqs queue:

resource "aws_sqs_queue" "my-queue" {
    name = "${var.sqs_queue_name}"
    policy = <<EOF
{
    "Version": "2012-10-17",
    "Id": "arn:aws:sqs:${var.region}:${var.account_number}:${var.sqs_queue_name}/SQSPolicy",
    "Statement": [
        {
            "Sid": "1234567890",
            "Effect": "Allow",
            "Principal": {
                "AWS": "*"
            },
            "Action": "SQS:SendMessage",
            "Resource": "arn:aws:sqs:${var.region}:${var.account_number}:${var.sqs_queue_name}",
            "Condition": {
                "ArnLike": {
                    "aws:SourceArn": "arn:aws:s3:*:*:${var.s3_bucket}"
                }
            }
        }
    ]
}
EOF
}

+1

I think this issue may be resolved by https://github.com/hashicorp/terraform/pull/8657 released in v0.7.3

Correct @conorgil aws_sqs_queue_policy was meant to address this problem.
Documentation is at https://www.terraform.io/docs/providers/aws/r/sqs_queue_policy.html

Do let us know if you have any issues with this new resource.

I have a similar sort of issue with some thing different, Now I don't want to write the policy in the terraform instead i created a custom policy in aws using console and and assigned to a user whose credentials i am using to execute my terraform script, but i have problem here. I have to set a condition into the policy so that i can dynamically pass the topic arn to the policy defined in aws.

Is there any way to use already existing policy at aws in terraform, or atleast modify it or add some more things to it like condition etc using terraform.

My Code goes like this.
Policy defined in aws using console.
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"SNS:",
"SQS:
"
],
"Resource": [
"arn:aws:sqs:::"
],
"Condition": {
"ArnEquals": {
"aws:SourceArn": "arn:aws:sns:
::" -- i wanted this to dynamically changed
}
}
}
]
}

I am not finding any this sort of example. can any one help is it possible or not, is there any way to avoid policy writing in tf script.

I'm going to lock this issue because it has been closed for _30 days_ ⏳. This helps our maintainers find and focus on the active issues.

If you have found a problem that seems similar to this, please open a new issue and complete the issue template so we can capture all the details necessary to investigate further.

Was this page helpful?
0 / 5 - 0 ratings