Terraform-如何为AWS Lambda创建IAM角色并两者都部署



我正在学习Terraform。我正在尝试创建一个新的lambda功能。我意识到我还需要创建IAM角色。因此,我正在尝试使用Terraform进行两者。但这不允许我创建角色。

这是我的Terraform文件

provider "aws" {
  profile = "default"
  region  = "eu-west-1"
}
data "aws_iam_policy" "AWSLambdaBasicExecutionRole" {
  arn = "arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole"
}
resource "aws_iam_role" "terraform_function_role" {
  name               = "terraform_function_role"
  assume_role_policy = "${data.aws_iam_policy.AWSLambdaBasicExecutionRole.policy}"
}
resource "aws_lambda_function" "terraform_function" {
  filename         = "terraform_function.zip"
  function_name    = "terraform_function"
  handler          = "index.handler"
  role             = "${aws_iam_role.terraform_function_role.id}"
  runtime          = "nodejs8.10"
  source_code_hash = "${filebase64sha256("terraform_function.zip")}"
}

这是我遇到的错误

Error creating IAM Role terraform_function_role: MalformedPolicyDocument: Has prohibited field Resource
status code: 400

我该如何修复?

iam角色的信任关系(或假定角色策略(定义了哪些资源/服务可以扮演角色。在此,我们没有定义资源字段。因此,我们不能附加IAM策略或使用该策略。信任关系的正确格式是:

{
    "Version": "2012-10-17",
    "Statement": [{
        "Effect": "Allow",
        "Principal": {
            "Service": "lambda.amazonaws.com"
        },
        "Action": "sts:AssumeRole"
    }]
}

在这种情况下,您帐户中的所有lambda功能都可以假定此角色。

您可以参考此AWS链接以获取更多示例。

编辑:基于@ydaetskcor评论,这是一个工作示例:

provider "aws" {
  profile = "default"
  region  = "eu-west-1"
}
data "aws_iam_policy_document" "AWSLambdaTrustPolicy" {
  statement {
    actions    = ["sts:AssumeRole"]
    effect     = "Allow"
    principals {
      type        = "Service"
      identifiers = ["lambda.amazonaws.com"]
    }
  }
}
resource "aws_iam_role" "terraform_function_role" {
  name               = "terraform_function_role"
  assume_role_policy = "${data.aws_iam_policy_document.AWSLambdaTrustPolicy.json}"
}
resource "aws_iam_role_policy_attachment" "terraform_lambda_policy" {
  role       = "${aws_iam_role.terraform_function_role.name}"
  policy_arn = "arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole"
}
resource "aws_lambda_function" "terraform_function" {
  filename         = "terraform_function.zip"
  function_name    = "terraform_function"
  handler          = "index.handler"
  role             = "${aws_iam_role.terraform_function_role.arn}"
  runtime          = "nodejs8.10"
  source_code_hash = "${filebase64sha256("terraform_function.zip")}"
}

您代码的更改包括以下内容:

  • 更新已更新的AWS_IAM_POLICY_DOCUMEMENT for PUSTION角色权限
  • 更改了AWS_IAM_ROLE资源以使用上述策略文档
  • 创建AWS_IAM_ROLE_POLICY_ATTACHMENT,以附加LambdabasiceXecution策略(可以登录到CloudWatch(
  • 更新已更新的AWS_LAMBDA_FUNCTION资源以使用IAM角色的ARN而不是ID,因为Lambda功能需要ARN

由于您仍处于学习阶段,我建议您改用terraform 0.12,因此可以使用templatefile之类的东西。因此,您不需要创建data对象。

另一件事是在制定策略时始终使用最低特权原则,这意味着您的资源(在这种情况下为lambda(只能访问其所需内容。就目前而言,这只是CloudWatch,但是在现实世界中,情况很可能并非如此。

回到您的问题,这是您如何创建IAM角色,IAM策略以及最终IAM政策附件(这是政策与角色之间的桥梁(以及AuderoLepolicy(这是这之间的信任关系它将使用它及其角色本身的服务。我将其全部提取到模板中,以便以后更容易维护。要点(在眼睛上更容易阅读(可以在这里找到。

# iam_role
resource "aws_iam_role" "iam_role" {
  name = "iam-role"
  assume_role_policy = templatefile("${path.module}/templates/lambda-base-policy.tpl", {})
}
#content of lambda-base-policy.tpl
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Action": "sts:AssumeRole",
      "Principal": {
        "Service": "lambda.amazonaws.com"
      },
      "Effect": "Allow",
      "Sid": ""
    }
  ]
}
#iam_policy
resource "aws_iam_policy" "policy" {
  name = "policy"
  policy = templatefile("${path.module}/templates/cloudwatch-policy.tpl", {})
}
#content of cloudwatch-policy.tpl
{
  "Version": "2012-10-17",
  "Statement": [
    {
            "Effect": "Allow",
            "Action": [
                "logs:CreateLogGroup",
                "logs:CreateLogStream",
                "logs:PutLogEvents"
            ],
            "Resource": "*"
        }
  ]
} 
#iam_policy_attachment
resource "aws_iam_policy_attachment" "policy_attachment" {
  name       = "attachment"
  roles      = ["${aws_iam_role.iam_role.name}"]
  policy_arn = "${aws_iam_policy.policy.arn}"
} 

如评论中所述,您必须创建假设角色,然后将假定规则附加到新创建的策略,这是完整的工作示例。

#assume role
resource "aws_iam_role" "role" {
      name = "test-alb-logs-to-elk"
      path = "/"
      assume_role_policy = <<EOF
    {
      "Version": "2012-10-17",
      "Statement": [
        {
          "Action": "sts:AssumeRole",
          "Principal": {
            "Service": "lambda.amazonaws.com"
          },
          "Effect": "Allow",
          "Sid": ""
        }
      ]
    }
    EOF
    }
# Created Policy for IAM Role (s3 and log access)
resource "aws_iam_policy" "policy" {
  name = "my-test-policy"
  description = "A test policy"

  policy = <<EOF
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": [
          "s3:Get*",
          "s3:List*"
          ],
            "Resource": "*"
        },
        {
            "Effect": "Allow",
            "Action": [
                "logs:*"
            ],
            "Resource": "arn:aws:logs:*:*:*"
        }
  ]
}
EOF
}
# Attached IAM Role and the new created Policy
resource "aws_iam_role_policy_attachment" "test-attach" {
  role       = "${aws_iam_role.role.name}"
  policy_arn = "${aws_iam_policy.policy.arn}"
}

# Created AWS Lamdba Function: Memory Size, NodeJS version, handler, endpoint, doctype and environment settings
resource "aws_lambda_function" "elb_logs_to_elasticsearch" {
  function_name = "mytest-alb-logs-to-elk"
  description   = "elb-logs-to-elasticsearch"
  memory_size = 1024
  filename         = "terraform_function.zip"
  runtime          = "nodejs8.10"
  role             = "${aws_iam_role.role.arn}"
  handler          = "index.handler"

}

相关内容

  • 没有找到相关文章

最新更新