Spring Boot 中的响应式编程和 WebFlux 入门

Spring 5.0 中发布了重量级组件 Webflux,拉起了响应式编程的规模使用序幕。

WebFlux 使用的场景是异步非阻塞的,使用 Webflux 作为系统解决方案,在大多数场景下可以提高系统吞吐量。Spring Boot 2.0 是基于 Spring5 构建而成,因此 Spring Boot 2.X 将自动继承了 Webflux 组件,本篇给大家介绍如何在 Spring Boot 中使用 Webflux 。

为了方便大家理解,我们先来了解几个概念。

响应式编程

在计算机中,响应式编程或反应式编程(英语:Reactive programming)是一种面向数据流和变化传播的编程范式。这意味着可以在编程语言中很方便地表达静态或动态的数据流,而相关的计算模型会自动将变化的值通过数据流进行传播。

例如,在命令式编程环境中,a=b+c 表示将表达式的结果赋给 a,而之后改变 b 或 c 的值不会影响 a 。但在响应式编程中,a 的值会随着 b 或 c 的更新而更新。

响应式编程是基于异步和事件驱动的非阻塞程序,只需要在程序内启动少量线程扩展,而不是水平通过集群扩展。

用大白话讲,我们以前编写的大部分都是阻塞类的程序,当一个请求过来时任务会被阻塞,直到这个任务完成后再返回给前端;响应式编程接到请求后只是提交了一个请求给后端,后端会再安排另外的线程去执行任务,当任务执行完成后再异步通知到前端。

Reactor

Java 领域的响应式编程库中,最有名的算是 Reactor 了。Reactor 也是 Spring 5 中反应式编程的基础,Webflux 依赖 Reactor 而构建。

Reactor 是一个基于 JVM 之上的异步应用基础库。为 Java 、Groovy 和其他 JVM 语言提供了构建基于事件和数据驱动应用的抽象库。Reactor 性能相当高,在最新的硬件平台上,使用无堵塞分发器每秒钟可处理 1500 万事件。

简单说,Reactor 是一个轻量级 JVM 基础库,帮助你的服务或应用高效,异步地传递消息。Reactor 中有两个非常重要的概念 Flux 和 Mono 。

Flux 和 Mono

Flux 和 Mono 是 Reactor 中的两个基本概念。Flux 表示的是包含 0 到 N 个元素的异步序列。在该序列中可以包含三种不同类型的消息通知:正常的包含元素的消息、序列结束的消息和序列出错的消息。当消息通知产生时,订阅者中对应的方法 onNext(), onComplete()和 onError()会被调用。

Mono 表示的是包含 0 或者 1 个元素的异步序列。该序列中同样可以包含与 Flux 相同的三种类型的消息通知。Flux 和 Mono 之间可以进行转换。对一个 Flux 序列进行计数操作,得到的结果是一个 Mono

WebFlux 是什么?

WebFlux 模块的名称是 spring-webflux,名称中的 Flux 来源于 Reactor 中的类 Flux。Spring webflux 有一个全新的非堵塞的函数式 Reactive Web 框架,可以用来构建异步的、非堵塞的、事件驱动的服务,在伸缩性方面表现非常好。

非阻塞的关键预期好处是能够以小的固定数量的线程和较少的内存进行扩展。在服务器端 WebFlux 支持2种不同的编程模型:

  • 基于注解的 @Controller 和其他注解也支持 Spring MVC
  • Functional 、Java 8 lambda 风格的路由和处理

如图所示,WebFlux 模块从上到下依次是 Router Functions、WebFlux、Reactive Streams 三个新组件。

  • Router Functions
    对标准的 @Controller,@RequestMapping 等的 Spring MVC 注解,提供一套 函数式风格的 API,用于创建 Router、Handler 和Filter。
  • WebFlux
    核心组件,协调上下游各个组件提供 响应式编程 支持。
  • Reactive Streams
    一种支持 背压 (Backpressure) 的 异步数据流处理标准,主流实现有 RxJava 和 Reactor,Spring WebFlux 集成的是 Reactor。

默认情况下,Spring Boot 2 使用 Netty WebFlux,因为 Netty 在异步非阻塞空间中被广泛使用,异步非阻塞连接可以节省更多的资源,提供更高的响应度。通过比较 Servlet 3.1 非阻塞 I / O 没有太多的使用,因为使用它的成本比较高,Spring WebFlux 打开了一条实用的通路。

值得注意的是:支持 reactive 编程的数据库只有 MongoDB, redis, Cassandra, Couchbase

Spring Webflux

Spring Boot 2.0 包括一个新的 spring-webflux 模块。该模块包含对响应式 HTTP 和 WebSocket 客户端的支持,以及对 REST,HTML 和 WebSocket 交互等程序的支持。一般来说,Spring MVC 用于同步处理,Spring Webflux 用于异步处理。

Spring Boot Webflux 有两种编程模型实现,一种类似 Spring MVC 注解方式,另一种是基于 Reactor 的响应式方式。

快速上手

添加 webflux 依赖

<dependency>    <groupId>org.springframework.boot</groupId>    <artifactId>spring-boot-starter-webflux</artifactId></dependency>

通过 IEDA 的依赖关系图我们可以返现spring-boot-starter-webflux依赖于spring-webflux、Reactor 和 Netty 相关依赖包。

创建 Controller

@RestControllerpublic class HelloController {    @GetMapping("/hello")    public Mono<String> hello() {        return Mono.just("Welcome to reactive world ~");    }}

通过上面的示例可以发现,开发模式和之前 Spring Mvc 的模式差别不是很大,只是在方法的返回值上有所区别。

  • just() 方法可以指定序列中包含的全部元素。
  • 响应式编程的返回值必须是 Flux 或者 Mono ,两者之间可以相互转换。

测试类

@RunWith(SpringRunner.class)@WebFluxTest(controllers = HelloController.class)public class HelloTests {    @Autowired    WebTestClient client;    @Test    public void getHello() {        client.get().uri("/hello").exchange().expectStatus().isOk();    }}

运行测试类,测试用例通过表示服务正常。启动项目后,访问地址:http://localhost:8080/hello,页面返回信息:

Welcome to reactive world ~

证明 Webflux 集成成功。

以上便是 Spring Boot 集成 Webflux 最简单的 Demo ,后续我们继续研究 Webflux 的使用。

示例

全网最全的 Spring Boot 学习示例项目,击下方链接即可获取。

https://github.com/ityouknow/spring-boot-examples

Image placeholder
GEEKZHAO
未设置
  82人点赞

没有讨论,发表一下自己的看法吧

推荐文章
Spring WebFlux 的设计及工作原理剖析

前言 Spring5发布有两年了,随Spring5一起发布了一个和SpringWebMvc同级的SpringWebFlux。这是一个支持反应式编程模型的新框架体系。反应式模型区别于传统的MVC最大的不

SpringBoot个人应用开发框架(SpringBoot版本2.1)+IDEA

前言: 此笔记为本人首个SpringBoot项目框架学习实践记录,期间参考了许多大神的笔记和心得。 参考文档如下: 项目git地址: 一、创建SpringBoot工程 1.1创建父POM工程结

再见 Spring Boot 1.X ,Spring Boot 2.X 走向舞台中心

2019年8月6日,Spring官方在其博客宣布,SpringBoot1.x停止维护,SpringBoot1.x生命周期正式结束。其实早在2018年7月30号,Spring官方就已经在博客进行过预告,

SpringBoot 中的 Servlet Web 容器

1.前言 SpringBoot支持一下嵌入式Servlet容器: SpringBoot2.0.3.RELEASE需要Java8或9以及SpringFramework5.0.7.RELEASE或更高版本

Spring-SpringAOP原理,手写Spring事务框架

一、Spring核心知识Spring是一个开源框架,Spring是于2003年兴起的一个轻量级的Java开发框架,由RodJohnson在其著作ExpertOne-On-OneJ2EEDevelopm

如何理解react响应式

如何理解react响应式React中响应式原理1、开发者只需关注状态转移(数据),当状态发生变化,React框架会自动根据新的状态重新构建UI。2、React框架在接收到用户状态改变通知后,会根据当前

前端-响应式布局

1.使用vw,vh,rem@functionvw($px){ @return($px/1920)*100vw; } @functionvh($px){ @return($px/1075)*100vh

SpringBoot 整合 Dubbo

1.整合dubbo 有的人或许会说已经有spring-cloud了,你整合dubbo干什么,其实没啥意图,主要就是想整合一下,毕竟dubbo在国内使用的还是很多的,你会一点点总不至于让你显得那么尴尬。

Stylus系列——webpack-spritesmith配合stylus使用示例

一、前言基于Webpack的CSSSprites实现方案,若是直接在html中调用雪碧图图标已经很方便,但是实际开发过程可能遇到需要在伪元素中使用雪碧图,或者需要hover切换另一个图标,这种情况下就

SpringBoot 集成 JWT 实现 token 验证,token 注销

什么是JWT Jsonwebtoken(JWT),是为了在网络应用环境间传递声明而执行的一种基于JSON的开放标准((RFC7519).定义了一种简洁的,自包含的方法用于通信双方之间以JSON对象的形

springboot 多数据源,最简单的整合方式

简介 相信大家有配置过多数据源,或者即将配置多数据的朋友们,会发现网上大概有以下几种方案: 1.使用AOP切片进行动态数据源切换 2.使用MapperScan的basePackages配置不同的map

你知道如何自动保存 Spring Boot 应用进程号吗

1.前言 欢迎阅读SpringBoot2实战系列文章PID对于系统运维来说并不陌生,但是对于一些开发者特别是新手还是要简单介绍一下的。它是ProcessID的简称,是系统分配给一个进程的唯一标识符,

云端的生存之道,第 1 单元:将 Spring Boot 部署到 Kubernetes

初始化Kubernetes集群 第一步是初始化IBMCloud上的Kubernetes集群。IBMCloud可能需要几分钟时间来启动新的Kubernetes集群;因此,通过先执行初始化操作,可以在后台

云端的生存之道,第 2 单元:将 Spring Boot 应用程序连接到云托管的数据库

前提条件 本系列教程的第1部分,因为本教程直接以第1部分中的课程内容和完成的操作为基础。 一个IBMCloud帐户 云原生数据持久性 IBMCloud提供了许多可持久存储数据的选项。在本教程中,我

Spring Boot自动装配整理

首先写一个我们自己的HelloWorld配置类 1、基于"注解驱动"实现@Enable模块 @ConfigurationpublicclassHelloWorldConfiguration{@Bean

SpringBoot2.0 支持 https 访问

买了dapideng.com,自然要上https。 其实在之前的博客中,也早有提及配置证书的事儿,只不过这次变成了springboot,它内置了tomcat容器,和把项目打包放在tomcat下面不太一

Spring Boot 高效数据聚合之道

项目地址和示例代码:https://github.com/lvyahui8/spring-boot-data-aggregator 背景 接口开发是后端开发中最常见的场景,可能是RESTFul接口,也

Spring boot 如何快速的配置多个 Redis 数据源

Redis简介 redis多数据源主要的运用场景是在需要使用多个redis服务器或者使用多个redis库,本文采用的是fastdep依赖集成框架,快速集成Redis多数据源并集成lettuce连接池,

Spring Boot到底是怎么运行的,你知道吗?

导读SpringBoot方式的项目开发已经逐步成为Java应用开发领域的主流框架,它不仅可以方便地创建生产级的Spring应用程序,还能轻松地通过一些注解配置与目前比较流行的微服务框架SpringCl

Spring Boot 面试,一个问题就干趴下了!

随着SpringBoot使用越来越广泛,SpringBoot已经成为Java程序员面试的知识点,很多同学对SpringBoot理解不是那么深刻,经常就会被几个连环跑给干趴下了!比如下面这一段的Spri

SpringBoot 深度调优,让你的项目飞起来!

项目调优作为一名工程师,项目调优这事,是必须得熟练掌握的事情。在SpringBoot项目中,调优主要通过配置文件和配置JVM的参数的方式进行。一、修改配置文件关于修改配置文件application.p

使用 Docker 部署 Spring Boot 项目

Docker技术发展为微服务落地提供了更加便利的环境,使用Docker部署SpringBoot其实非常简单,这篇文章我们就来简单学习下。首先构建一个简单的SpringBoot项目,然后给项目添加Doc

Spring Boot 中关于自定义异常处理的套路!

在SpringBoot项目中,异常统一处理,可以使用Spring中@ControllerAdvice来统一处理,也可以自己来定义异常处理方案。SpringBoot中,对异常的处理有一些默认的策略,我们

Github 上 Star 最多的 Spring Boot 个人开源学习项目

2016年,在一次技术调研的过程中认识到了SpringBoot,试用之后便一发不可收拾的爱上它。为了防止学习之后忘记,就在网上连载了 SpringBoot系列文章,没想到这一开始便与SpringBoo

SpringBoot整合RabbitMQ

SpringBoot整合RabbitMQSpringBoot框架已经提供了RabbitMQ的使用jar包,开发人员在使用RabbitMQ的时候只需要引用jar包简单的配置一下就可以使用RabbitMQ