※handlerの設定方法を根本的に勘違いして半日ぐらい無駄にした感じがするので、自戒を込めて記録を残しておきます。
結論
Lambdaのハンドラの指定方法は、file-name.function-name
という形式なので、
- 間違い:path.to.module.handler
- 正しい:path/to/module.handler
作業記録
やりたかったこと
小さいサービス向けに、Lambda関数のセットをまとめた状態でzipにしたものを関数作成時に指定したくて、
フォルダ構成
+ attakei/
+ __init__.py
+ models.py
+ handlers.py
ファイルの中身(一部)
attakei/handlers.py
def get_articles(event, context):
return {}
def search_by_tags(event, context):
return {"""something"""}
のような構成にした上で、Lambda関数作成時に、attakei.handlers.get_articles のように各種ハンドラーを指定していくことで、関数をセットで管理したい。
なぜかできない
この状態でAWSのルール通りにzipを作成してS3にアップロード→上記の書式でハンドラーを指定すると、Test実行時に全く動かない。こんなログが出続ける。
Unable to import module 'attakei.handlers': No module named attakei.handlers
トライ&エラー
上の結論に至るまでに試してみたことの羅列
- lambda-uploadを使ってアップロード ... NG
- main.pyを用意して、main内の関数で
attakei.handlers.get_articles
を呼ぶようにする ... OK - main.pyを用意して、main内では
from attakei.handler import get_articles
のみ書いて、main.get_articlesをハンドラー登録する ... OK
この辺で、「なんだこれ?」と感じで ドキュメント読みに行ってハッとなって問題点解決。
ドキュメントはちゃんと読まないとダメですね
愚痴
pythonのパッケージ作る際にコンソールコマンドを定義する時って、モジュールパス:関数名
って記載するから、完全に意識をそっちに向けてしまって脳が停滞してしまっていた模様。
でも、この形式に合わせてもらった方が個人的にはありがたかったかな...