2017-01-22 2 views
0

У меня есть следующий код лямбда-функция для просто распечатав Автор и метаданные закачиваемого случае ведро S3:«KeyError:„Records“» в AWS S3 - Лямбда триггер

from __future__ import print_function 
import json 
import urllib 
import boto3 

print('Loading function') 

s3 = boto3.client('s3') 


def lambda_handler(event, context): 

    #print("Received event: " + json.dumps(event, indent=2)) 
    # bucket = event['Records'][0]['s3']['bucket']['name'] 

    for record in event['Records']: 
     bucket = record[0]['s3']['bucket']['name'] 
     key = record[0]['s3']['object']['key'] 
     response = s3.head_object(Bucket=bucket, Key=key) 

     logger.info('Response: {}'.format(response)) 

     print("Author : " + response['Metadata']['author']) 
     print("Description : " + response['Metadata']['description']) 

Однако я Я получаю следующее сообщение об ошибке во время тестирования:

{ 
    "stackTrace": [ 
    [ 
     "/var/task/lambda_function.py", 
     17, 
     "lambda_handler", 
     "for record in event['Records']:" 
    ] 
    ], 
    "errorType": "KeyError", 
    "errorMessage": "'Records'" 
} 

я делаю что-то неправильно при обращении к имени ведро и ключ имя объекта S3? Если нет, то что я делаю неправильно здесь?

+0

Какой тип триггера S3 вы используете? – franklinsijo

+0

@franklinsijo 'Тип события: ObjectCreated' – Dawny33

+0

И это тестовое событие или реальное событие ?. Вы можете распечатать 'event' и проверить, содержит ли он' Records'? – franklinsijo

ответ

3

бит поздно на вечеринку. Но вот мой первый пост!

ОБЪЯСНЕНИЕ:

При тестировании в лямбда-панели -> Защита lambda_handler (событие, контекст) < - событие вводятся непосредственно.

Однако в AWS API его к необходимому добавить Mapping Template или иначе -> событие < - пусто, в результате чего опрашивать:

"errorType": "KeyError", "errorMessage": "'Records'"

это нулевой указатель. Записи не существует, поскольку -> событие < - не существует.

РЕШЕНИЕ:

Вам необходимо настроить Integration Request внутри AWS API. Нажмите на Шаблоны для оформления тела. Затем добавить Mapping Template Установить тип содержимого для приложения/JSON Затем редактирования сгенерированных шаблон отображения:

{ 
 
    "body" : $input.json('$'), 
 
    "headers": { 
 
    #foreach($header in $input.params().header.keySet()) 
 
    "$header": "$util.escapeJavaScript($input.params().header.get($header))" #if($foreach.hasNext),#end 
 

 
    #end 
 
    }, 
 
    "method": "$context.httpMethod", 
 
    "params": { 
 
    #foreach($param in $input.params().path.keySet()) 
 
    "$param": "$util.escapeJavaScript($input.params().path.get($param))" #if($foreach.hasNext),#end 
 

 
    #end 
 
    }, 
 
    "query": { 
 
    #foreach($queryParam in $input.params().querystring.keySet()) 
 
    "$queryParam": "$util.escapeJavaScript($input.params().querystring.get($queryParam))" #if($foreach.hasNext),#end 
 

 
    #end 
 
    } 
 
}

И функция редактирования Lambda:

заменить:

for record in event['Records']:

с:

for record in event['query']['Records']

не знаю, будет ли стек свистеть вам этот ответ - так я называю вас @ Dawny33 @KevinOelen @franklinsijo

Что касается объяснения я понял это сам , Однако «шаблон сопоставления» исходит от https://medium.com/simple-thoughts-amplified/passing-variables-from-aws-api-gateway-to-lambda-3c5d8602081b