Closed iamskar closed 5 years ago
Same over here.
(node:14604) UnhandledPromiseRejectionWarning: TypeError: Cannot read property 'done' of undefined
at createLambdaContext (/project/node_modules/serverless-offline/src/index.js:671:44)
at fail (/project/node_modules/serverless-offline/src/createLambdaContext.js:18:21)
at process._tickCallback (internal/process/next_tick.js:68:7)
(node:14604) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 1)
Seems like this line -> if (this.requests[requestId].done) {
in serverless-offline/src/index.js:671
raises the exception.
EDIT Added the following above the faulty line in there and seemed to work for me.
this.requests[requestId] = this.requests[requestId] || {};
I can also confirm this. It was introduced on version 4.10.1
. Version 4.10.0
works OK.
Function:
module.exports.handler = async event => {
try {
// ...
await someDatabaseQuery(); // Fulfills OK
// ...
return {
// Success response...
};
} catch (err) {
return {
// Error response...
};
}
};
Output:
(node:8187) UnhandledPromiseRejectionWarning: TypeError: Cannot read property 'done' of undefined
at createLambdaContext (/project/node_modules/serverless-offline/src/index.js:662:44)
at fail (/project/node_modules/serverless-offline/src/createLambdaContext.js:18:21)
at <anonymous>
at process._tickDomainCallback (internal/process/next_tick.js:229:7)
(node:8187) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 1)
Please check out the v4.10.3 and tell us if it is ok now :)
I can confirm on my system v4.10.3 works fine :) Thanks.
Confirmed works fine with "serverless-offline": "^4.10.3" 👍 Thanks @dherault
Thank @Andorbal 👍
Hi i'm having same issue, when run with NestJs here. Even if with "^4.10.3". https://github.com/fshidemo/serverless-nestjs
I think: this.requests[requestId] = this.requests[requestId] || {};
or something like this still need to control this situation
if (requestId in this.requests) { // do some logic } else { // do else }
The same error still persists with ^4.10.3
.
It seems to be working fine for me in latest 4.10.3
.
Can be verified that it's not working with 4.10.3 in this demo: https://github.com/mkondel/serverless-offline-test
It's still failing for me in 4.10.3
as well.
(node:2229) UnhandledPromiseRejectionWarning: TypeError: Cannot read property 'done' of undefined
at createLambdaContext (/home/circleci/project/node_modules/serverless-offline/src/index.js:671:44)
at handler.catch.then.then.response (/home/circleci/project/functions/dist/service/src/handlers/webpack:/packages/service/src/lib/apiGatewayHandler.ts:133:1)
at <anonymous>
at process._tickDomainCallback (internal/process/next_tick.js:229:7)
My fix addressed the truly async promise scenario, but it looks like @mkondel issue is a truly async callback scenario. I've got a failing test that proves this out:
it('should support handler that defers and uses done()', done => {
const offline = new OfflineBuilder(new ServerlessBuilder(serverless))
.addFunctionHTTP('index', {
path: 'index',
method: 'GET',
}, (request, context, serverlessDone) =>
setTimeout(() =>
serverlessDone({
statusCode: 200,
body: JSON.stringify({ message: 'Hello World' }),
}),
10)
).toObject();
offline.inject({
method: 'GET',
url: '/index',
payload: { data: 'input' },
}, res => {
expect(res.headers).to.have.property('content-type').which.contains('application/json');
expect(res.statusCode).to.eq(200);
expect(res.payload).to.eq('{"message":"Hello World"}');
done();
});
});
Put that right after the test "should support handler returning Promise that defers" in offline.js
and when you run tests, you'll see it fails with the error everyone is seeing. I don't know enough about that memory leak fix to know why the finally block is the way it is, so I'm not sure what to do about this specific scenario. I can personally ignore it because I'm using promises all the way down.
@mkondel, you can work around your problem by replacing line 5 of lambdas/index.js
with:
module.exports.react = (event, context) => sls(server, { binary: binaryMimeTypes })(event, context);
It's not pretty, but it looks like serverless-http is getting the done()
function from serverless-offline and assuming that you want to use a callback and not a promise. serverless-offline is giving you the option to use either, and figures out which you wanted to use by whether you get a promise back or not. So that puts you in the currently broken scenario.
@Andorbal thank you for that work around, I will test it out.
Edit: Your fix now works in the demo and in my full app!
@Andorbal Can you PR a fix for this bug this week ? Otherwise I'll revert to 4.10.0
What about v4.10.4?
@dherault seems to work for me.
Hi,
I have a simple code and i am running into this error :
(node:64802) UnhandledPromiseRejectionWarning: TypeError: Cannot read property 'done' of undefined at createLambdaContext (/Users/suri/Documents/Projects/Aptimise/subscription-services/node_modules/serverless-offline/src/index.js:671:44) at fail (/Users/suri/Documents/Projects/Aptimise/subscription-services/node_modules/serverless-offline/src/createLambdaContext.js:18:21) at process._tickCallback (internal/process/next_tick.js:68:7) (node:64802) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 2)
my code
`"use strict";
const fetch = require("node-fetch");
module.exports.handler = async (event, context, callback) => { try { const response = await fetch("https://reqres.in/api/users").catch(err => callback(err) ); const data = await response.json(); console.log(data); // if (!response.ok) { // // NOT res.status >= 200 && res.status < 300 // return { statusCode: response.status, body: response.statusText }; // } //const data = await response.json();
} catch (err) { //callback(err); } //console.log(data); callback(null, { statusCode: 200, body: JSON.stringify({ data: "somedata" }) }); }; `
Packages -
"serverless-offline": "^4.10.2" "node-fetch": "^2.5.0", "serverless: "1.42.3"
What am i doing wrong here ?