结果校验方法_SpringBoot参数校验

参考博客:

SpringBoot 参数校验的方法​www.cnblogs.com

实现整理如下:

一、为什么要进行参数校验?

虽然在前端做校验,可以通过前端禁止输入的方法来使参数合法。但应该考虑到可以跳过前端,直接像后端发送请求,如果后端未做参数校验的话,会使未经校验的参数经过service层来到dao层直到数据库,造成十分严重的后果。最好的结果是查不出数据,严重一点就是报错,如果这些没有被校验的参数中包含了恶意代码,那就可能导致更严重的后果。

前端做参数校验是为了用户体验,后端做参数校验是为了安全

二、SpringBoot的参数校验

controller层参数校验流程如下:

9183ba13a0236e1d5c374e9805b45570.png

SpringBoot的参数校验可分为两类:单个参数校验、实体类参数校验

创建SpringBoot项目CheckOut,参数校验依赖于:

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

首先将常用校验注解罗列如下,以便查看:

注解说明
@AssertFalse所注解的元素必须是Boolean类型,且值为false
@AssertTrue所注解的元素必须是Boolean类型,且值为true
@DecimalMax所注解的元素必须是数字,且值小于等于给定的值
@DecimalMin所注解的元素必须是数字,且值大于等于给定的值
@Digits所注解的元素必须是数字,且值必须是指定的位数
@Future所注解的元素必须是将来某个日期
@Max所注解的元素必须是数字,且值小于等于给定的值
@Min所注解的元素必须是数字,且值小于等于给定的值
@Range所注解的元素需在指定范围区间内
@NotNul所注解的元素值不能为null(注意:postman测试时,无法发送null的参数
@NotBlank所注解的元素值有内容
@Null所注解的元素值为null
@Past所注解的元素必须是某个过去的日期
@PastOrPresent所注解的元素必须是过去某个或现在日期
@Pattern所注解的元素必须满足给定的正则表达式
@Size所注解的元素必须是String、集合或数组,且长度大小需保证在给定范围之内
@Email所注解的元素需满足Email格式

1.单个参数校验

新建CheckOutController:

@RestController
@Validated
public class CheckOutController {

    @GetMapping("/single-check/test1")
    public String singleCheckTest1(@NotNull(message = "name 不能为空") String name,
                                   @Max(value = 99, message = "不能大于99岁") Integer age) {
        System.out.println("参数校验通过");
        return "通过";
    }
}

用postman发送请求时:

参数:

name张三
age100

后台打印错误:

45c23dc8a9e55fb93180a9a621a650f7.png

2. 实体类参数校验

当传递参数较多时,可以选择新建一个DTO类,来接收参数。

新建UserDTO类:

@Getter
@Setter
@AllArgsConstructor
@NoArgsConstructor
public class UserDTO {
    @NotBlank(message = "name不能为空字符串")
    private String name;

    @Size(max = 6, min = 2, message = "password所含字符数在[2,6]的范围内")
    private String password;

    @Max(value = 100, message = "age不能超过100")
    private Integer age;

    @AssertTrue(message = "liveInEarth必须为true")
    private boolean liveInEarth;
}

这里使用@NotBlank(检验字符串不为“”)、@Size(校验字符串、数组、集合的长度范围)、@Max(校验整数值的最大值上限)、@AssertTrue(校验入参一定为true)

对应controller方法:

@RestController
@Validated
public class CheckOutController {

    @PostMapping("/bean-check/test1")
    public void beanCheckTest1(@RequestBody @Valid UserDTO userDTO, BindingResult bindingResult) {
        System.out.println("参数校验通过");
    }

    @GetMapping("/bean-check/test2")
    public void beanCheckTest2(@Valid UserDTO userDTO, BindingResult bindingResult) {
        System.out.println("参数校验通过");
    }
}

注意:

①Controller类上的@Validated注解和controller方法中的@Valid注解都不能少,否则校验不会生效。

②这里有两个controller方法,分别展示了Post方法接收DTO实体类参数的参数校验和Get方法接收DTO实体类参数的参数校验的情形。

③这里方法中的BindingResult,存储了校验结果,可以用于后续统一异常处理

使用postman进行测试:

post:

2076e400453e18f232e74cb22e301273.png

后台输出:

javax.validation.ConstraintViolationException: 
beanCheckTest1.userDTO.liveInEarth: liveInEarth必须为true, 
beanCheckTest1.userDTO.name: name不能为空字符串, 
beanCheckTest1.userDTO.age: age不能超过100, 
beanCheckTest1.userDTO.password: password所含字符数在[2,6]的范围内

get:

73fd9c2004ea589280ebd8f5b27546d2.png

后台输出:

javax.validation.ConstraintViolationException: 
beanCheckTest2.userDTO.password: password所含字符数在[2,6]的范围内, 
beanCheckTest2.userDTO.name: name不能为空字符串, 
beanCheckTest2.userDTO.age: age不能超过100, 
beanCheckTest2.userDTO.liveInEarth: liveInEarth必须为true

3. 校验模式

在上面实体类参数校验的例子中,可以看到会校验所有字段,并将所有不符合校验规则的字段打印出来。这种校验策略是实体类参数校验的普通校验模式(默认的校验模式)。实际上有两种校验模式:

①普通模式(默认是这个模式): 会校验完所有的属性,然后返回所有的验证失败信息

②快速失败模式: 只要有一个验证失败,则返回。


如果想要配置第二种模式,需要添加如下配置类:

新建配置类ValidateStrategyConf:

import javax.validation.Validation;
import javax.validation.Validator;
import javax.validation.ValidatorFactory;
import org.hibernate.validator.HibernateValidator;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class ValidateStrategyConf {
    @Bean
    public Validator validator() {
        ValidatorFactory validatorFactory = Validation.byProvider( HibernateValidator.class )
                .configure()
                .failFast( true )
                .buildValidatorFactory();
        Validator validator = validatorFactory.getValidator();

        return validator;
    }
}

再次发送请求:

Get:

bbdcf405041afeede5d6a9b210b3e25b.png

后台打印:

a5398ce78007cc58ba7866aca905b6bd.png

可以看到校验到name字段不符合校验规则后,即停止校验了。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值