Creating dynamic IAM policy by populating the list of resources being created in policy JSON

Hi,

I am creating S3 buckets with different names provided in the variables list using the below code.

resource "aws_s3_bucket" "mybuckets" {
  count  = length(var.bucket_type)
  bucket = "${var.appender}-mybucket-${element(var.bucket_type, count.index)}"
  acl = "private"
  lifecycle_rule {

    enabled = true
    transition {
      days = 60
      storage_class = "STANDARD_IA"
    }
    transition {
      days = 120
      storage_class = "GLACIER"
    }
  }
  tags = {
    Name = "${var.appender}-mybucket-${element(var.bucket_type, count.index)}"
  }
}

Now, I want to create IAM Policy that will have access to these created buckets but I’m facing error creating that policy dynamically as I am using “aws_s3_bucket.mybuckets.arn” will be a tuple containing multiple elements i.e. it is list and not string.
I am using below code to generate IAM Policy for the user.

resource "aws_iam_user_policy" "bucket_access_policy" {
 name = "${var.appender}-bucketaccess-policy"
 user = aws_iam_user.this[0].name
 #policy = "data.template_file.policy_doc.rendered"
 policy = <<EOF
{
   "Version":"2012-10-17",
   "Statement":[
      {
         "Action":[
            "s3:ListAllMyBuckets",
            "s3:GetBucketLocation",
            "s3:HeadBucket",
            "s3:GetAccessPoint",
            "s3:ListJobs",
            "s3:CreateJob",
            "ec2:Describe*"
         ],
         "Effect":"Allow",
         "Resource":"*"
      },
      {
         "Action":[
            "s3:Get*",
            "s3:Put*",
            "s3:Update*",
            "s3:DeleteObject",
            "s3:RestoreObject"
         ],
         "Effect":"Allow",
         "Resource":[
            "${aws_s3_bucket.mybuckets[*].arn}",
            "${aws_s3_bucket.mybuckets[*].arn}/*"
         ]
      }
   ]
}
EOF
}

I tried multiple ways to achieve this but none worked or may be I’m making some mistake. I tried using rendered template_file and passing vars to it but that also fails with same error. I tried using $split(",", aws_s3_bucket.mybuckets[*].arn) as well. I also tried jsonencode in the policy block.

Also tried using ${concat(aws_s3_bucket.ontarget_buckets[*].arn)} but ends up with error as Cannot include the given value in a string template: string required.

Please suggest how I can achieve this! What change should I make to generate dynamic IAM Policy that will put list of all the buckets in the policy that are being created irrespective of the number of buckets.

Thanks in advance for help.

Terraform v.0.12.20

Did you get to solve this? I am trying to do the same but in my case I am trying to create an IAM policy for an ec2 instance to access buckets in different accounts.
My end goal is to create a module where next time if I have to add another bucket I should be able to add that to list of resources (inputs).