本記事はFIXERが提供する「cloud.config Tech Blog」に掲載された「Terraformを使って.NETのLambda関数をAWSにデプロイする」を再編集したものです。
こんにちは。二宮です。
伝説的名作フリーゲーム「Ruina 廃都の物語」のリメイク版がSteamで発売されるらしいです。楽しみですね!
さて、今回は、.NETで書いたLambda関数を1度のterraform applyだけでデプロイする方法を書いていきます。
事前準備
Terraformを使ってLambda関数をデプロイするためには、ローカルでzipファイルを作成するか、S3にアップロードする必要がありますが、今回はローカルでzipファイルを作成する方法でデプロイしていきます。
ソースのzipファイル化は、.NET ToolのAmazon.Lambda.Toolsを使用すると簡単です。 まずは、次のコマンドでAmazon.Lambda.Toolsをインストールします。
dotnet tool install -g Amazon.Lambda.Tools
Amazon.Lambda.Toolsがインストールできたら、次のコマンドでソースをzip化します。
dotnet lambda package
が、今回は一度のterraform applyでLambda関数をデプロイしたいので、このコマンドもTerraformから実行します。
Terraform作成
次のようなTerraformファイルを作成します。
provider "aws" {
region = "ap-northeast-1"
access_key = <アクセスキー>
secret_key = <シークレットキー>
}
resource "null_resource" "lambda_build" {
triggers = {
always_run = timestamp()
}
provisioner "local-exec" {
command = "dotnet lambda package --project-location <Functionのフォルダのpath> --output-package <zipファイルの出力先/filename.zip>"
}
}
resource "aws_lambda_function" "sample_function" {
filename = <zipファイルの出力先/filename.zip>
function_name = <Lambda関数の名前>
role = aws_iam_role.lambda_role.arn
handler = "<関数名>::<関数名>.<関数ファイル名>::<ハンドラー名>"
runtime = "dotnetcore3.1"
environment {
variables = {
Sample_Message = "Hello World"
}
}
depends_on = [
null_resource.lambda_build,
aws_iam_role_policy_attachment.basic_policy_attachment
]
}
data "aws_iam_policy_document" "lambda_role_policy_document" {
version = "2012-10-17"
statement {
actions = [
"sts:AssumeRole"
]
effect = "Allow"
principals {
type = "Service"
identifiers = ["lambda.amazonaws.com"]
}
}
}
resource "aws_iam_role" "function_role" {
name = "function_role"
assume_role_policy = data.aws_iam_policy_document.lambda_role_policy_document.json
}
data "aws_iam_policy" "basic_role" {
arn = "arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole"
}
resource "aws_iam_role_policy_attachment" "basic_policy_attachment" {
role = aws_iam_role.function_role.name
policy_arn = data.aws_iam_policy.basic_role.arn
}
providerブロックは、AWSのリージョン、アクセスキー、シークレットキーを入れることでTerraformとAWSを接続するブロックです。
provider "aws" {
region = "ap-northeast-1"
access_key = <アクセスキー>
secret_key = <シークレットキー>
}
null_resourceでは、コマンドを実行してLambda関数をビルド・zip化を行っています。
resource "null_resource" "lambda_build" {
triggers = {
always_run = timestamp()
}
provisioner "local-exec" {
command = "dotnet lambda package --project-location <Functionのフォルダのpath> --output-package <zipファイルの出力先/filename.zip>"
}
}
aws_lambda_functionでは、Lambdaリソースを定義しています。
depends_onでnull_resourceとaws_iam_policy_attachmentが完了を待っています。
resource "aws_lambda_function" "sample_function" {
filename = <zipファイルの出力先/filename.zip>
function_name = <Lambda関数の名前>
role = aws_iam_role.lambda_role.arn
handler = "<関数名>::<関数名>.<関数ファイル名>::<ハンドラー名>"
runtime = "dotnetcore3.1"
environment {
variables = {
Sample_Message = "Hello World"
}
}
depends_on = [
null_resource.lambda_build,
aws_iam_role_policy_attachment.basic_policy_attachment
]
}
以降のブロックではIAMロールを定義しています。
function_roleというロールを作成し、AWSにデフォルトで存在しているAWSLambdaBasicExecutionRoleというポリシーをアタッチしています。
data "aws_iam_policy_document" "lambda_role_policy_document" {
version = "2012-10-17"
statement {
actions = [
"sts:AssumeRole"
]
effect = "Allow"
principals {
type = "Service"
identifiers = ["lambda.amazonaws.com"]
}
}
}
resource "aws_iam_role" "function_role" {
name = "function_role"
assume_role_policy = data.aws_iam_policy_document.lambda_role_policy_document.json
}
data "aws_iam_policy" "basic_role" {
arn = "arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole"
}
resource "aws_iam_role_policy_attachment" "basic_policy_attachment" {
role = aws_iam_role.function_role.name
policy_arn = data.aws_iam_policy.basic_role.arn
}
terraformを実行
コードができたのでTerrafromを実行します。
次のコマンドでワークスペースを初期化します。
terraform init
ワークスペースの初期化が終わったら次のコマンドでTerraformによる実行計画を参照します。
terraform plan
実行計画が問題なければ、次のコマンドでリソースを構築します。
terraform apply
次のメッセージが表示され、作成したroleがアタッチされたLambdaが作成されます。
Apply complete! Resources: 4 added, 0 changed, 0 destroyed.
まとめ
今回は、Terraformを使った.NETのLambdaのデプロイ方法を紹介しました。
この方法ならbuildからzip化、デプロイまでを一度のterraform applyで一気に行えるので、手間を省くことができます。
TerraformでAWSのリソースを管理する際はぜひ活用して下さい。
二宮 涼/FIXER
いろいろなことに挑戦していきたいです。