紹介する内容
- localstackでlambdaを作ります
- localstackのdocker-entrypoint-initaws.dを使う。主にterraformを使います
- ユーザーが指定したディレクトリにpackageをインストールします
- インストールしたpackageをzipに固めます
結論
-
lambdaのpackageのインストールを別のdockerコンテナにしたら、いろんな言語のpackageインストールに対応できます
- localstackのコンテナにpythonのvenvなどのバージョン管理ツールをインストールして使う手もあります。ですが、言語ごとにツールの使い方を思えるより、dockerの使い方を覚えて全言語をカバーする方が効率的だと思いました
-
別のdockerコンテナでterraformをインストールして実行するから、HOSTマシン(MACやwindows)にインストールされているterraformを気にしなくてもいいと思います。
-
localstackのdocker-entrypoint-initaws.dでterraformを使うことで開発環境プロビジョニングするコストが減ります
- 例えば本番環境用terraformを持っていたら、開発環境用に少し修正してlocalstackですぐ使えます
紹介始めます
localstack紹介
実のAWSを使わずにいろいろ試せるものです。
バージョン0.11.0から大きな変化がありました。本記事は0.11.0バージョンのlocalstackを使います
https://github.com/localstack/localstack
terraform紹介
コードでインフラを管理できます。
https://www.terraform.io/
ディレクトリ構成
全体ソースコードは https://github.com/cheekykorkind/qiita-example/tree/master/localstack/0.11.0/init-by-terraform で確認できます
localstack構築
docker composeを使います。
version: '3'
services:
pip_installer:
container_name: 'pip_installer'
image: python:3.7-alpine3.10
tty: true
working_dir: /workspace/sam-lambda
environment:
LAMBDA_ZIP_PATH: /workspace/sam-lambda/hello_world/lambda.zip
TERRAFORM_PATH: /workspace/terraform
volumes:
- ./sam-lambda:/workspace/sam-lambda
- ./terraform:/workspace/terraform
localstack:
container_name: 'localstack-dev'
image: localstack/localstack:0.11.0
ports:
- '4566:4566'
environment:
SERVICES: lambda,logs,dynamodb
DEBUG: 1
HOSTNAME_EXTERNAL: localstack
EDGE_PORT: 4566
PORT_WEB_UI: 8080
AWS_ACCESS_KEY_ID: AKIAIOSFODNN7EXAMPLE
AWS_SECRET_ACCESS_KEY: wJalrXUtnFEMI/K7MDENG/bPxRfiCYEXAMPLEKEY
AWS_DEFAULT_REGION: us-east-1
LAMBDA_ZIP_PATH: /workspace/sam-lambda/hello_world/lambda.zip
volumes:
- /var/run/docker.sock:/var/run/docker.sock
- ./initaws:/docker-entrypoint-initaws.d
- ./tmp/localstack:/tmp/localstack
- ./sam-lambda:/workspace/sam-lambda
depends_on:
- pip_installer
docker-composeのvolumes(マウント)設定
-
localstackコンテナ
- packageインストールやzipファイル共有するために、AWS SAMプロジェクトをマウントしておきます。
-
./sam-lambda
は絶対パスqitta-example/localstack/0.11.0/init-by-terraform/sam-lambda
と同じです
-
- localstackの
docker-entrypoint-initaws.d
機能を使うためにマウントして置きます-
./initaws
は絶対パスqitta-example/localstack/0.11.0/init-by-terraform/initaws
と同じです
-
- packageインストールやzipファイル共有するために、AWS SAMプロジェクトをマウントしておきます。
-
pip_installerコンテナ
- packageインストールやzipファイル共有するために、AWS SAMプロジェクトをマウントしておきます。
-
./sam-lambda
は絶対パスqitta-example/localstack/0.11.0/init-by-terraform/sam-lambda
と同じです
-
- terraformを使用するためにマウントしておきます
-
./terraform
は絶対パスqitta-example/localstack/0.11.0/init-by-terraform/terraform
と同じです
-
- packageインストールやzipファイル共有するために、AWS SAMプロジェクトをマウントしておきます。
docker-composeの環境変数設定
-
localstackコンテナ
-
SERVICES
、DEBUG
、HOSTNAME_EXTERNAL
、EDGE_PORT
、PORT_WEB_UI
はlocalstack固有の環境変数です。localstackを調べると理解できると思います -
AWS_ACCESS_KEY_ID
、AWS_SECRET_ACCESS_KEY
、AWS_DEFAULT_REGION
はaws cliを便利に使うために設定しました -
LAMBDA_ZIP_PATH
はlambda生成に使うzipファイルの位置を書きました。コンテナ2つが連携して作業するから管理しやすくするために設定しました
-
-
pip_installerコンテナ
-
LAMBDA_ZIP_PATH
はlambda生成に使うzipファイルの位置を書きました。コンテナ2つが連携して作業するから管理しやすくするために設定しました -
TERRAFORM_PATH
はterraformファイルのパスです。terraformコマンド実行するためにterraformファイルがいるところに移動する必要があります。便利な移動のために事前に指定しておきました
-
docker-compose upによる作業の流れ
- pip_installerコンテナが作れる
- localstackコンテナが
depends_on
しているから、localstackコンテナより先に作られます -
tty: true
オプションによって、作れた後もup状態を維持します
- localstackコンテナが作れる
- コンテナが作れた後、localstack固有の
もろもろ初期化
作業が行われます
- docker-entrypoint-initaws.dディレクトリにあるshファイルを名前順で実行します
- localstackの固有機能です。
-
もろもろ初期化
作業が終わったら、マウントしているqitta-example/localstack/0.11.0/init-by-terraform/initaws
の00_create_lambda_zip.sh
を実行してくれます。
- 00_create_lambda_zip.sh
- 待機していたpip_installerコンテナにdockerコマンドで入ります
- pythonのpackageをディレクトリ
qitta-example/localstack/0.11.0/init-by-terraform/sam-lambda/hello_world/packages
に指定し、インストールします - pythonコード及びインストールしたpackageたちをzipで固めて
$LAMBDA_ZIP_PATH
に置きます - terraformをインストールしあます
- terraformファイルがいる
$TERRAFORM_PATH
に移動します - terraform initします
- terraform applyします。同時にterraformでlambdaのzipパス(
$LAMBDA_ZIP_PATH
)を渡します - terraformによってlambdaが作られます
- pip_installerコンテナを終了し、削除します
localstackで作ったlambdaを試します
docker-compose up -d && docker attach localstack-dev
します
cd qitta-example/localstack/0.11.0/init-by-terraform
docker-compose up -d && docker attach localstack-dev
docker attach localstack-devしているあからlocalstackコンテナの作業が見れます
terraformをインストールします
pythonのpackageがpipによってインストールされてます
インストール終了後、zipで固めてます
terraform initします
lambdaが作られました(terraform apply)
コンソールをもう一個開いて、localstackのlambdaにinvokeします
左側が docker attach localstack-dev
している方、右側が docker exec -it localstack-dev /bin/bash
してlambdaをinvokeする方です。
200返すことからちゃんと動いた確認が取れました。
lambdaのコードはrequestsパッケージを使ってGET一回投げることをしています。
qitta-example/localstack/0.11.0/init-by-terraform/sam-lambda/hello_world/app.py