-
-
Notifications
You must be signed in to change notification settings - Fork 2.6k
Block new incoming requests once close has been called #886
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
|
I'm -1 with this feature (from my point of view this is a breaking behaviour change). Anyway I'm +1 if the |
Actually, it can be interpreted as a bugfix. |
mcollina
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The example with inject is wrong. Can you use a http request with an agent with keep-alive?
@allevo, this is necessary for send() to actually work. If there is a keepalive connection, the connection is never severed, making a graceful disconnect not possible.
Really? I assumed it was FIFO. So in this code: fastify.onClose(async () => {
// This is called second
})
fastify.onClose(async () => {
// And this is called first
})? |
|
I don't understand. I expect that the HTTP server is closed before any other dependencies. Is this the currently behaviour ? |
@nwoltman yes. The reason is because the last plugin you have have registered should be the first you must close. |
|
@delvedor You're right, I forgot about the keep-alive connections. Would it help to include a |
|
The changes LGTM, although I think @mcollina has a good point about testing with something that uses keep-alive connections instead of |
|
I'm trying to write a test with keep alive, but I'm having some trouble to get it working. |
|
@delvedor you should verify it's reusing the same socket. I don't think it is, as you are not resuming the response. Also, add a |
|
It seems that AppVeyor is failing for a test that is not present in this branch 🤔 |
| if (closing === true) { | ||
| res.writeHead(503, { | ||
| 'Content-Type': 'application/json', | ||
| 'Content-Length': '80', |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Could you calculate it based on the payload as with 404 ?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That 80 is the length of the json response ;)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I know. It's better to write payload.length
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is the payload length.
We can do the same at the line you have pointed pointed out, since the payload will be always the same.
|
@delvedor I'm trying to reproduce it on my machine. |
|
@delvedor can't reproduce it on local Node 6.13.1 |
|
@StarpTech one of the two AppVeyor logs shows |
|
@delvedor no idea. Try to rebuild. |
|
I can't, @mcollina should do it. |
|
done. |
|
You'll need to increaase that timeout: https://ci.appveyor.com/project/mcollina/fastify/build/job/x2ml3eliuojq3au2#L41. |
|
@delvedor performance of what? The request / response shouldn't be effected. |
|
@StarpTech for every new connection you should update a |
|
@delvedor you are worried about to maintain a set? What's the alternative to close all pending connections? From my understanding, the problem is that |
|
I'm worried about the cost of maintaining a Regarding
|
|
@delvedor https://github.com/hunterloftis/stoppable This looks promising refer to design and performance. |
|
There is also an interesting thread about it nodejs/node#2642 Node.js does not close existing, idle connections. We should support it. |
|
@StarpTech I know, I've already read that issue before open this pr. What I don't understand it's why the test are failing in travis but not in my local machine. |
|
They are failing really randomly. Sometimes it works sometimes not. Try to run the single test in isolation. |
4a40e67 to
30428f3
Compare
30428f3 to
930292a
Compare
|
@mcollina can you check if the usage of |
mcollina
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you move the autocannon tests to a new file?
89d7374 to
affc212
Compare
|
Done, I've also added another check. |
test/close-pipelining.test.js
Outdated
| t.strictEqual(codes.shift(), statusCode) | ||
| }) | ||
|
|
||
| instance.on('done', () => t.pass()) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you use t.done? It is more clear
| } else { | ||
| done(null) | ||
| } | ||
| app.once('preReady', () => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe overwriting avvio ready method fits better here. Or not?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you rephrase?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Putting the onClose handler inside preReady event doesn't ensure that the callback is invoked before any others. It does only if the preReady callbacks are fired in FIFO.
We use
https://github.com/mcollina/avvio/blob/a957201b0b33facf06687a5ba8e52c82a46b1302/boot.js#L13
and creating ready method inside fastify.
The new method forces the add onClose handler as the last, so the first one to be invoked.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It does only if the preReady callbacks are fired in FIFO.
They are, it is an event emitter.
We can't use ready inside Fastify, because ready will start the boot sequence.
allevo
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM (once tests are passing)
mcollina
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM with green CI
|
Green CI! 🎉 |
|
This pull request has been automatically locked since there has not been any recent activity after it was closed. Please open a new issue for related bugs. |
Currently, if a user calls
fastify.closeand the server is under a heavy load, the server will not close until there is an open TCP connection, so every new request will execute the entire request lifecycle.With this change once
fastify.closeis invoked, Fastify will automatically start to respond with a503error, closing every new connection as soon as possible.There are not sensible changes in the benchmarks.
Checklist
npm run testandnpm run benchmark