Let's suppose I have 3 feign client A, B and C with their own request interceptor A_int, B_int and C_int. Now I want to inject dependency of spring class using @autowire for each of the interceptors. For this I have to put @component annotation in each of them, by doing so I am letting all clients to share the all the 3 interceptors because of this FeignClientFactoryBean#configureFeign
In short, I want to preserve the 1-1 mapping for feign client and interceptor by letting spring autowire other beans. Is there is any way we can do it? (or else I am happy to contribute to build feature around it 😄)
I am using feign client: v9.7.0 and open feign with feign starter version: Edgware.SR1
Reference: https://github.com/spring-cloud/spring-cloud-netflix/issues/2746
Comment From: OlgaMaciaszek
Hello, @poke19962008 this is configured per FeignContext (i.e. Feign client). You need to pass your configuration classes via @FeignClient annotation to have them configured per-client, please see the docs. Does this solve your issue? If not, please provide a minimal, complete, verifiable example that reproduces the issue. Also, please upgrade from Edgware. The only supported versions at this time are Hoxton (till the end of August) and Ilford.
Comment From: poke19962008
I see, passing configuration via @FeignClient will let 1-1 mapping, but is it possible to have 1-N mapping?
for example
// my client A
@FeignClient
public interface ClientA {}
@Component
public class InterceptorA1 extends RequestInterceptor {
@Autowired
private SomeService someService;
// some bussiness logic
}
@Component
public class InterceptorA2 extends RequestInterceptor {
@Autowired
private SomeService someService;
// some bussiness logic
}
// my client B
@FeignClient
public interface ClientB {}
@Component
public class InterceptorB1 extends RequestInterceptor { // similar to above interceptor but defferent logic
}
@Component
public class InterceptorB2 extends RequestInterceptor { // similar to above interceptor but defferent logic
}
Here in the above example ClientA should be intercepted with InterceptorA1 and InterceptorA2 only. Whereas for ClientB it should be InterceptorB1 and InterceptorB2.
If I remove @Component and follow this doc then it works but I loose all the @Autowired variables resulting in NPE
Comment From: OlgaMaciaszek
Instead of using @Component, try instantiating them with @Bean in the custom configurations.
Comment From: cbezmen
Olga is right. You can change you code like this. You can add your custom configuration to FeignClient annotation like below.
// my client A
@FeignClient(configuration = {InterceptorA1Configuration.class})
public interface ClientA {}
public class InterceptorA1Configuration {
@Autowired
private SomeService someService;
@Bean
public RequestInterceptor internalRequestInterceptor() {
return template -> {
// your business logic
}
}
}
Comment From: poke19962008
i see that's helpful, one thing is it possible to define multiple beans of RequestInterceptor here?
Comment From: cbezmen
Yes you can define multiple beans. They will call one by one in written order.
interceptorA is called before interceptorB.
@Bean
public RequestInterceptor interceptorA() {
return template -> {
// your business logic
}
}
@Bean
public RequestInterceptor interceptorB() {
return template -> {
// your business logic
}
}
Comment From: poke19962008
yeah! verified that works. thanks @cbezmen and @OlgaMaciaszek.