Search code examples
node.jsamazon-web-servicesaws-lambdalambda

sometimes lambda.invoke doesn't trigger lambda call


I have a long running download task that is being performed by download-lambda function. download-lambda function gets executed from other lambda function code, let's call it calling-other-lambda function.

Calling-other-lambda function

      try{

           lambda.invoke({
                FunctionName: `download-lambda`,        //<<<<<----- calling download-lambda function with lambda.invoke
                InvocationType: 'RequestResponse',
                Payload: JSON.stringify({
                    path: `api/download`,
                    headers: { "Content-Type": "application/json" },
                    body: JSON.stringify(req?.body),
                    httpMethod: "POST"
                }),
            }).promise();

         }catch(e){
               console.log(e);
         }

download-function

   // download - function code written in Nodejs

   // connect to RDS-MYSQL

   // fetch data from MYSQL can take 5-7 miuntes

   // preparing data

   // sending email with prepared data to user

download-function execution may take long time - 5, 10, 20 mins. It depends on the type of the request.

Problem:

Problem is, for some unknown reason, sometimes Calling-other-lambda function calls download-function and sometimes it doesn't. I don't want to wait for response to come back to Calling-other-lambda function from download-function. It is just fire & forget pattern.

I want to be able to execute download-function every time when called from Calling-other-lambda function. Event If previous call is being executed, new call must execute (parallelly) successfully.

How can I make sure it calls download-function every time ? IF it fails to call download-function, how can I capture failure and notify user that call was not successful?


Solution

  • Changing the InvocationType to Event in your lambda.invoke() call will make the invocation asynchronous (fire and forget).

    Event – Invoke the function asynchronously. Send events that fail multiple times to the function's dead-letter queue (if one is configured). The API response only includes a status code.

    This means that the calling-other-lambda will return immediately after triggering the download-lambda function, and it won’t wait for it to finish executing.

    I can also make an educated guess that your Lambda function might be timing out after 15 minutes, which is the reason for its occasional 'failure'. Otherwise, it should be invoked consistently.

    This should work:

    try {
        lambda.invoke({
            FunctionName: `download-lambda`,
            InvocationType: 'Event',
            Payload: JSON.stringify({
                path: `api/download`,
                headers: { "Content-Type": "application/json" },
                body: JSON.stringify(req?.body),
                httpMethod: "POST"
            }),
        }).promise();
    } catch(e) {
        console.log(e);
        // Here you can add code to notify the user about the failure
    }