spring boot 统一异常处理
2018-07-03 01:02:59来源:博客园 阅读 ()
需求源自于任何一个业务的编写总会有各种各样的条件判断,需要时时手动抛出异常,又希望让接口返回友好的错误信息。
spring boot提供的帮助是自动将异常重定向到路由为/error的控制器
但是我们又希望手动抛出的异常与正常的数据返回为同一类型
所以我的解决方案由三个步骤组成:
1.一个异常枚举类 StatusCodeEnum.java
public enum StatusCodeEnum implements Serializable { SUCCESS(0, "成功"), ERROR(-1, "失败"), USER_INVALID(60000, "无效用户"), SYS_ARG_INVALID(11000, "无效参数"), ; private static final long serialVersionUID = 1L; private int code; private String msg; StatusCodeEnum(int code, String msg) { this.code = code; this.msg = msg; } public int getCode() { return code; } public void setCode(int code) { this.code = code; } public String getMsg() { return msg; } public void setMsg(String msg) { this.msg = msg; } //根据code获取对应枚举 public static StatusCodeEnum getByCode(int code) { StatusCodeEnum[] values = StatusCodeEnum.values(); for (StatusCodeEnum bizStatusCodeEnum : values) { if (bizStatusCodeEnum.code == code) { return bizStatusCodeEnum; } } return null; } }
2.一个异常调用类 BaseException.java
因为抛出异常只能抛出字符串 所以这里使用了com.alibaba.fastjson.JSON包
public class BaseException { private int code; private String message; public static void error(StatusCodeEnum statusCodeEnum) throws Exception { error(statusCodeEnum.getCode(),statusCodeEnum.getMsg()); } public static void error(String message) throws Exception { error(-1,message); } public static void error(int code,String message) throws Exception { BaseException baseException = new BaseException(); baseException.setCode(code); baseException.setMessage(message); throw new Exception(JSON.toJSONString(baseException)) ; } public int getCode() { return code; } public void setCode(int code) { this.code = code; } public String getMessage() { return message; } public void setMessage(String message) { this.message = message; } @Override public String toString() { return "BaseException{" + "code=" + code + ", message='" + message + '\'' + '}'; } }
3.异常处理控制器 ErrorController.java
@Controller public class ErrorController extends AbstractErrorController{ @Autowired ObjectMapper objectMapper; public ErrorController() { super(new DefaultErrorAttributes()); } @Override public String getErrorPath() { return null; } @RequestMapping("/error") @ResponseBody public BaseRs getErrorPath(HttpServletRequest request, HttpServletResponse response) { Map<String,Object> model = Collections.unmodifiableMap(getErrorAttributes(request,false)); //获取异常 可将异常打印到日志 Throwable cause = getCause(request); int status = (Integer)model.get("status"); //自定义友好错误信息 String msg = (String)model.get("message"); JSONObject object = JSONObject.parseObject(msg); int code = object.getInteger("code"); String message = object.getString("message"); return new BaseRs(code,message); } protected Throwable getCause(HttpServletRequest request) { Throwable error = (Throwable)request.getAttribute("javax.servlet.error.exception"); if(null == error){ //MVC有可能会封装异常成ServletException ,需要调用getCause获取真正的异常 while (error instanceof ServletException && error.getCause() != null){ error = ((ServletException) error).getCause(); } } return error; } }
以上三个文件为异常处理的核心
其中的BaseRs类是统一数据返回
public class BaseRs<T> implements Serializable { private int code; private String message; public BaseRs() { } /** * 返回内容 */ private T content; public int getCode() { return code; } public String getMessage() { return message; } public T getContent() { return content; } public BaseRs(int code, String message) { this.code = code; this.message = message; } public BaseRs(int code, String message, T content) { this.code = code; this.message = message; this.content = content; } public BaseRs(StatusCodeEnum status) { this.code = status.getCode(); this.message = status.getMsg(); } public BaseRs(StatusCodeEnum status, T content) { this.code = status.getCode(); this.message = status.getMsg(); this.content = content; } public static <V> BaseRs ok(V content) { return new BaseRs(StatusCodeEnum.SUCCESS, content); } public static BaseRs ok() { return new BaseRs(StatusCodeEnum.SUCCESS); } public static BaseRs error(StatusCodeEnum error) { return new BaseRs(error); } public void setCode(StatusCodeEnum status) { this.code = status.getCode(); } public void setMessage(String message) { this.message = message; } public void setContent(T content) { this.content = content; } @Override public String toString() { return "BaseRs{" + "code=" + code + ", message='" + message + '\'' + ", content=" + content + '}'; } public void setCode(int code) { this.code = code; } }
最后的控制层代码以最简洁的方式调用即可:
@Controller public class IndexController { @RequestMapping("/a") @ResponseBody public BaseRs a() throws Exception{ boolean s = false; if(!s){ BaseException.error(StatusCodeEnum.USER_INVALID); } return new BaseRs(StatusCodeEnum.SUCCESS); } }
本篇博客的码云地址: https://gitee.com/zhao-baolin/springboot_error
标签:
版权申明:本站文章部分自网络,如有侵权,请联系:west999com@outlook.com
特别注意:本站所有转载文章言论不代表本站观点,本站所提供的摄影照片,插画,设计作品,如需使用,请与原作者联系,版权归原作者所有
上一篇:第8天 Java基础语法
下一篇:Map集合框架的练习
- Spring系列.ApplicationContext接口 2020-06-11
- springboot2配置JavaMelody与springMVC配置JavaMelody 2020-06-11
- 给你一份超详细 Spring Boot 知识清单 2020-06-11
- SpringBoot 2.3 整合最新版 ShardingJdbc + Druid + MyBatis 2020-06-11
- 掌握SpringBoot-2.3的容器探针:实战篇 2020-06-11
IDC资讯: 主机资讯 注册资讯 托管资讯 vps资讯 网站建设
网站运营: 建站经验 策划盈利 搜索优化 网站推广 免费资源
网络编程: Asp.Net编程 Asp编程 Php编程 Xml编程 Access Mssql Mysql 其它
服务器技术: Web服务器 Ftp服务器 Mail服务器 Dns服务器 安全防护
软件技巧: 其它软件 Word Excel Powerpoint Ghost Vista QQ空间 QQ FlashGet 迅雷
网页制作: FrontPages Dreamweaver Javascript css photoshop fireworks Flash