如何将Flux<T>包装在ResponseEntity中(ResponseEntity<Flux<T>)

问题描述 投票:0回答:2

首先,我知道还有一些其他问题本质上问同样的事情(How to Wrap Flux in a ResponseEntityHow to mix Flux and ResponseEntity in Spring Webflux controllers),但答案不知何故都结束了最后返回

Mono<ResponseEntity>

ResponseEntity<Mono<T>>

给定

Mono<Customer> getCustomer(Long customerId)
中的
CustomersService
方法,我的控制器代码将如下所示:

@Autowired CustomersService customersService;

public Mono<ResponseEntity<Customer> getCustomer(Long customerId) {
  return customersService
    .getCustomer(customerId)
    .map(ResponseEntity::ok)
    .defaultIfEmpty(ResponseEntity.notFound().build())
}

ResponseEntity<Flux<T>>

现在,如果服务更改为

Flux<Customer> getCustomers(String name)
并且控制器返回类型为
ResponseEntity<Flux<Customer>>
,控制器代码应该是什么样子?

public Flux<ResponseEntity<Customer> getCustomers(String name) {
  return customersService
    .getCustomers(name)
    ...?
}
java spring-boot spring-webflux flux reactor
2个回答
0
投票

它将与您的第一个案例相同。

@Autowired 
CustomersService customersService;

public Flux<ResponseEntity<Customer>> getCustomers(String name) {
    return customersService.getCustomers(name)
            .map(ResponseEntity::ok)
            .defaultIfEmpty(ResponseEntity.noContent().build());
}

0
投票

ℹ️ TL;DR:你必须使用

ResponseEntity<Flux<T>>

为什么是
ResponseEntity
Flux

HTTP 响应由一组标头和一个状态行组成,后跟一个潜在的流式正文。因此,您实际上是预先提供状态代码和 HTTP 标头,并在数据可用时提供数据流。

为什么不是
Flux
ResponseEntity

如果您要使用

Flux<ResponseEntity<T>>
,从概念上讲,您将尝试通过单个请求/响应交互发送多个完整的 HTTP 响应(每个响应都有自己的标头、状态代码和数据)。 HTTP 不支持同一响应中多个独立的标头和状态行集,因此这种方法不能清楚地映射到 HTTP 的工作方式。

如果你很固执,仍然尝试这样做,Spring 无论如何都会抱怨并且不会让你这么做。你会得到这样的异常:

java.lang.IllegalArgumentException: Only a single ResponseEntity supported
    at org.springframework.util.Assert.isTrue(Assert.java:116) ~[...]
    ...

查看文档。他们列出了所有可能性,虽然他们没有禁止

Flux<ResponseEntity<T>>
,但他们没有提及。

© www.soinside.com 2019 - 2024. All rights reserved.