浅谈Spring 5的响应式编程
这篇使用Spring 5进行响应式编程的入门文章展示了你现在可以使用的一些新的non-blocking, asynchronous。感谢优锐课老师给予的指导!
近年来,由于响应式编程能够以声明性的方式(而不是强制性的)构建应用程序,从而在响应程序和弹性方面具有更强的响应能力,因此在开发人员社区和客户中日益流行。Spring 5将Reactive Systems纳入其核心框架的事实表明,范式已向声明式编程转移。
响应式编程管理数据生产者与需要以非阻塞方式对数据做出反应的使用者之间的异步数据流。因此,响应式编程全部与异步和事件驱动的非阻塞应用程序有关,这些应用程序需要少量线程来扩展。
由于基于共享的可变状态,线程和锁扩展应用程序存在很高的复杂性,因此很难使用基于线程的框架来构建反应性应用程序。
在响应式编程上下文中,“一切都是流,并且当流中有数据时,一切都以非阻塞的方式进行。”
为什么响应式编程
响应式编程的高度抽象性提高了代码的可读性,因此开发人员可以主要关注定义业务逻辑的事件的相互依赖性。
反应模式自然适合高度并发环境中的消息处理,这是企业常见的用例。
具有强制背压的功能,响应式方法最适合控制生产者和消费者之间的流量,这将有助于避免内存不足的问题。
响应式编程可以更有效地管理高度互动和实时的应用程序或任何动作/事件可能触发多个连接子系统的通知的情况。
实现响应式编程的理想用例
- 大量交易处理服务,例如银行业。
- 大型在线购物应用程序(例如Amazon)的通知服务。
- 股票交易同时变化的股票交易业务。
响应式流
“响应流”定义了一个API规范,该规范包含一组最少的接口,这些接口公开了用于定义具有非阻塞背压的异步数据流的操作和实体的方法。
引入反压后,反应流允许订户控制发布者的数据交换速率。
Reactive Streams API作为java.util.concurrent.Flow正式成为Java 9的一部分。
响应式流主要用作互操作性层。
Spring 5响应式编程产品
Spring-Web-Reactive模块和Spring MVC都支持相同的@Controller编程,但是Spring-Web-Reactive另外在Reactive和非阻塞引擎上执行。
Spring-Web-Reactive模块和Spring MVC共享许多常用算法,但是Spring-Web-Reactive模块已经重新定义了许多Spring MVC合约,例如HandlerMapping和HandlerAdapter,以使它们异步和非阻塞并启用 反应性HTTP请求和响应(以RouterFunction和HandlerFunction的形式)。
除了现有的RestTemplate之外,Spring 5中还引入了新的反应式WebClient。
支持响应式编程的HTTP客户端(例如Reactor,Netty,Undertow)已经适应了一组响应式的ClientHttpRequest和ClientHttpResponse抽象,这些抽象将请求和响应主体公开为Flux <DataBuffer>,并且在读取和写入端具有完全的反压支持。
Spring 5 Framework引入了Reactor作为Reactive Streams规范的实现。
Reactor是下一代Reactive库,用于在JVM上构建非阻塞应用程序。
Reactor扩展了基本的Reactive Streams Publisher合同,并定义了Flux和Mono API类型,以分别对0..N和0..1的数据序列提供声明性操作。
Spring Web Reactive利用Servlet 3.1提供的非阻塞I / O并在Servlet 3.1容器上运行。
Spring WebFlux提供了两种编程模型的选择。
- 带注释的控制器:这些与Spring MVC相同,带有一些Spring-Web模块提供的附加注释。Spring MVC和WebFlux控制器都支持Reactive返回类型。此外,WebFlux还支持Reactive @RequestBody参数。
- 函数式编程模型:一个基于lambda的轻量级小型库,它公开实用程序来路由和处理请求。
Spring Web响应式与Spring Web MVC
Spring 5彼此相邻容纳了Spring Web Reactive(在spring-web-reactive模块下)和Spring Web MVC(在spring-webmvc模块下)。
尽管Spring Web Reactive和Spring Web MVC模块都共享许多算法,但是由于Spring Web Reactive能够在Reactive和非阻塞的Reactive Streams HTTP适配器层上运行,因此它们不共享代码。
Spring MVC执行需要Servlet容器,而Spring Web Reactive也可以在非Servlet运行时上运行,例如Netty和Undertow。
如果绝对需要带有Java 8 lambda或Kotlin的轻量级功能性Web框架的无阻塞Web堆栈,则应考虑从Spring MVC应用程序切换到Spring Web Reactive。
响应式编程的基本配置
这是带有5.0.0 M5版本和WebFlux依赖项的pom.xml。
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.0.M5</version>
</parent>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-webflux</artifactId> </dependency>
</dependencies>
传统方法与反应方法
在传统方法中,执行将被阻止,并将一直等到服务执行完成。在下面的代码中,在第一个打印语句之后,程序执行将被阻塞并等待服务执行完成。服务执行完成后,将恢复程序执行并执行第二个打印语句。
@GetMapping("/traditional")
public List < Product > getAllProducts() {
System.out.println("Traditional way started");
List < Product > products = prodService.getProducts("traditional");
System.out.println("Traditional way completed");
return products;
}
在响应式方法中,程序将继续执行,而无需等待服务执行的完成。 在下面的代码中,在第一个打印语句之后,第二个打印语句将以非阻塞方式执行,而无需等待服务执行完成。将使用产品数据填充Flux流。
@GetMapping(value = "/reactive", .TEXT_EVENT_STREAM_VALUE)
public Flux < Product > getAll() {
System.out.println("Reactive way using Flux started");
Flux < Product > fluxProducts = prodService.getProductsStream("Flux");
System.out.println("Reactive way using Flux completed");
return fluxProducts;
}
响应式Web客户端
除了现有的RestTemplate之外,Spring 5还引入了Reactive WebClient。
ClientHttpRequest和ClientHttpResponse抽象将请求和响应主体公开为Flux <DataBuffer>,在读取和写入侧具有完全的反压支持。
来自Spring Core的Encoder和Decoder抽象也用于客户端,用于与类型对象之间的字节通量序列化。
以下是一个Reactive WebClient的示例,该示例调用终结点并接收和处理Reactive Stream Flux对象。
@GetMapping("/accounts/{id}/alerts")
public Flux < Alert > getAccountAlerts(@PathVariable Long id) {
WebClient webClient = new WebClient(new ReactorClientHttpConnector());
return this.repository.getAccount(id).flatMap(account -> webClient.perform(get("/alerts/{key}", account.getKey())).extract(bodyStream(Alert.class)));
}
Spring 5的局限性
- 对响应式应用程序进行故障排除有些困难,并且有可能在解决问题时偶然引入了阻止代码。
- 大多数传统的基于Java的集成库仍处于阻塞状态。
- 除少数NoSQL数据库(例如MongoDB)外,Reactive数据存储区提供有限的选项。
- 仍然不支持Spring Security。
感谢阅读!
另外近期整理了一套完整的java架构思维导图,分享给同样正在认真学习的每位朋友~


浅谈Spring 5的响应式编程的更多相关文章
- Spring 5 响应式编程
要点 Reactor 是一个运行在 Java8 之上的响应式流框架,它提供了一组响应式风格的 API 除了个别 API 上的区别,它的原理跟 RxJava 很相似 它是第四代响应式框架,支持操作融合, ...
- springboot2 webflux 响应式编程学习路径
springboot2 已经发布,其中最亮眼的非webflux响应式编程莫属了!响应式的weblfux可以支持高吞吐量,意味着使用相同的资源可以处理更加多的请求,毫无疑问将会成为未来技术的趋势,是必学 ...
- [转帖]浅谈响应式编程(Reactive Programming)
浅谈响应式编程(Reactive Programming) https://www.jianshu.com/p/1765f658200a 例子写的非常好呢. 0.9312018.02.14 21:22 ...
- (转)Spring Boot 2 (十):Spring Boot 中的响应式编程和 WebFlux 入门
http://www.ityouknow.com/springboot/2019/02/12/spring-boot-webflux.html Spring 5.0 中发布了重量级组件 Webflux ...
- Spring Boot 2 (十):Spring Boot 中的响应式编程和 WebFlux 入门
Spring 5.0 中发布了重量级组件 Webflux,拉起了响应式编程的规模使用序幕. WebFlux 使用的场景是异步非阻塞的,使用 Webflux 作为系统解决方案,在大多数场景下可以提高系统 ...
- Spring Boot (十四): 响应式编程以及 Spring Boot Webflux 快速入门
1. 什么是响应式编程 在计算机中,响应式编程或反应式编程(英语:Reactive programming)是一种面向数据流和变化传播的编程范式.这意味着可以在编程语言中很方便地表达静态或动态的数据流 ...
- 响应式编程基础教程:Spring Boot 与 Lettuce 整合
本文主要介绍响应式编程访问 Redis,以及 Spring Boot 与 Lettuce 的整合使用. Lettuce 是可扩展性线程安全的 Redis 客户端,用于同步.异步和响应式使用.如果多个线 ...
- 什么是响应式编程——响应式Spring的道法术器
响应式编程之道 1.1 什么是响应式编程? 在开始讨论响应式编程(Reactive Programming)之前,先来看一个我们经常使用的一款堪称“响应式典范”的强大的生产力工具——电子表格. 举个简 ...
- Reactive(1) 从响应式编程到"好莱坞"
目录 概念 面向流设计 异步化 响应式宣言 参考文档 概念 Reactive Programming(响应式编程)已经不是一个新东西了. 关于 Reactive 其实是一个泛化的概念,由于很抽象,一些 ...
随机推荐
- word2vec词向量处理中文语料
word2vec介绍 word2vec官网:https://code.google.com/p/word2vec/ word2vec是google的一个开源工具,能够根据输入的词的集合计算出词与词之间 ...
- Activiti工作流数据库表结构
Activiti工作流引擎数据库表结构 数据库表的命名 Acitiviti数据库中表的命名都是以ACT_开头的.第二部分是一个两个字符用例表的标识.此用例大体与服务API是匹配的. ACT_RE_*: ...
- 如何批量删除.svn文件
参考资料:https://www.cnblogs.com/kisf/articles/4760367.html 当项目不需要SVN标志的时候,我们一般怎么办哪??可能很多人设置Windows显示隐藏文 ...
- 吴裕雄 Bootstrap 前端框架开发——Bootstrap 排版:引用(Blockquote)
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title> ...
- TensorFlow基础二(Shape)
首先说明tf中tensor有两种shape,分别为static (inferred) shape和dynamic (true) shape,其中static shape用于构建图,由创建这个tenso ...
- Day11 - J - Brave Game HDU - 1846
十年前读大学的时候,中国每年都要从国外引进一些电影大片,其中有一部电影就叫<勇敢者的游戏>(英文名称:Zathura),一直到现在,我依然对于电影中的部分电脑特技印象深刻.今天,大家选择上 ...
- Ansible ssh-key密钥认证配置
对于被管理服务器做免密码登录设置 1.在管理服务器生成ssh-key密钥 #ssh-keygen //生成秘钥 root@hsz:/etc/ansible# ssh-keygen Generatin ...
- 设计模式课程 设计模式精讲 12-2 适配器模式coding
1 重要 1.1 类适配器和对象适配器最大的区别 2 代码演练 2.1 代码演练1(类适配器模式) 2.2 代码演练2(对象适配模式) 2.3 代码演练3(具体应用场景) 1 重要 1.1 类适配器和 ...
- java Vector的特点与使用
Vector Vector的数据结构 基于数组,大小可变(数组扩容). Vector与ArrayList的比较 我看了下源码,最大区别就是Vector的方法加了synchronized,是线程安全的 ...
- kd-tree理论以及在PCL 中的代码的实现(转载)
该文转自:https://www.cnblogs.com/li-yao7758258/p/6437440.html kd-tree理论以及在PCL 中的代码的实现 (小技巧记录:博客园编辑的网页界 ...