Skip to content

Avoid using @ConditionalOnClass(Flux.class) and similar conditions #15574

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

Closed
vpavic opened this issue Dec 28, 2018 · 3 comments
Closed

Avoid using @ConditionalOnClass(Flux.class) and similar conditions #15574

vpavic opened this issue Dec 28, 2018 · 3 comments
Labels
status: declined A suggestion or change that we don't feel we should currently apply

Comments

@vpavic
Copy link
Contributor

vpavic commented Dec 28, 2018

The current Spring Boot codebase contains two instances of @ConditionalOnClass(Flux.class):

@Configuration
@ConditionalOnClass(Flux.class)
static class ReactiveHealthIndicatorConfiguration {

@Configuration
@ConditionalOnClass(Flux.class)
@ConditionalOnWebApplication(type = Type.REACTIVE)
public class ReactiveManagementContextAutoConfiguration {

When a Servlet based app depends on a library that transitively pulls in Project Reactor as mandatory dependency, such as Lettuce, the first example will result in ReactiveHealthIndicatorRegistry bean registered, which I believe shouldn't be the case in a Servlet app.

The second example is benign and has no consequences, but arguably having @ConditionalOnClass(Flux.class) there is needless as it will get shadowed by @ConditionalOnWebApplication(type = Type.REACTIVE).

IMO the conditions that test the presence of Project Reactor on classpath should be avoided due to high likeliness of false positives, unless there's really a valid case for those.

@spring-projects-issues spring-projects-issues added the status: waiting-for-triage An issue we've not yet triaged label Dec 28, 2018
@bclozel
Copy link
Member

bclozel commented Dec 28, 2018

Unless I'm missing something, the first instance in ReactiveHealthIndicatorConfiguration is about setting up the reactive infrastructure for any reactive health indicator. I don't know if we can refine the condition here, but in the case of Lettuce, there might be a reactive health indicator to set up for that so we need the infrastructure ready.

Worst case scenario, the application only declares blocking HealthIndicator and those are executed on an elastic scheduler. Is there any other downside that I've missed?

Now about the second case; it's true that this @ConditionalOnClass might have false positives, but I think that having an auto-configuration class without any @CondiontalOnClass is way worse; classpath conditions are cheap and can prevent the class from being loaded if the condition fails. Even with possible false positives, removing that condition will penalize all other cases. The bottom line is: if there's any other safe class that we can use here, less prone to false positives, we should consider it. Do you have any other class in mind?

@bclozel bclozel added status: waiting-for-feedback We need additional information before we can continue for: team-attention An issue we'd like other members of the team to review labels Dec 28, 2018
@vpavic
Copy link
Contributor Author

vpavic commented Jan 3, 2019

For Servlet based app, I don't think the choice of Redis driver should influence whether reactive infrastructure should be configured. This is what happens now - if I use Jedis there's no ReactiveHealthIndicatorRegistry bean registered.

That's why I think that relying on the presence of Project Reactor on classpath isn't the right thing to do here, but rather to react to the fact that some of the Spring Data's components for reactive Redis have been configured.

I don't do much reactive so I don't know what would be the best thing to do here, but since core of Project Reactor is simply a foundation for building reactive apps and can be used in so many different scenarios, I don't think its mere presence on classpath should influence how infrastructure is set up.

@spring-projects-issues spring-projects-issues added status: feedback-provided Feedback has been provided and removed status: waiting-for-feedback We need additional information before we can continue labels Jan 3, 2019
@bclozel bclozel removed the for: team-attention An issue we'd like other members of the team to review label Jan 10, 2019
@bclozel
Copy link
Member

bclozel commented Jan 10, 2019

Indeed, using Jedis doesn't trigger this piece of infrastructure; but I'm not seeing any downside in enabling that actuator part in case reactive bits are present. Even if the health indicators are not exposed through a web interface, they'll still be executed in a more efficient way.

Setting up a condition on Spring Data doesn't really matter here, since the health indicator usually rely on low-level constructs/drivers. As you said, Reactor is a foundation for reactive libraries and it's the best signal we can pick up here IMO.

The team has discussed that point and we feel that attempting to change that might result in blocking reactive infrastructure in some cases, whereas right now worst thing that can happen is wrapping blocking infrastructure with non-blocking calls.

@bclozel bclozel closed this as completed Jan 10, 2019
@bclozel bclozel added status: declined A suggestion or change that we don't feel we should currently apply and removed status: feedback-provided Feedback has been provided status: waiting-for-triage An issue we've not yet triaged labels Jan 10, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
status: declined A suggestion or change that we don't feel we should currently apply
Projects
None yet
Development

No branches or pull requests

3 participants