日志记录的作用和方法 java
程序中记录日志一般有两个目的:Troubleshooting和显示程序运行状态。好的日志记录方式可以提供我们足够多定位问题的依据。日志记录大家都会认为简单,但如何通过日志可以高效定位问题并不是简单的事情。这里列举下面三个方面的内容,辅以代码示例,总结如何写好日志,希望对他人有所启发和帮助:
- 怎样记日志可以方便Troubleshooting
- 程序运行状态可以记哪些
- 应该避免怎样的日志方式
怎样记日志可以方便Troubleshooting?
1. 对外部的调用封装
程序中对外部系统与模块的依赖调用前后都记下日志,方便接口调试。出问题时也可以很快理清是哪块的问题
- LOG.debug("Calling external system:" + parameters);
- Object result = null;
- try {
- result = callRemoteSystem(params);
- LOG.debug("Called successfully. result is " + result);
- } catch (Exception e) {
- LOG.warn("Failed at calling xxx system . exception : " + e);
- }
2.状态变化
程序中重要的状态信息的变化应该记录下来,方便查问题时还原现场,推断程序运行过程
- boolean isRunning;
- isRunning = true;
- LOG.info("System is running");
- //...
- isRunning = false;
- LOG.info("System was interrupted by " + Thread.currentThread().getName());
3.系统入口与出口:
这个粒度可以是重要方法级或模块级。记录它的输入与输出,方便定位
- void execute(Object input) {
- LOG.debug("Invoke parames : " + input);
- Object result = null;
- //business logic
- LOG.debug("Method result : " + result);
- }
4.业务异常:
任何业务异常都应该记下来:
- try {
- //business logical
- } catch (IOException e) {
- LOG.warn("Description xxx" , e);
- } catch (BusinessException e) {
- LOG.warn("Let me know anything");
- } catch (Exception e) {
- LOG.error("Description xxx", e);
- }
5.非预期执行:
为程序在“有可能”执行到的地方打印日志。如果我想删除一个文件,结果返回成功。但事实上,那个文件在你想删除之前就不存在了。最终结果是一致的,但程序得让我们知道这种情况,要查清为什么文件在删除之前就已经不存在
- int myValue = xxxx;
- int absResult = Math.abs(myValue);
- if (absResult < 0) {
- LOG.info("Original int " + myValue + "has nagetive abs " + absResult);
- }
6.很少出现的else情况:
else可能吞掉你的请求,或是赋予难以理解的最终结果
- Object result = null;
- if (running) {
- result = xxx;
- } else {
- result = yyy;
- LOG.debug("System does not running, we change the final result");
- }
程序运行状态可以记哪些?
程序在运行时就像一个机器人,我们可以从它的日志看出它正在做什么,是不是按预期的设计在做,所以这些正常的运行状态是要有的。
1. 程序运行时间:
- long startTime = System.currentTime();
- // business logical
- LOG.info("execution cost : " + (System.currentTime() - startTime) + "ms");
2. 大批量数据的执行进度:
- LOG.debug("current progress: " + (currentPos * 100 / totalAmount) + "%");
3.关键变量及正在做哪些重要的事情:
执行关键的逻辑,做IO操作等等
- String getJVMPid() {
- String pid = "";
- // Obtains JVM process ID
- LOG.info("JVM pid is " + pid);
- return pid;
- }
- void invokeRemoteMethod(Object params) {
- LOG.info("Calling remote method : " + params);
- //Calling remote server
- }
应该避免怎样的日志方式?
1. 混淆信息的Log
日志应该是清晰准确的: 当看到日志的时候,你知道是因为连接池取不到连接导致的问题么?
- Connection connection = ConnectionFactory.getConnection();
- if (connection == null) {
- LOG.warn("System initialized unsuccessfully");
- }
2. 记错位置
产品代码中,使用console记录日志,导致没有找到日志。
- } catch (ConfigurationException e) {
- e.printStackTrace();
- }
3. 记错级别
记错级别常常发生,常见的如:混淆代码错误和用户错误,如登录系统中,如果恶意登录,那系统内部会出现太多WARN,从而让管理员误以为是代码错误。可以反馈用户以错误,但是不要记录用户错误的行为,除非想达到控制的目的。
- LOG.warn("Failed to login by "+username+");
4. 遗漏信息
这里可能包含两种情况:(1)用户自己少写了信息,导致毫无参考价值;(2)用户调用log的方式导致丢失信息,如下例,没有stack trace.
- } catch (Exception ex) {
- log.error(ex);
- }
日志记录的作用和方法 java的更多相关文章
- 【学习笔记】开源日志记录工具log4j使用方法
http://blog.csdn.net/zouqingfang/article/details/37558469 一.在MyEclipse中使用log4j的步骤比较简单,主要分为以下四个步骤: 1. ...
- .NET Worker Service 添加 Serilog 日志记录
前面我们了解了 .NET Worker Service 的入门知识[1] 和 如何优雅退出 Worker Service [2],今天我们接着介绍一下如何为 Worker Service 添加 Ser ...
- Spring Boot 之日志记录
Spring Boot 之日志记录 Spring Boot 支持集成 Java 世界主流的日志库. 如果对于 Java 日志库不熟悉,可以参考:细说 Java 主流日志工具库 关键词: log4j, ...
- 巧用CurrentThread.Name来统一标识日志记录(java-logback篇)
▄︻┻┳═一Agenda: ▄︻┻┳═一巧用CurrentThread.Name来统一标识日志记录 ▄︻┻┳═一巧用CurrentThread.Name来统一标识日志记录(续) ▄︻┻┳═一巧用Cur ...
- Hibernate使用Log4j日志记录(使用xml文件)
日志记录使程序员能够将日志详细信息永久写入文件. Log4j和Logback框架可以在hibernate框架中使用来支持日志记录. 使用log4j执行日志记录有两种方法: 通过log4j.xml文件( ...
- Hibernate使用Log4j日志记录(使用properties文件)
我们知道,Log4j和Logback框架可用于支持日志记录hibernate,使用log4j有两种执行日志记录的方法: 通过log4j.xml文件(或) 通过log4j.properties文件 在这 ...
- 基于java.util.logging实现轻量级日志记录库(增加根据当前类class初始化,修复线程池模型(javaEE)下的堆栈轨迹顺序与当前调用方法不一致问题)
前言: 本章介绍自己写的基于java.util.logging的轻量级日志记录库(baseLog). 该版本的日志记录库犹如其名,baseLog,是个实现日志记录基本功能的小库,适合小型项目使用,方便 ...
- java异常处理 日志记录异常具体位置的方法
首先要在方法处抛出 Exception异常 然后在方法调用处try catch接收此异常对象 这样就能够记录异常具体位置了 控制台输出: 日志: 要点: System.getProperty(&quo ...
- Java学习笔记(十九)——Java 日志记录 AND log4j
[前面的话] 学习的进度应该稍微在快一点. Java日志到了必须学习怎么使用的时候了,因为在项目中要进行使用.基础性文章,选择性阅读. [结构] java日志对调试,记录运行,问题定位都起到了很重要的 ...
随机推荐
- Mysql Innodb 性能参数设置 https://www.rathishkumar.in/2017/01/how-to-allocate-innodb-buffer-pool-size-in-mysql.html
参考原文: https://www.rathishkumar.in/2017/01/how-to-allocate-innodb-buffer-pool-size-in-mysql.html 查看系统 ...
- all any some
SQLServer中有三个关键字可以修改比较运算符:All.Any和Some,其中Some和Any等价. 他们作用于比较运算符和子查询之间,作用类似Exists.not exists.in.not i ...
- monkey初接触
第一次听说monkey,根本不知道是什么东西,脑海里就一个印象,很厉害的自动化测试工具,可是体验了一下,似乎不是那么回事... 一.Monkey 是什么? monkey就是SDK中附带的一个工具. 二 ...
- Intellij IDEA使用Maven搭建spark开发环境(scala)
如何一步一步地在Intellij IDEA使用Maven搭建spark开发环境,并基于scala编写简单的spark中wordcount实例. 1.准备工作 首先需要在你电脑上安装jdk和scala以 ...
- Largest Rectangle in a Histogram(附上几组测试数据)
Largest Rectangle in a Histogram http://acm.hdu.edu.cn/showproblem.php?pid=1506 Time Limit: 2000/100 ...
- JavaScript的数据类型和运算符总结
1.定义变量用关键字 var var a = 1 var b = "abc" 2.javascript脚本每一行要用分号隔开 3.javascript的代码一般放在html代码的最 ...
- IIS 访问不了,IIS有问题,IIS右击浏览没反应
查看是否是下面的问题 web服务扩展中,下面三项设置为 “允许” CGI扩展 ISAPI扩展 Active Server Pages
- Halcon一维码和二维码的解码步骤和技巧——第11讲
针对Halcon中一维码和二维码的解码,我分别写了两篇文章,参见: <Halcon的一维条码解码步骤和解码技巧>:https://www.cnblogs.com/xh6300/p/1048 ...
- linux-git服务搭建
第一步,安装git: 源码安装参考:http://www.cnblogs.com/syuf/p/9151115.html 第二步,创建一个git用户,用来运行git服务: $ sudo adduser ...
- mysql简单实现查询结果添加序列号的方法
方法1: SELECT @rownum :=@rownum + 1 AS rownum, t.* FROM integral_system_user t, (SELECT @rownum := 0) ...