Мне нужно выполнить шаблон Terraform для подготовки инфраструктуры для учетной записи AWS, к которой я могу получить доступ, приняв на себя роль.
Проблема, с которой я столкнулся сейчас, заключается в том, что у меня нет учетной записи IAM в этой учетной записи AWS, поэтому у меня нет aws_access_key_id
или aws_secret_access_key
для настройки другого именованного профиля в моем ~/.aws/credentials
. Когда я запускаю команду terraform apply
, шаблон создает инфраструктуру для моей учетной записи, а не другой учетной записи.
Как запустить шаблон Terraform, используя вашу учетную запись, у которой есть роль для доступа к службам другой учетной записи AWS?
Вот мой файл Terraform:
# Input variables
variable "aws_region" {
type = "string"
default = "us-east-1"
}
variable "pipeline_name" {
type = "string"
default = "static-website-terraform"
}
variable "github_username" {
type = "string"
default = "COMPANY"
}
variable "github_token" {
type = "string"
}
variable "github_repo" {
type = "string"
}
provider "aws" {
region = "${var.aws_region}"
assume_role {
role_arn = "arn:aws:iam::<AWS-ACCOUNT-ID>:role/admin"
profile = "default"
}
}
# CodePipeline resources
resource "aws_s3_bucket" "build_artifact_bucket" {
bucket = "${var.pipeline_name}-artifact-bucket"
acl = "private"
}
data "aws_iam_policy_document" "codepipeline_assume_policy" {
statement {
effect = "Allow"
actions = ["sts:AssumeRole"]
principals {
type = "Service"
identifiers = ["codepipeline.amazonaws.com"]
}
}
}
resource "aws_iam_role" "codepipeline_role" {
name = "${var.pipeline_name}-codepipeline-role"
assume_role_policy = "${data.aws_iam_policy_document.codepipeline_assume_policy.json}"
}
# CodePipeline policy needed to use CodeCommit and CodeBuild
resource "aws_iam_role_policy" "attach_codepipeline_policy" {
name = "${var.pipeline_name}-codepipeline-policy"
role = "${aws_iam_role.codepipeline_role.id}"
policy = <<EOF
{
"Statement": [
{
"Action": [
"s3:GetObject",
"s3:GetObjectVersion",
"s3:GetBucketVersioning",
"s3:PutObject"
],
"Resource": "*",
"Effect": "Allow"
},
{
"Action": [
"cloudwatch:*",
"sns:*",
"sqs:*",
"iam:PassRole"
],
"Resource": "*",
"Effect": "Allow"
},
{
"Action": [
"codebuild:BatchGetBuilds",
"codebuild:StartBuild"
],
"Resource": "*",
"Effect": "Allow"
}
],
"Version": "2012-10-17"
}
EOF
}
# CodeBuild IAM Permissions
resource "aws_iam_role" "codebuild_assume_role" {
name = "${var.pipeline_name}-codebuild-role"
assume_role_policy = <<EOF
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"Service": "codebuild.amazonaws.com"
},
"Action": "sts:AssumeRole"
}
]
}
EOF
}
resource "aws_iam_role_policy" "codebuild_policy" {
name = "${var.pipeline_name}-codebuild-policy"
role = "${aws_iam_role.codebuild_assume_role.id}"
policy = <<POLICY
{
"Version": "2012-10-17",
"Statement": [
{
"Action": [
"s3:PutObject",
"s3:GetObject",
"s3:GetObjectVersion",
"s3:GetBucketVersioning"
],
"Resource": "*",
"Effect": "Allow"
},
{
"Effect": "Allow",
"Resource": [
"${aws_codebuild_project.build_project.id}"
],
"Action": [
"codebuild:*"
]
},
{
"Effect": "Allow",
"Resource": [
"*"
],
"Action": [
"logs:CreateLogGroup",
"logs:CreateLogStream",
"logs:PutLogEvents"
]
}
]
}
POLICY
}
# CodeBuild Section for the Package stage
resource "aws_codebuild_project" "build_project" {
name = "${var.pipeline_name}-build"
description = "The CodeBuild project for ${var.pipeline_name}"
service_role = "${aws_iam_role.codebuild_assume_role.arn}"
build_timeout = "60"
artifacts {
type = "CODEPIPELINE"
}
environment {
compute_type = "BUILD_GENERAL1_SMALL"
image = "aws/codebuild/nodejs:6.3.1"
type = "LINUX_CONTAINER"
}
source {
type = "CODEPIPELINE"
buildspec = "buildspec.yml"
}
}
# Full CodePipeline
resource "aws_codepipeline" "codepipeline" {
name = "${var.pipeline_name}-codepipeline"
role_arn = "${aws_iam_role.codepipeline_role.arn}"
artifact_store = {
location = "${aws_s3_bucket.build_artifact_bucket.bucket}"
type = "S3"
}
stage {
name = "Source"
action {
name = "Source"
category = "Source"
owner = "ThirdParty"
provider = "GitHub"
version = "1"
output_artifacts = ["SourceArtifact"]
configuration {
Owner = "${var.github_username}"
OAuthToken = "${var.github_token}"
Repo = "${var.github_repo}"
Branch = "master"
PollForSourceChanges = "true"
}
}
}
stage {
name = "Deploy"
action {
name = "DeployToS3"
category = "Test"
owner = "AWS"
provider = "CodeBuild"
input_artifacts = ["SourceArtifact"]
output_artifacts = ["OutputArtifact"]
version = "1"
configuration {
ProjectName = "${aws_codebuild_project.build_project.name}"
}
}
}
}
Обновление:
Следуя ответу Даррена (это имеет большой смысл) ниже, я добавил:
provider "aws" {
region = "us-east-1"
shared_credentials_file = "${pathexpand("~/.aws/credentials")}"
profile = "default"
assume_role {
role_arn = "arn:aws:iam::<OTHER-ACCOUNT>:role/<ROLE-NAME>"
}
}
Однако я столкнулся с этой ошибкой:
provider.aws: Роль "arn: aws: iam ::: role /" не может быть принята.
Существует несколько возможных причин этого, наиболее распространенными из которых являются:
- Учетные данные, используемые для принятия роли, являются недействительными
- У учетных данных нет соответствующих прав для принятия роли
- Роль ARN недействительна
Я проверил роль в другой учетной записи и могу перейти на эту роль с помощью консоли AWS из своей учетной записи. Я также проверил руководство AWS здесь
Итак: эта роль ARN действительна, у меня есть учетные данные для принятия роли и все разрешения, необходимые для запуска стека.
Обновление
Я также пробовал с новой ролью, которая имеет все права доступа к службам . Однако я столкнулся с этой ошибкой:
Ошибка: ошибка при обновлении состояния: 2 произошла ошибка:
* aws_codebuild_project.build_project: 1 error(s) occurred:
* aws_codebuild_project.build_project: aws_codebuild_project.build_project: Error retreiving Projects:
"InvalidInputException: неверный ARN проекта: идентификатор учетной записи не совпадает
учетная запись вызывающего абонента \ n \ tstatus code: 400, идентификатор запроса: ... "
* aws_s3_bucket.build_artifact_bucket: 1 произошла ошибка (и):
* aws_s3_bucket.build_artifact_bucket: aws_s3_bucket.build_artifact_bucket: error getting S3 Bucket CORS
конфигурация: AccessDenied: доступ запрещен
код состояния: 403, идентификатор запроса: ..., идентификатор хоста: ...
=====
ОБНОВЛЕНИЕ 29 апреля 2019 г .:
Следуя предложению @ Rolando, я добавил эту политику для пользователя ОСНОВНОГО СЧЕТА, который я пытаюсь использовать, чтобы взять на себя роль ДРУГОГО СЧЕТА, где я планирую выполнить terraform apply
.
{
"Version": "2012-10-17",
"Statement": {
"Effect": "Allow",
"Action": "sts:AssumeRole",
"Resource": "arn:aws:iam::<OTHER-ACCOUNT-ID>:role/admin"
}
}
Это Trust Relationship
роли admin
принадлежит ДРУГОЙ УЧЕТНОЙ ЗАПИСИ:
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"AWS": "arn:aws:iam::<MAIN_ACCOUNT_ID>:root"
},
"Action": "sts:AssumeRole",
"Condition": {
"Bool": {
"aws:MultiFactorAuthPresent": "true"
}
}
}
]
}
Однако, когда я запустил эту команду:
aws sts assume-role --role-arn arn:aws:iam::<OTHER-ACCOUNT-ID>:role/admin --role-session-name "RoleSession1" --profile default > assume-role-output.txt
У меня есть эта ошибка:
An error occurred (AccessDenied) when calling the AssumeRole operation: Access denied