You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring Boot WebFlux中数组响应转DTO及合并校验逻辑实现方法

Spring WebFlux 移除WebClient调用中间变量方案

完全可以实现两段逻辑合并,不需要单独定义库存响应数组的中间变量,以下是具体实现方式:

方案1:保留原有同步阻塞逻辑,仅移除中间变量

你可以直接在Mono流内用map算子完成库存状态判断,最后block()直接返回布尔值结果,无需定义中间数组变量:

// Call Inventory Service, and place order if product is in stock
boolean allProductsInStock = webClient.get()
        .uri("http://localhost:8092/api/inventory",
                uriBuilder -> uriBuilder.queryParam("skuCode", skuCodes).build())
        .retrieve()
        .bodyToMono(InventoryResponse[].class)
        // 直接在流内完成数组遍历判断
        .map(inventoryResponsArray -> Arrays.stream(inventoryResponsArray)
                .allMatch(InventoryResponse::isInStock))
        .block();

注意:这种写法虽然满足移除中间变量的需求,但在Spring WebFlux响应式链路中调用block()会阻塞事件循环线程,彻底丢失响应式编程的非阻塞性能优势,仅适合临时兼容旧逻辑使用。

方案2:符合WebFlux规范的全响应式写法(推荐)

如果你是基于WebFlux开发响应式微服务,建议把整个方法改造成非阻塞的响应式链路,全程不调用block(),从根源上避免不必要的中间变量和阻塞操作:

// 方法返回Mono,全程非阻塞
public Mono<Void> placeOrder(OrderRequest orderRequest) {
    List<OrderLineItems> orderLineItems = orderRequest.getOrderLineItemsDtoList()
            .stream()
            .map(this::mapToDto)
            .collect(Collectors.toList());

    Order order = new Order();
    order.setOrderNumber(UUID.randomUUID().toString());
    order.setOrderLineItemsList(orderLineItems);

    List<String> skuCodes = order.getOrderLineItemsList()
            .stream()
            .map(orderLineItem -> orderLineItem.getSkuCode())
            .collect(Collectors.toList());

    // 串联整个库存查询、判断、下单流程
    return webClient.get()
            .uri("http://localhost:8092/api/inventory",
                    uriBuilder -> uriBuilder.queryParam("skuCode", skuCodes).build())
            .retrieve()
            .bodyToMono(InventoryResponse[].class)
            .map(inventoryArray -> Arrays.stream(inventoryArray)
                    .allMatch(InventoryResponse::isInStock))
            .flatMap(allProductsInStock -> allProductsInStock ?
                    // 库存充足则执行响应式保存,注意这里需要使用Reactive类型的OrderRepository
                    orderRepository.save(order).then() :
                    // 库存不足抛出异常
                    Mono.error(new IllegalArgumentException("Product is not in stock, please try again later"))
            );
}

注意:该方案要求你的orderRepository是响应式Repository(即继承ReactiveCrudRepository/ReactiveMongoRepository等响应式数据接口),如果还是传统的阻塞式JPA Repository,会在数据库操作环节产生阻塞,同样不符合WebFlux的使用规范。

内容的提问来源于stack exchange,提问作者Jeff Cook

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.30 10:36:25