这是我参与8月更文挑战的第10天,活动详情查看:8月更文挑战
Spring WebFlux
提供了注解式
和函数式
的使用方式。注解式
类似于Spring MVC
使用注解开发接口,函数式
使用RouterFunction (路由函数)
和HandlerFunction (处理函数)
开发接口。本文演示注解式
的开发方式。
示例
-
新建项目
-
添加依赖
r2dbc-mysql
是响应式的MySQL连接驱动
,Spring Data R2DBC
需要r2dbc-mysql
配合工作。引入spring-boot-starter-validation
依赖主要是为了像在Spring MVC
一样使用注解进行参数效验。
<!-- 响应式的MySQL驱动-->
<dependency>
<groupId>dev.miku</groupId>
<artifactId>r2dbc-mysql</artifactId>
</dependency>
<!-- Spring参数效验-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-validation</artifactId>
</dependency>
- 编写yml配置文件
Spring Data R2DBC
和Spring Data JPA
一样支持Repository
模式。需要注意的是Spring Data R2DBC
的url使用r2dbc
开头而不是jdbc
server:
port: 8099
spring:
data:
r2dbc:
repositories:
enabled: true # 开启Repository模式
r2dbc:
url: r2dbc:mysql://**********:****/user?useUnicode=true&characterEncoding=UTF-8&useSSL=false
username: ****
password: ****
pool:
enabled: true
max-size: 10
initial-size: 10
validation-query: select 1
- 编写创建实体类
Spring WebFlux
支持使用spring validation
进行参数效验。如实体类中的name字段加上了不能为空的效验注解
@Data
@Table(value = "user")
public class User {
@Id
private Integer id;
// NotBlank:效验注解
@NotBlank(message = "name为空")
private String name;
// Java 8 新时间类型
private LocalDate birthday;
private String sex;
}
时间类型不能使用
Date
,不然会出现Cannot encode value of type 'class java.util.Date
异常
- 创建实体类的
Repository
创建接口,继承R2dbcRepository
接口。R2dbcRepository
接口提供了响应式的增删改查方法类似于JPA中的JpaRepository
接口。
public interface UserRepository extends R2dbcRepository<User, Integer> {
}
R2dbcRepository
提供了增删改查、分页查询、命名查询、jpql等功能,继承图如下所示:
- 编写Controller
创建Controller编写增删改查接口,这里功能比较简单就不写service了。
Spring WebFlux
标识请求接口的注解有@RequestMapping
、@GetMapping
、@PostMapping
、@PutMapping
、@DeleteMapping
、@PatchMapping
。同时支持如下注解功能同Spring MVC
@PathVariable
@MatrixVariable
@RequestParam
@RequestHeader
@CookieValue
@RequestBody
@RequestPart
@ModelAttribute
@SessionAttribute
@RequestAttribute
@RestController
public class UserController {
@Resource
private UserRepository userRepository;
// 使用@Validated注解激活参数效验
@PostMapping("users")
public Mono<Integer> createUser(@RequestBody @Validated User user){
return userRepository.save(user).map(User::getId);
}
@GetMapping("users")
public Flux<User> getUsers(){
return userRepository.findAll();
}
@GetMapping("users/{id}")
public Mono<User> getUserById(@PathVariable("id") Integer id){
return userRepository.findById(id);
}
@PutMapping("users")
public Mono<String> updateUser(@RequestBody User user){
userRepository.save(user);
return Mono.just("修改成功");
}
@DeleteMapping("users/{id}")
public Mono<String> delUser(@PathVariable("id") Integer id){
userRepository.deleteById(id);
return Mono.just("删除成功");
}
}
结果
- 新增User
新增不传name字段时,效验未通过
-
查询所有User
-
根据id查询User
-
修改User
-
删除User