Spring 5 Reactive WebClient无法反序列化参数化类型问题咨询
我之前刚好解决过这个问题,WebClient处理Spring Data REST返回的HAL+JSON分页资源确实和RestTemplate有一点点不同,但核心思路还是用ParameterizedTypeReference来指定泛型类型。下面是一步步的实现方案:
1. 确保依赖到位
首先得保证项目里已经引入了Spring HATEOAS和WebFlux的相关依赖,Spring Boot的话直接用starter就好:
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-webflux</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-hateoas</artifactId> </dependency>
2. 正确创建WebClient(自动配置优先)
如果是Spring Boot项目,直接用自动配置的WebClientBuilder来创建WebClient就好,它会自动注册处理HAL+JSON的Jackson2HalModule,不用手动配置codec:
@Autowired private WebClient webClient; // 或者通过@Bean自定义 @Bean public WebClient webClient(WebClientBuilder builder) { return builder.baseUrl("http://your-api-base-url").build(); }
3. 使用ParameterizedTypeReference实现反序列化
和RestTemplate类似,我们需要用ParameterizedTypeReference来明确PagedResources<Foo>的泛型类型,然后传给WebClient的bodyToMono()方法:
// 定义参数化类型引用 ParameterizedTypeReference<PagedResources<Foo>> pagedFooType = new ParameterizedTypeReference<PagedResources<Foo>>() {}; // 发起请求并反序列化为PagedResources Mono<PagedResources<Foo>> pagedFooMono = webClient.get() .uri("/foos") // 你的分页接口地址 .accept(MediaTypes.HAL_JSON) // 明确指定接受HAL+JSON类型 .retrieve() .bodyToMono(pagedFooType); // 传入类型引用 // 订阅处理结果 pagedFooMono.subscribe(pagedResources -> { // 获取当前页的数据列表 List<Foo> currentPageItems = pagedResources.getContent(); // 获取分页元数据(总元素数、总页数、当前页大小等) PageMetadata metadata = pagedResources.getMetadata(); System.out.printf("当前页元素数:%d,总元素数:%d,总页数:%d%n", metadata.getSize(), metadata.getTotalElements(), metadata.getTotalPages()); // 处理分页链接(比如下一页、上一页) Link nextLink = pagedResources.getLink(IanaLinkRelations.NEXT); if (nextLink != null) { // 这里可以继续发起请求获取下一页数据 System.out.println("下一页链接:" + nextLink.getHref()); } });
4. 注意事项
- 如果是手动配置WebClient的codec,需要确保添加了
Jackson2HalModule,否则会无法正确反序列化HAL格式的分页资源。 PagedResources是Spring HATEOAS提供的类型,它包含了分页元数据和资源链接,比普通的Page对象多了HATEOAS的链接信息。- 分页资源是一个单一的容器对象,所以用
Mono<PagedResources<Foo>>才是正确的选择,不需要用Flux。
内容的提问来源于stack exchange,提问作者aimass
相关产品推荐
相关产品推荐

