瑞吉外卖项目实践笔记(全部异常处理)
瑞吉外卖项目实践笔记
使用全局异常处理
1 应用背景
1.1 遇到的问题
在完成瑞吉外卖项目中的新增用户功能时,数据库中username字段添加索引(无法重复),即一个username只能对应一个用户。首次实现时未对username字段唯一性进行处理。新增相同username用户在数据库添加时会抛出sql异常。sql异常如下:
java.sql.SQLIntegrityConstraintViolationException: Duplicate entry test for key idx_username
附上新增用户对应Controller的实现方法代码:
@PostMapping
public R<String> employee(HttpServletRequest request, @RequestBody Employee employee) {
Long createEmployee = (Long) request.getSession().getAttribute("employee");
employee.setCreateUser(createEmployee);
employee.setUpdateUser(createEmployee);
String password = "XXXXXXX";
//密码MD5加密
password = DigestUtils.md5DigestAsHex(password.getBytes());
employee.setPassword(password);
LocalDateTime time = LocalDateTime.now();
employee.setCreateTime(time);
employee.setUpdateTime(time);
boolean save = employeeService.save(employee);
if (save) {
return R.success("");
} else {
return R.error("");
}
}
1.2 问题的解决方法
针对以上问题解决方法有二:
-
校验方法:使用Java代码在接收到参数username时进行唯一性校验; 异常处理方法:捕获因唯一性而产生的sql异常,并进行异常处理;
1.2.1 校验方法
校验username唯一性方法实现步骤可以如下:
- 获取POST请求中的username作为参数;
- 通过username查询数据库用户表并返回Employee对象;
- 如果返回对象为空即当前username是唯一的,可以正常进行添加操作。相反则数据库中已存在相同username用户,直接返回错误信息给前端;
1.2.2 异常处理方法
异常处理方法可以在方法体中捕获因添加重复索引产生的sql异常,也可以选择添加全局异常处理来统一管理。
这里阐述一下采用全局异常处理的优势:
- 能够实现针对异常进行统一性管理,方便维护;
- 是对Spring面向切面特性(AOP)的实现;
2 应用实现
全部异常处理的实现为新建一个处理类GlocalExceptiionHandler,代码如下:
@ControllerAdvice(annotations = {
RestController.class, Controller.class})
@ResponseBody
@Slf4j
public class GlobalExceptionHandler {
@ExceptionHandler(value = SQLIntegrityConstraintViolationException.class)
public R<String> exceptionHandler(SQLIntegrityConstraintViolationException exception){
String ExMsg = exception.getMessage();
log.error(ExMsg);
if (ExMsg.contains("Duplicate entry")){
String[] s = ExMsg.split(" ");
return R.error("添加的用户名[" + s[2] +"]已存在!");
}
return R.error("未知异常!");
}
}
-
@ControllerAdvice设定拦截规则 @ExceptionHandler设定拦截的异常类型
