AWS
lambda
APIGateway

API GatewayのLambda統合で嵌った話

今まで仕事でLambdaを触っていたけど、自宅で一から作ろうとしたら嵌ったので、その時の話を書いていきます。

仕事の記憶を頼りに、次のようなLambdaハンドラとserverless.ymlを書きました。ごく単純なPOSTメソッドで、リクエストボディからparamという値を取り出します。


handler.py

def handle_request(event, context):

body = event.get('body')
param = body.get('param')
# 以下省略


serverless.yml

functions:

sample:
handler: python:handler.handle_request
events:
- http: post sample

早速リクエストを送ってみると、502 Internal server errorが返ってきて、Lambdaのログには以下のエラーが出ていました。

[ERROR] AttributeError: 'str' object has no attribute 'get'

Traceback (most recent call last):
File "/var/task/handler.py", line 22, in handle_request
param = body.get('param')

あれ、おかしいな。仕事の時はbodyからgetするだけでパラメータを取得できていたのだが…。

で、調べてみると、Lambdaプロキシ統合が関係していることが分かりました。

Lambdaプロキシ統合.png

今までほとんど意識していませんでしたが、これを使用するとAPI GatewayがLambdaへうまい感じにリクエストパラメータ等を渡したり、Lambdaからのレスポンスを処理したりするようです。

ただし、リクエストボディはJSON形式ではなく文字列に変換されてしまうとのこと。Lambdaプロキシ統合を使用しないとJSON形式で扱えたので、この点だけは若干不便な気がします。


serverless.yml

functions:

sample:
handler: python:handler.handle_request
events:
- http:
path: sample
method: post
integration: lambda

このように書くと、Lambda統合はされますが、Lambdaプロキシ統合は使用されません。仕事ではこうしていたからgetだけでうまく行ったんだな。週明けに直さなきゃ!