简体   繁体   English

Spring Webflux - 如何从 Mono/Flux 中多次检索值,而无需多次调用以获取这些 Mono/Flux

[英]Spring Webflux - how to retrieve value from Mono/Flux multiple times without making multiple calls to get those Mono/Flux

I'm using Spring Webflux & reactor, Java 11, Spring boot 2.4.5, Spring 5.3.6 versions for this reactive application. I'm using Spring Webflux & reactor, Java 11, Spring boot 2.4.5, Spring 5.3.6 versions for this reactive application.
Use case:用例:
I need to make a call to API and get data from it.我需要调用 API 并从中获取数据。 From this data I take uniqueId and then call bunch of API's to get other data, and then finally combine all this data to new Object and return.从这些数据中我获取 uniqueId 然后调用一堆 API 来获取其他数据,然后最后将所有这些数据组合到新的 Object 并返回。
Example code:示例代码:

Mono<Response> 1stAPIResponse = 1stAPI.callMethod(eventId); // response object has ProductId, and other details.
Mono<List<String>> productIds = 1stAPIResponse.map(Response::ProductId).collect(Collectors.toList());

Mono<2ndAPIResponse> 2ndAPIResponse = productIds.flatMap(ids -> 2ndAPI.callMethod(ids));
Mono<3rdAPIResponse> 3rdAPIResponse = productIds.flatMap(ids -> 3rdAPI.callMethod(ids));
...

1stAPIResponse.foreach(response -> {
    FinalResponse.builder()
    .productId(response.productId)
    .val1(2ndAPIResponse.get(response.productId))
    .val3(3ndAPIResponse.get(response.productId))
    . ...
    .build()});

Here the problem is, when ids are passed to 2ndAPI, 3rdAPI,... method, it makes call to 1stAPI and get the data each time.这里的问题是,当 ids 被传递给 2ndAPI, 3rdAPI,... 方法时,它每次都会调用 1stAPI 并获取数据。 And finally when creating object it makes another call to 1st API.最后,在创建 object 时,它再次调用第一个 API。 In this example it makes total of 3 calls.在此示例中,它总共进行了 3 次调用。

How can I avoid similar multiple calls from occurring?如何避免发生类似的多次调用?

One way to avoid this is, I can make 1stAPI call blocking but is it correct?避免这种情况的一种方法是,我可以进行 1stAPI 调用阻塞,但它正确吗? doesn't it defeat non-blocking style of coding?它不会打败非阻塞式编码吗?
Ex: Response 1stAPIResponse = 1stAPI.callMethod(eventId).toFuture().get();例如: Response 1stAPIResponse = 1stAPI.callMethod(eventId).toFuture().get();

How can I write a correct reactive program (without blocking) but still make only one call to 1stAPI?如何编写正确的反应程序(不阻塞)但仍然只调用 1stAPI?

Let me know for any questions.让我知道任何问题。

So, you need to refactor your code in more reactive style and use zip operator for parallel calls:因此,您需要以更具反应性的方式重构代码并使用 zip 运算符进行并行调用:

1stAPI.callMethod(eventId)
    .flatmap(response -> // collect your id to list (ids);
     return 2ndAPI.callMethod(ids).zipWith(3ndAPI.callMethod(ids))
         .flatmap(tuple2 ->   FinalResponse.builder() // tuple contains result of 2ndAPI and 3ndAPI
                                  .productId(response.productId)
                                  .val1(2ndAPIResponse.get(response.productId))
                                  .val3(3ndAPIResponse.get(response.productId)))
                                  ... 
     )

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM