java后端开发常用日志技巧

经过不断的项目实践,不断总结,一个好的开发人员,应该有个好的开发习惯,日志是开发过程中不可缺少的一项,有了日志可以节省很多我们不必要的麻烦,也可以使我们迅速的定位问题。

使用Logging框架写Log基本上就三个步骤
  1. 引入loggerg类和logger工厂类
  2. 声明logger
  3. 记录日志
例子:

//1. 引入slf4j接口的Logger和LoggerFactory
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class UserService {
  //2. 声明一个Logger,这个是static的方式,我比较习惯这么写。
  private final static Logger logger = LoggerFactory.getLogger(UserService.class);

  public boolean verifyLoginInfo(String userName, String password) {
    //3. log it,输出的log信息将会是:"Start to verify User [Justfly]
    logger.info("Start to verify User [{}]", userName);
    return false;
  }
}

学习链接:

http://slf4j.org/faq.html#declared_static

两种方式的优劣概述如下:
  • 静态Logger对象相对来说更符合语义,节省CPU,节省内存,不支持注入
  • 对象变量Logger支持注入,对于一个JVM中运行的多个引用了同一个类库的应用程序,可以在不同的应用程序中对同个类的Logger进行不同的配置。比如Tomcat上部署了俩个应用,他们都引用了同一个lib
通常为了代码的规范,判断日志Logger是否开启使用如下方法
  • public boolean isTraceEnabled();
  • public boolean isDebugEnabled();
  • public boolean isInfoEnabled();
  • public boolean isWarnEnabled();
  • public boolean isErrorEnabled();
如:
这组方法的作用主要是避免没必要的log信息对象的产生,尤其是对于不支持参数化信息的Log框架(Log4j 1, commons-logging)。如下面的例子所示,如果没有加debug级别判断,在Debug级别被禁用的环境(生产环境)中,第二行的代码将没有必要的产生多个String对象。
1   if (logger.isDebugEnabled()){
2    logger.debug("["+resultCount+"]/["+totalCount+"] of users are returned");
3  }

3. Log什么

前面讲了怎么使用Loggger的方法log日志,下面继续讲讲在什么地方需要记录什么级别的log,以及需要记录什么内容。

3.1 如何使用不同级别的Log

SLF4J把Log分成了Error,Warn,Info,Debug和Trace五个级别。我们可以把这俩个级别分成两组

3.1.1 用户级别

Error、Warn和Info这三个级别的Log会出现在生产环境上,他们必须是运维人员能阅读明白的
3.1.1.1 Error
  • 影响到程序正常运行、当前请求正常运行的异常情况,例如:
    • 打开配置文件失败
    • 第三方应用网络连接异常
    • SQLException
  • 不应该出现的情况,例如:
    • 某个Service方法返回的List里面应该有元素的时候缺获得一个空List
    • 做字符转换的时候居然报错说没有GBK字符集
3.1.1.2 Warn
  • 不应该出现但是不影响程序、当前请求正常运行的异常情况,例如:
    • 有容错机制的时候出现的错误情况
    • 找不到配置文件,但是系统能自动创建配置文件
  • 即将接近临界值的时候,例如:
    • 缓存池占用达到警告线
3.1.1.3 Info
  • 系统运行信息
    • Service方法的出入口
    • 主要逻辑中的分步骤
  • 外部接口部分
    • 客户端请求参数和返回给客户端的结果
    • 调用第三方时的调用参数和调用结果
在一些Exception处理机制中,我们会每层或者每个Service对应一个RuntimeException类,并把他们抛出去,留给最外层的异常处理层处理。典型代码如下:
try {
  
} catch (Exception ex){
  String errorMessage=String.format("Error while reading information of user [%s]",userName);
  logger.error(errorMessage,ex);
   throw   new  UserServiceException(errorMessage,ex);
}


最后为了避免日志过于繁琐,开发者应该注意在项目中日志的打印,简单一句话,记录有利于定位问题的日志,做到不多打,也不少打同时根据需求调节日志的级别,一般建议到info级别。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值