Функция AWS лямбда перестает работать после выключения ошибки
У меня есть простая лямбда-функция, которая асинхронно выполняет вызовы API и затем возвращает данные. 99% времени это отлично работает. Когда API когда-либо занимает больше времени, а затем ждал лямбда-тайм-аут, он дает ошибку, как ожидалось. Теперь проблема заключается в том, что когда я делаю последующие вызовы функции лямбда, она постоянно дает мне ошибку тайм-аута.
"errorMessage": "2016-05-14T22:52:07.247Z {session} Task timed out after 3.00 seconds"
Чтобы проверить, что это так, я установил тайм-аут лямбды на 3 секунды и способ запуска этих двух функций в лямбда.
Javascript
function now() {
return response.tell('success');
}
function wait() {
setTimeout(function() { return response.tell('success'); }, 4000);
}
Когда я вызываю функцию now
, проблем нет. Когда я вызываю функцию wait
, я получаю ошибку таймаута, а затем любые последующие вызовы now
дают мне ту же ошибку.
Это ожидаемое поведение? Я думаю, что любые последующие вызовы лямбда-функции должны работать. Я понимаю, что всегда могу увеличить таймаут конфигурации, но скорее не буду.
Ответы
Ответ 1
Вы должны посмотреть, как работает ваш дескриптор функции с определенным
context.callbackWaitsForEmptyEventLoop
Если этот логический тип false
, setTimeout никогда не будет запущен, потому что вы могли бы ответить или обработать вызов лямбда ранее.
Но если значение callbackWaitsForEmptyEventLoop
равно true
- тогда ваш код будет делать то, что вы ищете.
Кроме того, возможно, проще обрабатывать все через обратные вызовы напрямую, без необходимости "ручных" тайм-аутов, изменения тайм-аутов конфигурации и т.д....
например.
function doneFactory(cb) { // closure factory returning a callback function which knows about res (response)
return function(err, res) {
if (err) {
return cb(JSON.stringify(err));
}
return cb(null, res);
};
}
// you're going to call this Lambda function from your code
exports.handle = function(event, context, handleCallback) {
// allows for using callbacks as finish/error-handlers
context.callbackWaitsForEmptyEventLoop = false;
doSomeAsyncWork(event, context, doneFactory(handleCallback));
};
Ответ 2
Хорошо, если вы определили 3 секунды в своей конфигурации функций, этот тайм-аут переопределит время внутри вашего кода, поэтому обязательно увеличьте время ожидания из ваших конфигураций лямбда-функции и повторите попытку wait(), и он должен работать!
Ответ 3
Я столкнулся с одной и той же проблемой, на самом деле существует много случаев, когда Lambda становится невосприимчивой, например:
-
Разбор недействителен json:
exports.handler = function(event, context, callback)
{
var nonValidJson = "Not even Json";
var jsonParse = JSON.parse(nonValidJson);
-
Доступ к свойству переменной undefined:
exports.handler = function(event, context, callback)
{
var emptyObject = {};
var value = emptyObject.Item.Key;
-
Не закрывать соединение mySql после доступа к RDS приводит к тайм-ауту Lambda, а затем становится невосприимчивым.
Когда я говорю, что он не отвечает, буквально даже не загружая, т.е. сначала печатать внутри обработчика не печатается, а Lambda просто выходит из каждого прогона с таймаутом:
exports.handler = function(event, context, callback)
{
console.log("Hello there");
Это ошибка, известная команде AWS почти год:
https://forums.aws.amazon.com/thread.jspa?threadID=238434&tstart=0
К сожалению, он все еще не исправлен, после некоторых тестов выяснилось, что на самом деле Lambda пытается перезагрузить (перезагрузить контейнер?), просто не хватает времени. Если вы установите тайм-аут на 10 секунд, то после ~ 4 секунд выполнения Lambda начнет работать, а затем в следующих прогонах будет вести себя нормально. Я также пробовал играть с настройкой:
context.callbackWaitsForEmptyEventLoop = false;
и помещая все блоки "require" внутри обработчика, ничего действительно не работает. Единственный способ предотвратить Lambda, чтобы быть мертвым, устанавливает более высокий тайм-аут, 10s должно быть более чем достаточно в качестве обходной защиты от этой ошибки.
Ответ 4
В конфигурации Amazon console AWS вам нужно изменить тайм-аут по умолчанию с 3 секунд до более (максимум 5 мин)