-
Notifications
You must be signed in to change notification settings - Fork 419
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
CachedThreadPool does not spin down idle threads #1075
Comments
Following: ruby-concurrency/concurrent-ruby#1075 Current implementation in Ruby Concurrent is not spinning down threads New implementation is simpler and as a bonus respects Discourse database conventions so it is multisite safe (discourse fonts is weird - not sure what is up with that)
What's the cost/downside you're seeing with a sleeping thread on Queue#pop? To prune precisely I think we have a couple of options:
|
@bensheldon mainly complexity, it is complexity we do not want to carry. I wrote a queue with a conditional var here: I am more than happy for this to be lifted into concurrent ruby, it has a few tiny discoursisms (multisite support and logging patterns) but is safe. For us this is perfect, I have not benched it against the current implementation but for our usage we always tend to make DB calls so we are not optimising for microsecond execution times shortest would be usually 10s of milliseconds. |
FWIW I also recall writing one in https://github.com/ruby/timeout/blob/607d8c6fbe4d86db1cf22846e89198b47cec7161/lib/timeout.rb#L105-L109 |
@eregon thanks for the tip, I ended up following up with a hybrid approach https://github.com/discourse/discourse/pull/30392/files There is so much detail in such a small amount of code. being able to efficiently scale up the queue is very tough, coordinating work between all the critical sections is tough. I am not even sure if this is my last PR refining this ... Would love it if you can have a look and let me know if this is something we should port to concurrent, having a building block like this is super important, I want it to work for everyone |
Previous version was prone to the bug: ruby-concurrency/concurrent-ruby#1075 This is particularly bad cause we could have a DB connection attached to the thread and we never clear it up, so after N hours this could start exhibiting weird connection issues.
Previous version was prone to the bug: ruby-concurrency/concurrent-ruby#1075 This is particularly bad cause we could have a DB connection attached to the thread and we never clear it up, so after N hours this could start exhibiting weird connection issues.
I think having the improvement to automatically spin down idle threads in CachedThreadPool would make a lot of sense. It seems the Java version does that:
So it would be good for consistency too. |
Hey folks, I was pointed this way after opening a PR to fix a similar issue with
Context: |
TIL about ...but also presents the challenge that it becomes simple (imo) to implement spinning down idle threads in Ruby 3.2+... and somewhat complex to do so in older versions of Ruby (assuming that a timeoutable-queue-pop is the strategy). I sorta see two paths, and I'd love feedback about which to pick:
|
There is a 100% working implementation using https://github.com/discourse/discourse/blob/main/lib/scheduler/thread_pool.rb No background thread needed, Queue timeout is awesome, but this achieves the exact same goal in a backwards compatible way. The challenge here imo is not the implementation, it is more the architecture of Concurrent rb. Given its Java roots there are lots of abstractions at play and conditional Java code baked in. It makes it very complicated to port in a solution like this despite it being pretty much ready. |
In the Ruby implementation:
CachedThreadPool only spins down threads when you queue work, so if you are done queuing work you need to remember to wait for it to be done and then issue a #prune_pool call
This is technically very tricky cause you need to carry an extra thread for that. The Ruby design should change so threads just wait idle_time for new work and spin down if no new work arrives.
The text was updated successfully, but these errors were encountered: