S3+CloudFrontにてファイル更新の際にInvalidationを行うLambda関数の作成
S3のファイルが更新されたらCloudFrontのキャッシュをクリアしたいので、S3の更新をトリガーとしたLambda関数を作ってInvalidationを発行する。
以下手順書的な。
関数の作成
- 分かりやすい関数名を入力
- ランタイム Python3.7を選択
- 実行ロールはデフォルトのまま(基本的なLambdaアクセス権限で新しいロールを作成)
トリガーを追加
- トリガーを選択 -> S3
- バケットを選択
- 他はデフォルトのまま(必要があれば編集)
- 追加をクリック
コードの編集
CloudFrontのDistributionIdを以下のコードのxxxxxxxxxxに埋め込む。
lambda_function.py
from __future__ import print_function
import boto3
import time
def lambda_handler(event, context):
for items in event["Records"]:
path = "/" + items["s3"]["object"]["key"]
print(path)
client = boto3.client('cloudfront')
invalidation = client.create_invalidation(DistributionId='xxxxxxxxxx',
InvalidationBatch={
'Paths': {
'Quantity': 1,
'Items': [path]
},
'CallerReference': str(time.time())
})
備考
更新されたファイルごとにInvalidationが発行されるため、S3のファイルの更新頻度が高い場合はInvalidationの料金がかさむ(月1000件までは無料。それ以上は1件ごとに$0.005)点に注意。
問題になりそうなときはトリガーのプレフィックスとサフィックスを調整して、フラグとなるファイルが更新された場合のみItemsに「/*」(すべてのファイル)を指定して全クリアするのがいいだろう。例えば「trigger.invalidation」というファイルが更新された場合のみキャッシュクリアするなど。少し運用でカバー的な話になるが。
アクセス権限
- アクセス権限のタブを開く
- 実行ロール 編集をクリック
- IAMコンソールで表示をクリック
- アクセス権限 ポリシーをクリック
- ポリシーの編集をクリック
- ビジュアルエディタ さらにアクセス許可を追加する
- サービス名 CloudFront
- アクション CreateInvalidation
- ポリシーの確認
- 変更の保存