问题描述
我希望对以下声明中的粗体文本进行澄清(我提供了完整的段落,仅用于上下文):
找到此处:https://docs.spring.io/spring/docs/current/spring-framework-reference/web-reactive.html
特别是对Spring MVC应用程序使用WebClient
而不是RestTemplate
有什么好处?使用适当配置的连接和套接字配置,WebClient
与RestTemplate
相比,HttpClient
和PoolingHttpClientConnectionManager
如何实现更高的规模?推荐答案
WebClient
为非阻塞,RestTemplate
为阻塞/同步。如果将非阻塞WebFlux API与阻塞库一起使用,则实质上是将其转换为阻塞API。
认为RestTemplate
实际上是为每个事件创建一个新的线程,而不是WebClient
创建一个任务(就像在队列上一样,这实际上是Reader在幕后为您管理的内容)。如果对于每个非阻塞任务都有一个阻塞调用支持它(就像每个RestTemplate
的情况一样;请注意,委托给ConnectionManager
仍然是进行阻塞调用),您很快就会达到线程饥饿状态。另一方面,任务将由反应性框架排队,并在您有适当的可用资源时执行。
为什么将WebClient与Spring MVC一起使用
WebClient是非阻塞的!您可以使用它的所有Flux
功能(发布订阅、背压等)。这有助于节省资源(即使用更少的线程和更少的内存),并且反应器将允许您最大限度地使用不使用的线程。这里的问题并不是"我为什么要在Spring MVC中使用WebClient",而是"我为什么要在我的应用程序中使用被动/非阻塞"框架。网上有很多这个问题和答案的例子(here's one)。
Mono
和Flux
也可以返回Java 8 CompletableFuture
。
为什么将WebClient与WebFlux一起使用
查看您所在页面的引用referenced in that documentation:
关键是WebClient
使用与Flux
相同的反应式非阻塞类型。这就是为什么集成得如此完美,您就可以获得出色的任务处理功能。例如(我借用了that doc中的一段代码):WebClient client = WebClient.create("http://example.org");
Mono<Void> result = client.post()
.uri("/persons/{id}", id)
.contentType(MediaType.APPLICATION_JSON)
.body(personMono, Person.class)
.retrieve()
.bodyToMono(Void.class);
看到这段代码如何生成Mono
吗?这是一个反应式结构WebFlux
构建在之上,这就是为什么您要在框架中使用它。例如,您实际上可以return that Mono
reactively in a Controller
call:@PostMapping("/person")
Mono<Void> create(@RequestBody Publisher<Person> personStream) {
// ... above code could go here...
return result;
}
这类事情是他们说您应该对WebFlux
库使用WebClient
的关键原因。
这篇关于RestTemplate与WebClient在基于Servlet的Web MVC应用程序中的优势的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!