Reputation: 1422
I'm using ReactiveFeignClient from Playtika I need to use dynamic URL especially for the host part because I want to use the same interface for several services that have the same request and response formats, but different host. The URLs on each service can have different host name and prefix, but all have the same suffix. For example:
Actually I don't know whether it has the same behavior as non-reactive feign client. I follow the suggestion on How can I change the feign URL during the runtime?.
Here's the client interface.
@ReactiveFeignClient(
name = "dummy",
configuration = TransactionClient.Configuration.class
)
public interface TransactionClient {
// @PostMapping("/purchase") // Using @PostMapping and @RequestLine both don't work
@RequestLine("POST /purchase")
Mono<PurchaseResponseDto> doPurchase(
URI baseUrl,
@Valid @RequestBody PurchaseRequestDto requestDTO
);
@RequiredArgsConstructor
class Configuration {
@Bean
public ReactiveStatusHandler reactiveStatusHandler() {
return new CustomStatusHandler();
}
}
}
And here's the auto configuration
@Configuration
public class TransactionClientServiceAutoConfiguration {
@Bean
public Contract useFeignAnnotations() {
return new Contract.Default();
}
@Bean
@LoadBalanced
public TransactionClient botRemoteClient() {
return Feign.builder().target(Target.EmptyTarget.create(TransactionClient.class));
}
}
However, I got error indicating that no service with name dummy. It's just a dummy name indeed, because the name parameter is required for @ReactiveFeignClient annotation and I want to use the interface for multiple services.
How to make dynamic url possible for @ReactiveFeignClient
Upvotes: 2
Views: 4135
Reputation: 530
Workaround with Java21 using ReactiveHttpRequestInterceptor
and @RequestHeader
:
@ReactiveFeignClient(name = "ReactiveDynamicUrlApi", url = BASE_URL, path = "v1/api/product", configuration = ReactiveDynamicUrlApi.RequestInterceptor.class)
interface ReactiveDynamicUrlApi {
String BASE_URL = "base-url";
@PostMapping(path = "{id}", headers = "Content-Type=application/json")
Mono<String> post(@RequestHeader(BASE_URL) String baseUrl, @PathVariable String id, @RequestHeader String token, @RequestBody Map requestBody);
class RequestInterceptor implements ReactiveHttpRequestInterceptor {
@Override
public Mono<ReactiveHttpRequest> apply(final ReactiveHttpRequest request) {
var uri = URI.create(request.headers().get(BASE_URL).getFirst() + request.uri().getPath());
request.headers().remove(BASE_URL);
return Mono.just(new ReactiveHttpRequest(request, uri));
}
}
}
Upvotes: 0
Reputation: 11
From reactive feign github I found this snippet:
IcecreamServiceApi client =
WebReactiveFeign //WebClient based reactive feign
.<IcecreamServiceApi>builder()
.target(IcecreamServiceApi.class, "http://www.myUrl.com")
You can change the url by creating a new instance of the client. Found no other way. Also, I added both @PostMapping and @RequestLine("POST") to the feign interface since I couldn't get the contracts option to work. Sharing this for posterity or until a better version comes along.
Upvotes: 1