この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。
デプロイをCloudFormationテンプレート(IaC)化すると、デプロイパイプラインにスムーズに組み込むことができます。
今回は、コンテナイメージ版LambdaをCloudFormationでデプロイする方法を紹介します。
コンテナLambdaをデプロイするCloudFormation テンプレート
コンテナLambda(非VPC版)をデプロイするには、次のテンプレートを利用します。
AWSTemplateFormatVersion: '2010-09-09'
Parameters:
EcrImageUri:
Description: ECR image URI
Type: String
Resources:
LambdaFunc:
Type: AWS::Lambda::Function
Properties:
Role:
Fn::GetAtt:
- LambdaRole
- Arn
PackageType: Image
Code:
ImageUri: !Ref 'EcrImageUri'
Architectures:
- x86_64
MemorySize: 512
Timeout: 30
LambdaRole:
Type: AWS::IAM::Role
Properties:
AssumeRolePolicyDocument:
Version: '2012-10-17'
Statement:
- Effect: Allow
Principal:
Service:
- lambda.amazonaws.com
Action:
- sts:AssumeRole
Path: /
ManagedPolicyArns:
- arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole
コンテナ Lambda固有の記述について、かいつまんで紹介します。
コンテナ固有のプロパティ
コンテナLambdaの場合、 PackageType
プロパティに Image
を設定し、
コンテナイメージのURIを Code
プロパティで指定します。
Properties:
...
PackageType: Image
Code:
ImageUri: ECRのURI
...
本テンプレートでは、イメージURIをパラメーター化しています。
不要なプロパティ
コンテナLambdaの場合、以下のプロパティは不要です。
Runtime
(nodejs14.x
など)Handler
(index.handler
など)
コンテナLambdaをCloudFormationでデプロイしてみる
作成した CloudFormation テンプレートを利用し、コンテナLambdaをデプロしてみます。
ECR の作成
まずは、コンテナレジストリのAmazon Elastic Container Registry (ECR)を作成します。
$ aws ecr create-repository --repository-name test
{
"repository": {
"repositoryArn": "arn:aws:ecr:eu-central-1:123:repository/test",
"registryId": "123",
"repositoryName": "test",
"repositoryUri": "123.dkr.ecr.eu-central-1.amazonaws.com/test",
"createdAt": "2022-01-03T21:06:35+01:00",
"imageTagMutability": "MUTABLE",
"imageScanningConfiguration": {
"scanOnPush": false
},
"encryptionConfiguration": {
"encryptionType": "AES256"
}
}
}
アプリケーションの作成
次に動作確認用 Python アプリケーションを作成します。
app.py
と Dockerfile
の2ファイルを作成します。
app.py
app.py
import sys
def handler(event, context):
return 'Hello from AWS Lambda using Python' + sys.version + '!'
Dockerfile
Dockerfile
FROM public.ecr.aws/lambda/python:3.9
COPY app.py ${LAMBDA_TASK_ROOT}
CMD [ "app.handler" ]
イメージをビルド
このイメージをビルドします。
$ docker build -t test:latest .
ローカルで動作確認します。
# コンテナ起動用ターミナル
$ docker run -p 9000:8080 test:latest
# クライアント用ターミナル
$ curl -XPOST "http://localhost:9000/2015-03-31/functions/function/invocations" -d '{}'
"Hello from AWS Lambda using Python3.9.8 (main, Dec 10 2021, 06:31:09) \n[GCC 7.3.1 20180712 (Red Hat 7.3.1-13)]!"
実行出来ています。
ECR にイメージをプッシュ
このイメージをECRにプッシュします。
$ aws ecr get-login-password | docker login --username AWS --password-stdin アカウントID.dkr.ecr.リージョン.amazonaws.com
$ docker tag test:latest アカウントID.dkr.ecr.リージョン.amazonaws.com/test:latest
$ docker push アカウントID.dkr.ecr.リージョン.amazonaws.com/test:latest
コンテナ Lambda のデプロイ
CloudFormationテンプレートを使い、コンテナ Lambda をデプロイします。
$ aws cloudformation deploy \
--stack-name lambda-container-test \
--template-file ./cfn.yml \
--parameter-overrides EcrImageUri=アカウントID.dkr.ecr.リージョン.amazonaws.com/test:latest \
--capabilities CAPABILITY_IAM
--template-body
引数で CloudFormation テンプレートを指定し、--parameters
で ECR イメージの URI を指定します。
AWSコンソールからCloudFormationスタックを作成することも出来ます。
コンテナLambdaの動作確認
最後に、Lambda関数を動作確認します。
$ aws lambda invoke \
--function-name lambda-container-test-LambdaFunc-xxx \
--invocation-type RequestResponse \
--payload '{}' response.json && cat response.json
{
"StatusCode": 200,
"ExecutedVersion": "$LATEST"
}
"Hello from AWS Lambda using Python3.9.8 (main, Dec 10 2021, 06:31:09) \n[GCC 7.3.1 20180712 (Red Hat 7.3.1-13)]!"
無事実行できました。
AWS SAMでもデプロイ可能
コンテナ Lambdaをデプロイしたい場合、AWS サーバーレスアプリケーションモデル(AWS SAM)を使うアプローチも有力です。
AWSのAPIを逐一呼び出さずに済み、ディベロッパーの開発フローに寄り添ったコマンド体系が提供されています。
詳細は次のドキュメントを参照ください。
それでは。