Lambda + API Gateway の実行に 10秒以上かかることがある
この記事のコード、VPC 内で RDS に1行挿入してるだけなのに curl で実行してレスポンス返ってくるまでに 10秒以上かかることがザラにあります。
どこに時間がかかってそうか
怪しいポイントを抑える
- 怪しいポイント1: コンテナ起動のタイミング
- Lambda はコンテナ上で実行される
- コールされた時にコンテナがなかったらコンテナ作成から始める
- 1回コンテナが死んだ後の初期化のタイミングが怪しい
- → コンテナは 1回立ち上がったら 15〜20分生きているっていう話なので、15〜25分間隔でコールする
- 怪しいポイント2: RDS 接続
- RDS に接続する際に時間がかかっている可能性もある
- → RDS に接続するファンクションと接続しないファンクションそれぞれで計測
- 怪しいポイント3: VPC 絡み
- Lambda は CloudFront 使ってそうなので、VPC 使う場合に無理が出そう
- → VPC 使うファンクションと No VPC のファンクションそれぞれで計測
- 怪しいポイント4: 言語による違い
- 使用する言語でコンテナ初期化に有意の差が出そう
- → ランタイムを nodejs と Python にした場合それぞれで計測
計測した組み合わせ・手法
上記の怪しいポイントを調べるため、下記のコードで試してみました。
個人的な親しみやすさから nodejs と Python でしかやってません。
- nodejs, VPC, RDS 接続して 1行インサートするコード
- nodejs, VPC, 入力値を返すだけのコード
- nodejs, No VPC, 入力値を返すだけのコード
- Python, VPC, RDS 接続して 1行インサートするコード
- Python, VPC, 入力値を返すだけのコード
- Python, No VPC, 入力値を返すだけのコード
- 実際に計測に使用したコードはこちら
- フレームワークは Serverless を使用
- 上記コードそれぞれを単体で、ある程度の期間毎時 0,15,35分 に curl からコールした
計測結果
1. nodejs/VPC/RDS | 2. nodejs/VPC/No RDS | 3. nodejs/No VPC | 4. Python/VPC/RDS | 5.Python/VPC/No RDS | 6. Python/No VPC | |
---|---|---|---|---|---|---|
AVG (s) | 6.101391304 | 5.86835443 | 0.3762264151 | 1.295380165 | 1.415769231 | 0.786875 |
STDEVP | 6.327611794 | 6.100448888 | 0.3658991325 | 3.468776883 | 3.516890337 | 1.419660767 |
MAX (s) | 18.345 | 18.102 | 1.794 | 14.84 | 14.648 | 5.465 |
MIN (s) | 0.189 | 0.214 | 0.208 | 0.175 | 0.209 | 0.225 |
意外と明確な差が出ました。
ばらつきが大きいので平均値にあまり意味はなく、
MIN 値を大きく上回る回数が焦点になりそうです。
集計前の全データはこちら (Google SpreadSheet)
まとめ
- VPC を利用する場合、実行にものすごく時間がかかることがある
- VPC を利用する場合、Python の方が nodejs よりも相対的に速そう
- そもそも Lambda では非同期処理がさほど意味ない上に遅いのであれば nodejs 使う意味って
- 単純なコードしか試してないからかもしれないが
- Python 使うにしても REST API で 10秒以上かかるのは許容しがたい
- 平均値だけ見るとうっかり許容しそうになるけど...
- 時間かかってるタイミングとコンテナ初期化のタイミングが一致するのか調べるべき
- ランタイムによってコンテナの寿命が違うのか
- 同一プロジェクト内に複数のファンクション作った場合にコンテナは共用されるのか
- されるのであれば、コンテナ初期化用のファンクションを別に作っておいて、あらかじめ起こしておけば実用に耐えうるかも?