-
-
Notifications
You must be signed in to change notification settings - Fork 604
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
Engine Interface optimisations #59
Comments
Could you explain what you mean under:
I supposed that this must be transparent for applications i.e. apps just send the same requests as before but they batched in Centrifugo before publishing. Seems I miss something? |
I meant that for it to be useful, batching must be exposed right through to the client API. Even if we only choose to expose it via redis API, right now that just makes internal calls to API commands. I think we should support it on http API too though as it will make that much more powerful for medium to high throughput cases. I don't think backward incompatible changes are the best way though, I was just pointing out the options. My vote would be to make a new API command called 'publish_batch'. Internally we can just make existing publish and broadcast commands use the internal batch publish method. Make sense. Apologies I wasn't clear.
|
Part one done via #61 |
Part two. Yesterday I made proof of concept showing that we can actually batch publish requests to Redis over pipeline and this makes things more performant as we save time on RTT to Redis. But the hardest part is how to seamlessly add batching support to existing API.
Also we should keep the behaviour in which call to |
There is another option which I think is best. Why can't we just make whole engine async internally? I.e.:
This keeps the external synchronous interface but allows full use of pipelining with no extra config nor any trade off between latency and throughput. If for some reason we don't want to do that then we should at least use dynamic batching rather than fixed interval. I was going to write an article about this technique as its so simple and yet is about the only design choice in IO handling space that optimises both latency and throughput at same time: http://mechanical-sympathy.blogspot.co.uk/2011/10/smart-batching.html?m=1
|
Actually I thought about this option (I meant this as solution if choose option 1). But I thought to do this just for |
Didn't think too hard about it yet but I don't see why we wouldn't use the same mechanism for everything if we built it.
|
Part two released with v1.4.2 @banks do you have any thoughts about what should be done in next iteration? Maybe special
Requests like this (two publish commands in one request): [
{
"method": "publish",
"params": {
"channel": "channel1",
"data": {}
}
},
{
"method": "publish",
"params": {
"channel": "channel2",
"data": {}
}
},
] Will wait for at least 2 round-trips to Redis anyway, because Centrifugo will wait for response from publishing into |
As #90 merged I think we are done here (as far as I can see we've made all proposals and much more with that refactoring). |
With #52 we improved throughput enough to keep up with our publish volume for now.
However publishing messages that are almost all not actually delivered to anyone nr stored (thanks to #51) is using a lot of CPU and causing delivery latency to be slower than it could be in some cases.
To fix this I suggest we consider a few different optimisations:
addHistory
method and instead pass history options topublish()
.drop_inactive
optimisation.Batch publishing in 2. will require changes further up the stack though - the application itself will need to support batch publish API requests (should we make new API call? Or breaking change to current API params?).
This is becoming more important as we increase publish load and see CPU usage climb.
The text was updated successfully, but these errors were encountered: