异常处理器
- 出现异常现象的常见位置与常见诱因如下:
    - 框架内部抛出的异常:因使用不合规导致
- 数据层抛出的异常:因外部服务器故障导致(例如:服务器访问超时)
- 业务层抛出的异常:因业务逻辑书写错误导致(例如:遍历业务书写操作,导致索引异常等)
- 表现层抛出的异常:因数据收集校验等规则导致(例如:不匹配的数据类型间导致异常)
- 工具类抛出的异常:因工具类书写不严谨不够强壮导致(例如:必要释放的连接长期未释放等)
 
- 所有的异常均抛出到表现层进行处理。
SpringMVC中的异常处理
- 异常处理器
    - 集中的、统一的处理项目中出现的异常
 
如何使用:
- 在表现层包中创建异常处理类,在类前添加@RestControllerAdvice注解
- 在类中添加需要的异常处理方法,并将对应的异常作为形参传入
- 在方法前添加@ExceptionHandler注解并在属性中以类的方式注名所处理的异常
- 在异常处理中返回的数据要和其他表现层方法返回值相同,采用与前端通信的联通协议即可
项目异常分类
- 业务异常 (BusinessException)
    - 不规范的用户行为产生的异常
- 规范的用户行为产生的异常
 
- 系统异常 (SystemException)
    - 项目运行过程中可预计且无法避免的异常
 
- 其他异常 (Exception)
    - 编程人员未预料到的异常
 
项目异常的处理方案
- 业务异常的处理
    - 发送对应消息传递给用户,提醒规范操作
 
- 系统异常的处理
    - 发送固定消息传递给用户,安抚用户
- 发送特定消息给运维人员,提醒维护
- 记录日志
 
- 其他异常的处理
    - 发送固定消息传递给用户,安抚用户
- 发送特定消息给编程人员,提醒维护(纳入预期范围内)
- 记录日志
 
如何操作
- 自定义两种异常
public class SystemException extends RuntimeException{
    private Integer code;
    public Integer getCode() {
        return code;
    }
    public void setCode(Integer code) {
        this.code = code;
    }
    public SystemException(Integer code, String message ) {
        super(message);
        this.code = code;
    }
    public SystemException(Integer code, String message, Throwable cause ) {
        super(message, cause);
        this.code = code;
    }
}
public class BusinessException extends RuntimeException{
    private Integer code;
    public Integer getCode() {
        return code;
    }
    public void setCode(Integer code) {
        this.code = code;
    }
    public BusinessException(Integer code, String message ) {
        super(message);
        this.code = code;
    }
    public BusinessException(Integer code, String message, Throwable cause ) {
        super(message, cause);
        this.code = code;
    }
}
- 编写异常处理类
@RestControllerAdvice
public class ProjectExceptionAdvice {
    @ExceptionHandler(SystemException.class)
    public Result doSystemException(SystemException systemException) {
        //记录日志
        //发送消息给运维
        //将异常信息发送邮件给开发人员
        return new Result(systemException.getCode(),null,systemException.getMessage());
    }
    @ExceptionHandler(BusinessException.class)
    public Result doBusinessException(BusinessException businessException) {
        return new Result(businessException.getCode(),null,businessException.getMessage());
    }
    @ExceptionHandler(Exception.class)
    public Result doException(Exception exception) {
        //记录日志
        //发送消息给运维
        //将异常信息发送邮件给开发人员
        return new Result(Code.SYSTEM_UNKNOWN_ERR,null,"系统繁忙,请稍后再试!");
    }
}
在代码中使用try…catch将异常重新封装成自定义异常即可。
