この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。
モバイルアプリサービス部の五十嵐です。
今回は1つのserverlessプロジェクトで複数のLambdaを管理してみます。JAWSやserverless 0.x系にはモジュールという単位でLambdaを管理できましたが、1.0系ではその機能がありません。ではどうやって複数のLambdaを管理するのでしょうか。
今回作成したソースコードはこちら。
環境
- serverless 1.0.0-rc.1
- node.js 4.3.2
- npm 2.14.12
複数のFunctionを作成する
複数のLambdaを定義するには、設定ファイルに複数のfunctionを記述すればよいです。極端な例ですが以下でも良いです。全く同じ機能でARNは異なるLambdaが2つ作成されます。
functions:
hello1:
handler: handler.hello
hello2:
handler: handler.hello
# sls deploy
Serverless: Packaging service...
Serverless: Uploading CloudFormation file to S3...
Serverless: Uploading service .zip file to S3...
Serverless: Updating Stack...
Serverless: Checking Stack update progress...
...........
Serverless: Stack update finished...
Service Information
service: sample
stage: dev
region: us-east-1
endpoints:
None
functions:
sample-dev-hello2: arn:aws:lambda:us-east-1:XXX:function:sample-dev-hello2
sample-dev-hello1: arn:aws:lambda:us-east-1:XXX:function:sample-dev-hello1
形式に直すと以下のとおりです。
functions:
<名前>:
handler: <ファイル名(拡張子を除く)>.<エントリーポイントの関数名>
<名前>:
handler: <ファイル名(拡張子を除く)>.<エントリーポイントの関数名>
実際には実行コードのファイルは別々に分け、共通する機能があれば別ファイルに切り出して参照させるかと思います。
今回はhandler2.jsというファイルをプロジェクトに追加しています。また、タイムアウト時間を60秒に変更しています。
functions:
slashCommands:
handler: handler.slashCommands
events:
- http:
path: slack/slash-commands
method: post
request:
template:
application/x-www-form-urlencoded: '{ "body": $input.json("$") }'
passThrough: NEVER
echo:
handler: handler2.echo
timeout: 60 # optional, default is 6
Functionごとのパッケージを作成する
前回までの定義は以下のとおりです。
# you can add packaging information here
package:
exclude:
- config/default_sample.json
- event.json
これでは共通の設定しかできないので無駄なモジュールなどが含まれてしまいます。それを防ぐために、functionごとにパッケージに入れる/入れないを設定できるようになっています。(参照: serverless/10-packaging.md)
まず package:
に individually: true
を設定します。これにより、functionごとにパッケージが作成されるようになります。個々のパッケージは、 packege:
と function:packege:
をマージした結果になります。重複する設定がある場合、 function:packege:
のほうが優先されます。
以下のように記述することで必要最小限のパッケージを作ることができました。
# you can add packaging information here
package:
individually: true
exclude:
- config
- event.json
- node_modules
- handler.js
- handler2.js
functions:
slashCommands:
handler: handler.slashCommands
package:
include:
- handler.js
- config/default.json
- node_modules/config
events:
- http:
path: slack/slash-commands
method: post
request:
template:
application/x-www-form-urlencoded: '{ "body": $input.json("$") }'
passThrough: NEVER
echo:
handler: handler2.echo
package:
include:
- handler2.js
timeout: 60 # optional, default is 6
Function毎のコマンド操作
デプロイは --function(-f) <名前>
オプションを付けることでFunctionごとにデプロイできます。 logs
などのコマンドも同様です。ただし注意しなくてはならないのは、serverlessのCloudFormationは1つだけということです。 remove
コマンドを実行したり、AWSコンソールからCloudFormationを削除すると全てのFunctionが削除されます。
まとめ
複数のLambda Functionを扱えることが分かりました。考えてみれば、実際にFunctionを数十個も連携させるようなLambdaはなかなかないわけですから、モジュールという単位は大きすぎたのかもしれませんね。現実的には多くても数個なので、この程度で十分なのかもしれません。また、まだ取り上げていない機能としてpluginsという機能があります。これはCLIコマンドを拡張するための機能のようです。
これらの変更点から、2度にわたる大きな仕様変更(JAWSからserverless0.x系、0.x系から1.x系)の歴史が垣間見えるような気がしました。