0
votes

I am trying to update an IAM Role and it's attached policy with Terraform through GitLab-CI. My terraform code looks like below:-

data "aws_iam_policy_document" "billing-roles" {
  statement {
      effect = "Allow"
      principals {
          type = "Federated"
          identifiers = ["${var.samlprovider_arn}"]
      }
      actions = ["sts:AssumeRoleWithSAML"]
      condition {
        test = "StringEquals"
        variable ="SAML:aud"
        values = ["https://signin.aws.amazon.com/saml"]
       }
    }
}

resource "aws_iam_role" "billing_role" {
  name               = "billing-role"
  permissions_boundary = "${var.permissions_boundary_arn}"
  assume_role_policy = "${data.aws_iam_policy_document.billing-roles.json}"
  tags =  {
      Applicatio_ID = "${var.app_id}"
      Environment = "${var.environment}"
      Name = "billing-role"
      Owner = "Terraform"
  }
}


resource "aws_iam_policy" "billing_policy" {
  name  = "billing-policy"
  policy= "${file("${path.module}/policies/billing-role-policy.json")}"
}

resource "aws_iam_role_policy_attachment" "billing_attachment" {
  role  = aws_iam_role.billing_role.name
  policy_arn = aws_iam_policy.billing_policy.arn
}

I am running various phases of terraform(INIT, PLAN, APPLY) through GitLab-CI. This works the first time but fails with EntityAlreadyExists error. The .gitlab-ci.yml looks like this:-

include:
  - project: 'infrastructure/infrastructure-code-cicd-files'
    ref: master
    file: '.for_terraform_iam.yml'

stages:
  - init
  - plan
  - apply

tf_init:
  extends: .tf_init
  tags:
    - integration
  stage: init
  variables:
    ACCOUNT: "ACCOUNT_ID"
    ASSUME_ROLE: "arn:aws:iam::ACCOUNT_ID:role/devops-cross-account"
    backend_bucket_name: "iam-role-backend-${ACCOUNT}"
    tfstate_file: "iam-role/terraform.tfstate"

tf_plan:
  extends: .tf_plan
  variables:
    ASSUME_ROLE: "arn:aws:iam::ACCOUNT_ID:role/devops-cross-account"
  tags:
    - integration
  stage: plan


tf_apply:
  extends: .tf_apply
  variables:
    ASSUME_ROLE: "arn:aws:iam::ACCOUNT_ID:role/devops-cross-account"
  tags:
    - integration
  stage: apply

This gitlab-ci configuration includes a utility file which has all the terraform logic for Init, Plan and Apply.

I am running the setup on Terraform 0.12.13. Terraform import though successful in importing the resources does not help here as terraform complains about "EntityAlreadyExists" Terraform taint does not work dues to a bug in the terraform version that I am using here.

I want a workflow where IAM Role once created, its attached inline policy can be updated by an Ops Engineer and an approver will approve the merge request and that way the IAM role will have added services as desired by the Ops engineer.

Is there a way we can update the IAM policy here. I understand that updating an IAM role would require detaching the policies first and then attach the new policies to it.

Please help

1
Why do you want to keep re-creating role billing-role all the time?Marcin
The billing_role was an example. There are other roles which needs to be updated for instance, we've given a role a policy that allow "ec2:createinstances" but in future we want to update this role with a policy that allows "ec2:deleteinstances" as well. would this be possible.Biplab Biswas
Where do you keep your TF state file? I guess its remote one?Marcin
yes it's kept in s3 backend. ThanksBiplab Biswas

1 Answers

0
votes

The issue was with passing terraform.tfstate file into plan stage which I had missed. We run an "aws s3 cp s3://backend-bucket/keys ." to get the statefile and this has solved the problem.