天天看点

阿里巴巴 Java 开发手册之异常日志(二)-------我的经验二、异常日志

说明:无法通过预检查的异常除外,如在解析一个外部传来的字符串形式数字时,通过catch numberformatexception来实现。 正例:if (obj != null) {...} 反例:try { obj.method() } catch (nullpointerexception e) {...}

说明:本规约明确防止npe是调用者的责任。即使被调用方法返回空集合或者空对象,对调用者来说,也并非高枕无忧,必须考虑到远程调用失败,运行时异常等场景返回null的情况。

正例:可以使用jdk8的optional类来防止npe问题。(说实话,这个optional没用过)

说明:关于rpc方法返回方式使用result方式的理由:

1)使用抛异常返回方式,调用方如果没有捕获到就会产生运行时错误。

2)如果不加栈信息,只是new自定义异常,加入自己的理解的error message,对于调用端解决问题的帮助不会太多。如果加了栈信息,在频繁调用出错的情况下,数据序列化和传输的性能损耗也是问题。

正例:一个类中有多个public方法,都需要进行数行相同的参数校验操作,这个时候请抽取:private boolean checkparam(dto dto) {...}(虽然这样说没错,但有时候秉着不改别人代码的原则很多时候都是复制代码,我觉得这个坏习惯该改了)

import org.slf4j.logger;

import org.slf4j.loggerfactory;

private static final logger logger = loggerfactory.getlogger(abc.class);

正例:mppserver应用中单独监控时区转换异常,如: mppserver_monitor_timezoneconvert.log

说明:推荐对日志进行分类,错误日志和业务日志尽量分开存放,便于开发人员查看,也便于通过日志对系统进行及时监控。

说明:logger.debug("processing trade with id: " + id + " symbol: " + symbol); 如果日志级别是warn,上述日志不会打印,但是会执行字符串拼接操作,如果symbol是对象,会执行tostring()方法,浪费了系统资源,执行了上述操作,最终日志却没有打印。

正例:(条件)

if (logger.isdebugenabled()) {

logger.debug("processing trade with id: " + id + " symbol: " + symbol);

}

正例:(占位符)

logger.debug("processing trade with id: {} symbol : {} ", id, symbol);

正例:< logger name="com.taobao.dubbo.config" additivity="false">

正例:logger.error(各类参数或者对象tostring + "_" + e.getmessage(), e);

记录日志时请思考:这些日志真的有人看吗?看到这条日志你能做什么?能不能给问题排查带来好处?