Following this example from Hashicorp, I'm struggling to understand the right way to populate Aliases for AWS Providers.
Let's assume I've got 2 AWS Roles in 2 different accounts, OIDC is configured properly for Terraform Cloud to access them:
arn:aws:iam::123456789012:role/test-terraform-cloud-access
arn:aws:iam::123456789013:role/staging-terraform-cloud-access
Now, following the documentation, I use:
TFC_AWS_PROVIDER_AUTH = true
TFC_AWS_RUN_ROLE_ARN = arn:aws:iam::123456789012:role/test-terraform-cloud-access
Now, based on their documentation, they advice using this config:
variable "tfc_aws_dynamic_credentials" {
description = "Object containing AWS dynamic credentials configuration"
type = object({
default = object({
shared_config_file = string
})
aliases = map(object({
shared_config_file = string
}))
})
}
Then you can target the alias this way:
provider "aws" {
shared_config_files = [var.tfc_aws_dynamic_credentials.default.shared_config_file]
}
provider "aws" {
alias = "ALIAS1"
shared_config_files = [var.tfc_aws_dynamic_credentials.aliases["ALIAS1"].shared_config_file]
}
My questions are:
shared_config_file
is configured in Terraform Cloud?["STAGING"]
?TFC_AWS_RUN_ROLE_ARN_STAGING
for this to work?I did try the last one, but it doesn't seem to be picked up by the system.
Thanks a lot again!
If you have multiple configurations for the hashicorp/aws
provider that each need a separate dynamic credentials configuration then you must also consider the companion tutorial Specifying Multiple Configurations. The tutorial you linked in your question is focused on the simpler and more common case of using only a single set of dynamic credentials for each provider.
The tutorial describes setting additional environment variables where each has a suffix which will appear as the key in the aliases
map.
In your case then, if you want to use the "staging" ARN for ALIAS1
then you would set the environment variables as follows:
TFC_AWS_RUN_ROLE_ARN
to arn:aws:iam::123456789012:role/test-terraform-cloud-access
TFC_AWS_RUN_ROLE_ARN_ALIAS1
to arn:aws:iam::123456789013:role/staging-terraform-cloud-access
With those two environment variables set, your var.tfc_aws_dynamic_credentials
object should contain both the default
object as before, referring to an AWS configuration file for the "test" role, and also have an ALIAS1
key in aliases
whose object refers to a separate AWS configuration file for the "staging" role.
A configuration like you wrote should then work:
variable "tfc_aws_dynamic_credentials" {
description = "Object containing AWS dynamic credentials configuration"
type = object({
default = object({
shared_config_file = string
})
aliases = map(object({
shared_config_file = string
}))
})
}
provider "aws" {
shared_config_files = [
var.tfc_aws_dynamic_credentials.default.shared_config_file,
]
}
provider "aws" {
# Notice that this "alias" doesn't need to match the one
# in the environment variable. These are two separate
# namespaces, so you can use the same names here if you
# like but that's not actually required.
alias = "staging"
shared_config_files = [
var.tfc_aws_dynamic_credentials.aliases["ALIAS1"].shared_config_file,
]
}
These shared_config_file
arguments refer to AWS configuration files as described in the AWS docs Shared config
and credentials
files. When you're using dynamic credentials, Terraform Cloud's execution environment creates those files dynamically just before running Terraform CLI, and then passes the paths to those files in as as part of the input variable tfc_aws_dynamic_credentials
.
Those configuration files contain information about which role to assume and which JSON Web Token to use to authenticate to the AWS APIs. Therefore the file associated with ALIAS1
will specify the staging role ARN, while the file associated with the "default" object will specify the testing role ARN.