I'm trying to retrieve data from a REST service using Spring's WebClient and trying to throw the 4XX and 5XX in a Error
instead of instead of a RuntimeException
.
return webclient.
.get()
.uri(myURI)
.accept(MediaType.APPLICATION_JSON)
.retrieve()
.onStatus(HttpStatus::isError, handleError()
.bodyToMono(String.class)
.block();
private static Function<ClientResponse, Mono<? extends Throwable>> handleError() {
return response -> response.bodyToMono(String.class).map(CustomError::new);
}
I'm trying to get this Error
in a test but received a ReactiveException
instead.
org.opentest4j.AssertionFailedError: Unexpected exception type thrown,
Expected :class com.example.CustomError
Actual :class reactor.core.Exceptions$ReactiveException
When I switch the extesion of CustomError
from Error
to RuntimeException
the test pass.
Since the onStatus expcept a Function<ClientResponse, Mono<? extends Throwable>>
I expected to be able to throw an Error in this call.
I'm working on a test library and a initial request is strictly necessary and without a successfully request the test must fail. A Error
will be prevent anyone to catch any problem related with the REST request in their own tests.
You might want to try to return a
Mono.error(new CustomError(response));
in your handleError()
method.
This way you've let the reactive pipeline know an error has occured and what to throw afterwards. Right now you just map to an Error object, which is not handled the same way as RuntimeExceptions.
I would also say that it is probably better to stick to Exceptions
instead of Errors
. Errors tend to be unrecoverable situations for the program to run (OutOfMemoryError
for example), whereas Exceptions are just exceptional cases that could be reacted to potentially (retrying for a 503 status code, or reauthenticating when you receive a 401 status code back).
Example implementation
public Mono<? extends Throwable> handleError(ClientResponse clientResponse) {
String message = String.format("Service error: %s",
clientResponse.statusCode().getReasonPhrase());
return Mono.error(new CustomError(message));
}
This is also a good answer: Correct way of throwing exceptions with Reactor