英文:
Spring WebClient nested Mono according to status codes
问题
使用WebClient,我想根据HTTP状态代码分别处理ClientResponse。在下面,您可以看到在doOnSuccess的顶部使用了两个新的subscribe()方法。我如何将这些嵌套的Monos传递到WebClient的Mono链中?也就是说,如何消除内部的Monos。
webClient.post()
.uri(soapServiceUrl)
.contentType(MediaType.TEXT_XML)
//.body(Mono.just(req), String.class )
.body(Mono.just(getCountryRequest), GetCountryRequest.class)
.exchange()
.filter((ClientResponse response) -> { return true; })
.doOnSuccess((ClientResponse response) -> {
// 嵌套的Mono 1
if (response.statusCode().is5xxServerError()) {
response.toEntity(String.class).doOnSuccess(
error -> {
System.out.println("error : " + error);
}).subscribe();
}
// 嵌套的Mono 2
if (response.statusCode().is2xxSuccessful()) {
response.toEntity(GetCountryResponse.class).doOnSuccess(
getCountryResponse -> {
System.out.println("success : " + getCountryResponse.getBody().getCountry().getCapital());
}).subscribe();
}
})
.doOnError((Throwable error) -> {
System.out.println("getCountryResponse.error : " + error);
})
.subscribe();
英文:
Using WebClient I want to handle ClientResponse separately according to HTTP status codes. Below you see two new subscribe() method used in top doOnSuccess. How can I carry those nested Monos to WebClient's Mono chain? That is to say, how to eliminate inner monos.
webClient.post()
.uri( soapServiceUrl )
.contentType(MediaType.TEXT_XML)
//.body(Mono.just(req), String.class )
.body( Mono.just(getCountryRequest) , GetCountryRequest.class )
.exchange()
.filter( (ClientResponse response) -> { return true; } )
.doOnSuccess( (ClientResponse response) -> {
//nested mono 1
if( response.statusCode().is5xxServerError() ){
response.toEntity(String.class).doOnSuccess(
error -> {
System.out.println("error : "+ error);
}).subscribe();
}
//nested mono 2
if( response.statusCode().is2xxSuccessful() ){
response.toEntity(GetCountryResponse.class).doOnSuccess(
getCountryResponse -> {
System.out.println("success : "+ getCountryResponse.getBody().getCountry().getCapital());
}).subscribe();
}
})
.doOnError( (Throwable error) -> {
System.out.println( "getCountryResponse.error : "+ error );
})
.subscribe();
答案1
得分: 1
WebClient的“retrieve()”方法有更好的处理错误代码的方式。
我会这样做:
```java
webClient.post()
.uri(soapServiceUrl)
.contentType(MediaType.TEXT_XML)
//.body(Mono.just(req), String.class )
.body(Mono.just(getCountryRequest), GetCountryRequest.class)
.retrieve()
.onStatus(
HttpStatus::isError,
clientResponse -> clientResponse
// 将错误响应体作为字符串获取
.bodyToMono(String.class)
// 将errorResponseBody映射为新的错误信号
.flatMap(
errorResponseBody -> Mono.error(
new ResponseStatusException(
clientResponse.statusCode(),
errorResponseBody))))
// 将成功响应获取为Mono<GetCountryResponse>
.bodyToMono(GetCountryResponse.class)
.doOnSuccess(response ->
System.out.println("success : " +
response.getBody().getCountry().getCapital()))
// 现在将会记录响应错误
.doOnError(ResponseStatusException.class, error -> {
System.out.println("getCountryResponse.error : " + error);
})
.subscribe();
<details>
<summary>英文:</summary>
The Webclient's ``retrieve()`` method has better ways to handle error codes.
I would do it like this:
webClient.post()
.uri( soapServiceUrl )
.contentType(MediaType.TEXT_XML)
//.body(Mono.just(req), String.class )
.body( Mono.just(getCountryRequest) , GetCountryRequest.class )
.retrieve()
.onStatus(
HttpStatus::isError,
clientResponse ->
clientResponse
//get the error response body as a string
.bodyToMono(String.class)
//flatmap the errorResponseBody into a new error signal
.flatMap(
errorResponseBody ->
Mono.error(
new ResponseStatusException(
clientResponse.statusCode(),
errorResponseBody))))
//get success response as Mono<GetCountryResponse>
.bodyToMono(GetCountryResponse.class)
.doOnSuccess( (GetCountryResponse response) ->
System.out.println("success : " +
response.getBody().getCountry().getCapital()))
//Response errors will now be logged below
.doOnError(ResponseStatusException.class, error -> {
System.out.println( "getCountryResponse.error : "+ error );
})
.subscribe();
</details>
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论