A scheduler is the abstraction Reactor, our reactive library runs code on. Ideally we would only run non-blocking code on a parallel scheduler. In practice we also run blocking code on an elastic scheduler. Elastic schedulers are unbounded so we can end up with a very large number of threads thus defeating the benefits of reactive code.
For this reason, project reactor deprecates elastic in favor of bounded elastic.
This switch was attempted before but resulted in dead locks.
Such deadlocks can be avoided by:
- Avoiding wrapping .blocks calls in an elastic thread. This means essentially improving the quality of our reactive pipelines and not blocking them in the middle. - Avoid calls to subscibeOn before blocking. Instead use the blocked threads (that is anyway blocked) for the ongoing computation.
- In last result use a SEDA like approach:
- Introduce a new instance of boundedElastic dedicated to wrap our calls to .block where we can't avoid it. - Use core boundedElastic only when no reactor .block call is involved to prevent starvation
Alternatives would be to increase to an absurd amount the size of boundedElastic essentially mimicking the behavior of elastic.
We have 161 calls to .elastic().
Acceptance criteria: no performance degradation. Recent performance improvements were furthermore delivered in recent reactor releases.
This would eventually be needed to upgrade to reactor 3.5.0.