Reputation: 11
I'm working on a Spring Boot project that includes 2 maven dependencies, those dependencies both use org.springframework.web.client.RestTemplate
so when in my project I do:
@Autowired
AClassUsingRestTemplate object;
it triggers:
No qualifying bean of type 'org.springframework.web.client.RestTemplate' available: expected single matching bean but found 2: externalDependencyOneRestTemplate,externalDependencyTwoRestTemplate
I have the control of only one of those dependencies, where I've defined:
@Bean(name = "externalDependencyOneRestTemplate")
public RestTemplate buildExternalDependencyOneRestTemplate() {
final HttpComponentsClientHttpRequestFactory clientHttpRequestFactory =
new HttpComponentsClientHttpRequestFactory(HttpClientBuilder.create().build());
final RestTemplate restTemplate = new RestTemplate(clientHttpRequestFactory);
restTemplate.setRequestFactory(new BufferingClientHttpRequestFactory(restTemplate.getRequestFactory()));
return restTemplate;
}
what can I do to fix it?
Do I have to tell ClassUsingRestTemplate
to use a specifi RestTemplate
implementations? If yes, how to do that?
Thanks
Upvotes: 0
Views: 572
Reputation: 77177
In addition to the @Qualifier
approach mentioned by Andreas, there are two marginally better options with Boot:
If your class is Spring-aware, inject RestTemplateBuilder
instead of a RestTemplate
, and use that for your customization. This allows for application-level configuration (e.g., adding authentication and tracing interceptors), and then further configuration on the specific service level (converters, failure handlers).
Use @Bean
to configure your AClassUsingRestTemplate
, passing a RestTemplate
to its constructor. (Constructor injection is recommended over field injection.) In @Bean
, you can do whatever custom setup you want.
Upvotes: 0
Reputation: 782
Spring has found 2 types of beans it can inject in this Autowired member: "externalDependencyOneRestTemplate" or "externalDependencyTwoRestTemplate".
Spring cannot choose because it doesn't read your mind. You must help Spring by specifying which bean you want by using the Qualifier annotation:
@Autowired
@Qualifier("nameOfMyBeanHere")
AClassUsingRestTemplate object;
Additionally, it doesn't look like your RestTemplate implementation does anything special, i would suggest enabling Spring Autoconfiguration (which automatically creates a RestTemplate bean) and injecting it instead of creating your own.
Upvotes: 0
Reputation: 159086
Specify which one you want using @Qualifier
:
@Autowired
@Qualifier("externalDependencyOneRestTemplate")
RestTemplate restTemplate;
If you cannot modify the code depending on the RestTemplate
, you can specify which one is the default, i.e. which one to use if @Qualifier
is not specified:
@Primary
@Bean(name = "externalDependencyOneRestTemplate")
public RestTemplate buildExternalDependencyOneRestTemplate() {
...
}
Upvotes: 1