异常处理和日志输出使用小结

一、能经过预检查的异常直接处理,不用catch来处理,没法经过预检查的异常才去使用catch处理;前端


二、不要对大段代码进行try catch,只须要在非稳定代码地方进行try catch处理;数据库


三、异常的捕获是为了处理他而不是抛弃它,若是不想处理能够传给外层的调用者,可是应用的最外层调用者必须处理它。一般在SpringMVC应用中,controller就已是最外层的调用者了,异常最迟在这里就必须处理掉而不能将异常抛给前端,返回给前端的必须是一个处理以后的比较友好的提示信息,一般异常是在controller层或者Service层就处理掉;网络


四、捕获到异常时,一般作法是先将异常的详细信息输出到日志,而后再给前端返回一个比较友好的提示信息,这样在前端获取到异常结果时能够经过日志系统快速定位到问题所在,可是一般状况下日志会比较多,日志中定位问题比较困难,有如下两个建议:
  1)、日志记录详细尽量详细,好比说包含出现异常所在的类名、方法名、出错时间、入参信息、业务异常代码、异常详细信息、异常惟一编码等,若是有异常堆栈建议也一块儿输出;
  2)、在输出日志时生成一个异常惟一编码输出到日志中,同时在返回给调用者的信息中带上这个编码,这样在前端捕获到异常结果时能根据这个异常惟一编码快速定位到日志对应地方;]框架


五、一般要捕获的异常的地方有:方法入口处进行参数为空和参数合法性检查,对框架或者JDK等底层代码抛出的异常(好比iBatis抛出的数据库操做异常、Spring框架抛出的异常、RPC调用抛出的异常、网络操做抛出的异常、除零、空指针、下标越界等JDK抛出的异常等等),业务操做异常(好比查询数据返回结果为空、数据业务合法性检查等等);其中业务操做异常建议根据业务状况作一个汇编,将每种异常分配一个统一的编码和描述信息定义为一个枚举值,这样方便业务异常的排查;测试


六、必定不要忘记对资源对象、流对象在try finally中关闭,而且还要作异常处理;JDK7及以上的建议使用try-with-resources的方式处理,代码看起来会简洁不少;编码

 

七、不能在finally中使用return,由于这会致使try中的return失效;debug


八、调用其余方法必须进行空指针判断(注意基本数据类型和基本数据类型对象,好比int和Integer,Integer有可能为NULL,而int不可能为NULL,还有级联调用也容易产生空指针异常,好比:obj.getA().getB().getC());指针


九、对于trace/debug/info级别的日志输出,必须使用条件输出或者占位符的方式,避免执行字符串拼接而浪费系统资源,可是日志最终却没有打印;
  好比:
  错误:logger.debug("process trade with id:" + id + "and symbol:" + symbol);
  正确:
    条件输出:
      if (logger.isDebugEnabled()) {
        logger.debug("process trade with id:" + id + "and symbol:" + symbol);
      }
    占位符:
      logger.debug("process trade with id: {} and symbol: {}", id, symbol);调试


十、谨慎的注意每条日志输出的级别设置:debug级别的日志用于协助调试用的,通常只输出到开发环境和测试环境吗,info级别的日志必须有选择的输出,其做用是用于协助查看系统运行情况;debug和info级别的日志严禁在生产环境输出;warn级别的日志用于非系统和业务错误,可是会影响系统输出结果的信息,好比记录用户输入参数错误的状况可使用warn级别日志,避免用户投诉时有据可依;error级别只记录系统逻辑错误、异常等重要的错误信息,如非必要,请不要使用这个级别;日志

相关文章
相关标签/搜索