今天记录下 SpringBoot 中 @ExceptionHandler 的使用。
场景
有一个员工表(employee),且给表中的 username 属性设置了唯一性。
-- auto-generated definition
create table employee
(
id bigint auto_increment comment '主键'
primary key,
name varchar(32) not null comment '姓名',
username varchar(32) not null comment '用户名',
password varchar(64) not null comment '密码',
phone varchar(11) not null comment '手机号',
sex varchar(2) not null comment '性别',
id_number varchar(18) not null comment '身份证号',
status int default 1 not null comment '状态 0:禁用,1:启用',
create_time datetime null comment '创建时间',
update_time datetime null comment '更新时间',
create_user bigint null comment '创建人',
update_user bigint null comment '修改人',
constraint idx_username
unique (username)
)
comment '员工信息' collate = utf8_bin;
我想通过新增员工功能添加一个员工,但是当添加用户名重复时会报以下错误。
IDEA报错
API接口报错
处理
可以看到前端并没有返回具体的报错信息,此时我们想要把 用户名重复 的错误返回给前端就可以用到 @ExceptionHandler 注解来实现。
先写一个类并添加 @RestControllerAdvice 注解来捕获异常,编写一个方法并添加 @ExceptionHandler 注解使其能够捕获我们想要捕获的错误类型(方法参数里面使我们想要捕获的错误类型)。
根据上面 IDEA 截图的报错可以看到报错的类型为 “SQLIntegrityConstraintViolationException”,报错信息为 " Duplicate entry ‘zhangsan’ for key ‘employee.idx_username’ ",
package com.sky.handler;
import com.sky.result.Result;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.RestControllerAdvice;
import java.sql.SQLIntegrityConstraintViolationException;
/**
* 全局异常处理器,处理项目中抛出的业务异常
*/
@RestControllerAdvice
@Slf4j
public class GlobalExceptionHandler {
// 处理重复用户名错误
@ExceptionHandler
public Result exceptionHandler(SQLIntegrityConstraintViolationException ex){
// 得到报错信息:Duplicate entry 'zhangsan' for key 'employee.idx_username'
String message = ex.getMessage();
// 判断是否是重复数据异常
if (message.contains("Duplicate")) {
// 得到重复的用户名
String[] split = message.split(" ");
String userName = split[2];
return Result.error("用户名已存在:" + userName);
}
// 若不是重复数据异常,则返回默认的错误信息
else{
return Result.error("位置错误");
}
}
}
结果
此时再添加重复员工信息时就会返回具体信息。
API接口界面
IDEA界面
可以看到此时IDEA控制台界面就不会在报错了,因为我们已经将这个错误正常处理了。