use*_*094 4 hash amazon-web-services terraform devops terraform-provider-aws
我有一个用于分配 AWS Lambda 的 Terraform 配置。我希望它在检测到更改时自动更新代码。为此,我正在使用该source_code_hash属性,如下所示。作为构建过程的一部分,我将所有代码压缩,然后用于openssl获取 zip 文件的 SHA256 哈希值,将其粘贴到文本文件中,然后将两者上传到 S3 存储桶。
这是我的 Terraform 配置:
data "aws_s3_bucket_object" "mylambdacode_sha256" {
bucket = "myapp-builds"
key = "build.zip.sha256"
}
resource "aws_lambda_function" "my_lambda" {
function_name = "${var.lambda_function_name}"
role = "${aws_iam_role.iam_for_lambda.arn}"
handler = "index.handler"
runtime = "nodejs10.x"
s3_bucket = "myapp-builds"
s3_key = "build.zip"
source_code_hash = "${data.aws_s3_bucket_object.mylambdacode_sha256.body}"
timeout = 900
}
Run Code Online (Sandbox Code Playgroud)
我跑了terraform apply,它告诉我source_code_hash已经改变了:
~ source_code_hash = <<~EOT
- c9Nl4RRfuh/Z5fJvEOT69GDTJqY9n/QTB5cBGtOniYc=
+ 73d365e1145fba1fd9e5f26f10e4faf460d326a63d9ff4130797011ad3a78987
Run Code Online (Sandbox Code Playgroud)
该73d365e1145fba1fd9e5f26f10e4faf460d326a63d9ff4130797011ad3a78987部分确实是 S3 上文件中的内容。所以,这一切看起来都是正确的。但是当我terraform apply之后立即再次运行时,它认为哈希再次发生了变化。
检查.tfstate文件我看到它刚刚说的新哈希没有被保存。
Terraform 是对我的哈希进行哈希处理还是进行其他一些操作并将结果保存到.tfstate? 或者我有什么配置不正确?
编辑:
根据下面的答案,我更新了source_code_hash语句以使用该base64encode函数,如下所示:
source_code_hash = "${base64encode(data.aws_s3_bucket_object.my_lambda_build_sha256.body)}"
Run Code Online (Sandbox Code Playgroud)
这是来自的输出 terraform state show aws_lambda_function.my_lambda && terraform apply && terraform state show aws_lambda_function.my_lambda
$ terraform state show aws_lambda_function.my_lambda && terraform apply && terraform state show aws_lambda_function.my_lambda
# aws_lambda_function.my_lambda:
resource "aws_lambda_function" "my_lambda" {
arn = "arn:aws:lambda:us-east-2:XXXXXXXXXX:function:my_lambda"
function_name = "my_lambda"
handler = "index.handler"
id = "my_lambda"
invoke_arn = "arn:aws:apigateway:us-east-2:lambda:path/2015-03-31/functions/arn:aws:lambda:us-east-2:XXXXXXXXXX:function:my_lambda/invocations"
last_modified = "2019-08-02T15:00:32.621+0000"
layers = []
memory_size = 128
publish = false
qualified_arn = "arn:aws:lambda:us-east-2:XXXXXXXXXX:function:my_lambda:$LATEST"
reserved_concurrent_executions = -1
role = "arn:aws:iam::XXXXXXXXXX:role/my_lambda-role"
runtime = "nodejs10.x"
s3_bucket = "myapp-builds"
s3_key = "myapp/build.zip"
source_code_hash = "r5D6o1FuCug6FD4QPQ43VdUlfYP4Qe1l1DcElNsf5E0="
source_code_size = 12793672
tags = {}
timeout = 900
version = "$LATEST"
tracing_config {
mode = "PassThrough"
}
}
postgresql_database.postgres: Refreshing state... [id=postgres]
aws_iam_policy.lambda_logging: Refreshing state... [id=arn:aws:iam::XXXXXXXXXX:policy/lambda_logging]
aws_cloudwatch_log_group.my_lambda: Refreshing state... [id=/aws/lambda/my_lambda]
aws_iam_role.iam_for_lambda: Refreshing state... [id=my_lambda-role]
aws_cloudwatch_event_rule.my_lambda-rule: Refreshing state... [id=my_lambda-rule]
data.aws_s3_bucket_object.myapp_lambda_build_sha256: Refreshing state...
data.aws_s3_bucket_object.myapp_lambda_build_zip: Refreshing state...
aws_iam_role_policy_attachment.lambda_logs: Refreshing state... [id=my_lambda-role-20190801190935907200000001]
aws_lambda_function.my_lambda: Refreshing state... [id=my_lambda]
aws_lambda_permission.allow_cloudwatch_to_call_trigger_lambda: Refreshing state... [id=AllowExecutionFromCloudWatch]
aws_cloudwatch_event_target.my_lambda-rule-event-target: Refreshing state... [id=my_lambda-rule-terraform-20190801192030362600000001]
An execution plan has been generated and is shown below.
Resource actions are indicated with the following symbols:
~ update in-place
Terraform will perform the following actions:
# aws_lambda_function.my_lambda will be updated in-place
~ resource "aws_lambda_function" "my_lambda" {
arn = "arn:aws:lambda:us-east-2:XXXXXXXXXX:function:my_lambda"
function_name = "my_lambda"
handler = "index.handler"
id = "my_lambda"
invoke_arn = "arn:aws:apigateway:us-east-2:lambda:path/2015-03-31/functions/arn:aws:lambda:us-east-2:XXXXXXXXXX:function:my_lambda/invocations"
~ last_modified = "2019-08-02T15:00:32.621+0000" -> (known after apply)
layers = []
memory_size = 128
publish = false
qualified_arn = "arn:aws:lambda:us-east-2:XXXXXXXXXX:function:my_lambda:$LATEST"
reserved_concurrent_executions = -1
role = "arn:aws:iam::XXXXXXXXXX:role/my_lambda-role"
runtime = "nodejs10.x"
s3_bucket = "myapp-builds"
s3_key = "myapp/build.zip"
~ source_code_hash = "r5D6o1FuCug6FD4QPQ43VdUlfYP4Qe1l1DcElNsf5E0=" -> "YWY5MGZhYTM1MTZlMGFlODNhMTQzZTEwM2QwZTM3NTVkNTI1N2Q4M2Y4NDFlZDY1ZDQzNzA0OTRkYjFmZTQ0ZAo="
source_code_size = 12793672
tags = {}
timeout = 900
version = "$LATEST"
tracing_config {
mode = "PassThrough"
}
}
Plan: 0 to add, 1 to change, 0 to destroy.
Do you want to perform these actions?
Terraform will perform the actions described above.
Only 'yes' will be accepted to approve.
Enter a value: yes
aws_lambda_function.my_lambda: Modifying... [id=my_lambda]
aws_lambda_function.my_lambda: Modifications complete after 1s [id=my_lambda]
Apply complete! Resources: 0 added, 1 changed, 0 destroyed.
# aws_lambda_function.my_lambda:
resource "aws_lambda_function" "my_lambda" {
arn = "arn:aws:lambda:us-east-2:XXXXXXXXXX:function:my_lambda"
function_name = "my_lambda"
handler = "index.handler"
id = "my_lambda"
invoke_arn = "arn:aws:apigateway:us-east-2:lambda:path/2015-03-31/functions/arn:aws:lambda:us-east-2:XXXXXXXXXX:function:my_lambda/invocations"
last_modified = "2019-08-02T15:05:08.079+0000"
layers = []
memory_size = 128
publish = false
qualified_arn = "arn:aws:lambda:us-east-2:XXXXXXXXXX:function:my_lambda:$LATEST"
reserved_concurrent_executions = -1
role = "arn:aws:iam::XXXXXXXXXX:role/my_lambda-role"
runtime = "nodejs10.x"
s3_bucket = "myapp-builds"
s3_key = "myapp/build.zip"
source_code_hash = "r5D6o1FuCug6FD4QPQ43VdUlfYP4Qe1l1DcElNsf5E0="
source_code_size = 12793672
tags = {}
timeout = 900
version = "$LATEST"
tracing_config {
mode = "PassThrough"
}
}
Run Code Online (Sandbox Code Playgroud)
小智 5
它适用于我在将其上传到 S3 之前生成“build.zip.sha256”:
openssl dgst -sha256 -binary build.zip | openssl enc -base64 > build.zip.sha256
Run Code Online (Sandbox Code Playgroud)
为了避免 <<~EOT 与我使用的原始 sha256 不匹配:
source_code_hash = chomp(data.aws_s3_bucket_object.my_lambda_build_sha256.body)
Run Code Online (Sandbox Code Playgroud)