Process timeout | Amazon Lambda for Firebase

I wrote the code in node.js and my data is on Firebase. The problem I am facing is that my code never exits. I made it as a Link

The problem is that the firebase link or listener never becomes null, and so my function never exits. I tried using firebase.database().goOffline() , but that did not work.

On my local machine, I decisively stopped the process using process.exit(0) , but when I deployed my code to AWS lambda, it does not return any response / callback and exits (error message " Process completed before request completion ")

I also added a wait of 5-10 seconds after calling the callback to the lambda, and then forcibly quit the process, but that didn't help either.

How to fix this problem? Please, help.

+3
source share
4 answers

After going through the crisis, any new lambda user has left.

As suggested, you can use context.done to stop. However , this is not recommended as it is only possible because of the historical versions of runj versions.


why does this timeout occur?

Your lambda may fall into the last line of your code and continue to work. Well, actually it is waiting for something, because the event loop will be empty.

what does it mean?

In nodejs, when you perform an async operation and register a callback function that will be executed after the operation is completed, the registration is sorted in the event loop.

On one line, this is an event loop that knows which callback function should execute when the async operation completes. But this is to another thread :)


back to lambda

Given the above information, it follows that the lambda should not stop before the empty chain of events is reached - as this means that the subsequent procedure will not be performed after some asynchronous return of goods.

What if you still need to stop execution manually? regardless of the state of the event loop? At the beginning of the function, do:

 context.callbackWaitsForEmptyEventLoop = false 

And then use the third parameter that you get in the handler signature. This is a callback .

callback parameter

This is the function that you call when you want to complete the execution.

If you call it without parameters or with the first parameter as zero, and the text as the second parameter, it is considered a successful call.

To make lambda execution fail, you can call the callback function with some non-zero value as the first parameter.

+7
source

Add this line to the top of your handler function, and then you can use the callback without any problems:

 function handler (event, context, callback) { context.callbackWaitsForEmptyEventLoop = false // Add this line } 
+4
source

Calling callback funciton and then process.exit(0) did not help in my case. goOffline() the firebase method didn’t help either.

I fixed the problem calling context.done(error, response) (instead of the callback method). Now my code is working.

However, if anyone has a better solution, welcome here. This may help someone else :)

+1
source

Setting callbackWaitsForEmptyEventLoop to false should only be your last resort if nothing works for you, as this can lead to worse errors than the problem you are trying to solve here.

This is what I do instead to ensure that every call has firebase initialization and is deleted before exiting.

 // handlerWithFirebase.js const admin = require("firebase-admin"); const config = require("./config.json"); function initialize() { return admin.initializeApp({ credential: admin.credential.cert(config), databaseURL: "https://<your_app>.firebaseio.com", }); } function handlerWithFirebase(func) { return (event, context, callback) => { const firebase = initialize(); let _callback = (error, result) => { firebase.delete(); callback(error, result); } // passing firebase into your handler here is optional func(event, context, _callback, firebase /*optional*/); } } module.exports = handlerWithFirebase; 

And then in my lambda handler code

 // myHandler.js const handlerWithFirebase = require("../firebase/handler"); module.exports.handler = handlerWithFirebase( (event, context, callback, firebase) => { ... }); 
0
source

Source: https://habr.com/ru/post/1262773/


All Articles