こんにちは、後藤です。
Terraform開発を進める中で「こんなことできるのか」と思った機能があったので、備忘録も兼ねて紹介します。
それはローカルのファイルを操作できる、という機能です。
TerraformではAWSやAzure、GCPなどのパブリッククラウドプロバイダを扱えますが、localやarchiveといったHashiCorp社によるプロバイダがあります。
このプロバイダを使えば、Terraformを実行するローカル環境のファイル操作が可能になります。
当記事では、よく使われるであろう方法を3つ紹介していきます。
※Terraformバージョン1.5.6で検証しております。
1つ目:local_file
local_fileリソースを記述すればローカル環境にファイルを作成できます。resourceブロックによってファイルを作成し、dataブロックによってファイルを読み込むことができます。
またfile_permissionといった設定項目があり、作成したファイルのパーミッションを設定することもできます。
resource "local_file" "example" { content = "hello" filename = "./hello.txt" file_permission = "0600" }
local_fileの使用例①
パラメータをtfファイル内に記載せず、別のテキストファイルで管理したいときに使えます。
以下の例ではdataブロックを使ってローカルにあるIPリストファイルを読み込み、読み込んだ内容をS3に格納しています。このS3を他のAWSサービスから参照する構成にしていれば有効的です。
data "local_file" "ip_list" { filename = "./ip_list.txt" } resource "aws_s3_object" "object" { bucket = "my-bucket" key = "my-key" content = data.local_file.ip_list.content }
パラメータを編集する際は特定ファイルのみに絞ることができ、tfファイルを操作する必要がなくなるので、セキュリティ強化にもなります。
2つ目:local_sensitive_file
local_sensitive_fileリソースを記述すれば、パスワードなど機微情報をbase64エンコードしてローカル環境にファイルを作成することができます。
local_file同様、file_permission項目が設定可能です。
resource "local_sensitive_file" "example_secret" { content = "keypair.pem" filename = "./foo.bar" }
local_sensitive_fileの使用例
EC2-Windowsを作成して、OSにログインするときに使えます。
EC2-WindowsへOSログインするには事前にキーペアを作成しておき、それを登録する必要があります。
以下例ではキーペアを作成し、それを使ってEC2を作成していますが、ローカルにpemファイルを保存するようにもしています。
resource "tls_private_key" "ssh-keygen" { algorithm = "RSA" rsa_bits = 4096 } resource "aws_key_pair" "key-pair" { key_name = "ec2-keypair" public_key = tls_private_key.ssh-keygen.public_key_openssh } resource "aws_instance" "ec2-windows" { ami = "abcd123456789" instance_type = "t3.large" key_name = aws_key_pair.key-pair.key_name } resource "local_sensitive_file" "key-pair-pem" { content = tls_private_key.ssh-keygen.private_key_pem filename = "./keypair.pem" }
1~9行目でキーペアを作り、11~15行目でそのキーペアを用いてEC2を作成、17~20行目でローカルに保存しています。
3つ目:archive_file
archive_fileリソースを記述すれば、ローカルファイルをzip化することができます。
data "archive_file" "example-archive" { type = "zip" source_file = "./function.py" output_path = "./files/function.zip" }
archive_fileの使用例
Lambdaスクリプトをローカルで管理する場合に有効です。
data "archive_file" "function-code" { type = "zip" source_dir = "lambda/function" output_path = "lambda/upload/function.zip" } resource "aws_lambda_function" "function" { filename = data.archive_file.function-code.output_path function_name = "function-example" role = aws_iam_role.lambda_function_role.arn handler = "lambda_function.lambda_handler" source_code_hash = data.archive_file.function-code.output_base64sha256 runtime = "python3.12" memory_size = 128 timeout = 30 }
Lambdaスクリプトをtfファイルではなく、外部ファイルで管理できるようになります。
おまけ
local_fileを使った一風変わった使い方も紹介しておきます。リージョンを跨いでリソースを動的参照する方法です。
複数リージョン構成では、以下のようにリージョンごとにフォルダを分けることが多いと思います。
env/ ├─ap-northeast-1/ | ├─terraform.tf | ├─alb.tf | ├─s3.tf | └─route53.tf | ├─ap-northeast-3/ | ├─terraform.tf | └─alb.tf |
しかし別リージョンのリソースを参照する場合、aws_lb.test.zone_idのような動的参照ができないので、取得したいリソースの値をべた書きすることになります。
そこで、local_fileを使って動的に取得できるようにします。
local_fileを使って値をファイルに出力し、他リージョンのリソースからそのファイルを読み込む仕組みです。
以下の例では大阪リージョンにあるALBの値をファイルに出力し、東京リージョンではそのファイルを読み込んで、Route53に設定しています。
値のべた書きを避けられるのは良いですね。
参考
local_fileリファレンス registry.terraform.io
local_sensitive_fileリファレンス registry.terraform.io
archive_fileリファレンス registry.terraform.io