How to AssumeRole in Terraform LocalExec Provisioner Block


I needed to execute a Terraform null_resource provisioner (local-exec) block to run an awscli command, but assume a role passed down to it.

There was no obvious way to pass the credentials to it, or assume a role directly, so the following workaround did the trick:

AssumeRole and Pass LocalExec Provisioner Command

resource "null_resource" "start-appstream-fleet" {
  provisioner "local-exec" {
    interpreter = ["/bin/bash", "-c"]
    command = <<EOF
set -e
CREDENTIALS=(`aws sts assume-role \
  --role-arn ${local.workspace.role} \
  --role-session-name "start-appstream-fleet" \
  --query "[Credentials.AccessKeyId,Credentials.SecretAccessKey,Credentials.SessionToken]" \
  --output text`)

unset AWS_PROFILE
export AWS_DEFAULT_REGION=us-east-1
export AWS_ACCESS_KEY_ID="$${CREDENTIALS[0]}"
export AWS_SECRET_ACCESS_KEY="$${CREDENTIALS[1]}"
export AWS_SESSION_TOKEN="$${CREDENTIALS[2]}"

aws appstream start-fleet --name sample-app-${var.environment}-fleet --region ${var.region} --output json
EOF
  }
}

The above code snippet runs 2 aws cli commands. The first is to get the credentials, which are then stored in environment variables, followed by consuming them in the actual aws cli command at the bottom.

The role that we want to assume, has been setup in the local.workspace.role local variable.

It is an ARN string that looks something like this:

"arn:aws:iam::<ACCOUNTID>:role/<PROJECT>-Pipeline-Role"