关于LOGBACK日志分包打印,过滤不需要的日志
前景提要
最近收到个任务,由于定时任务日志打印跟其他任务日志打印在同一个文件中,导致其他日志可读性很差,基本都是十秒一个的定时任务的日志,这样原先的日志就失去了意义,需要将定时任务中的日志与其他任务的日志分开打印,于是就使用到了logback的日志分包打印,以及过滤器功能.
下面上一个小demo,其中也参考了很多博客,供大家参考.
-
总体项目结构
首先的话是三个类的创建,service以及两个dao.
@Service
public class ObligationService {
static final Logger log = LoggerFactory.getLogger(ObligationService.class);
@Resource
ObligationDao dao;
@Resource
Obligation2Dao obligation2Dao;
public void obligate(){
log.debug("task:obligate start...");
dao.queryObligations();
obligation2Dao.queryObligations();
log.error("task:An error occurred during the progress");
log.debug("task:obligate end...");
}
}
@Repository
public class ObligationDao {
static final Logger log = LoggerFactory.getLogger(ObligationDao.class);
public void queryObligations() {
log.debug("task:query obligations start...");
log.error("task: An error occurred during the query");
log.debug("task: query obligations end...");
}
}
@Repository
public class Obligation2Dao {
static final Logger log = LoggerFactory.getLogger(Obligation2Dao.class);
public void queryObligations() {
log.debug("query obligations start...22222222222222");
log.error("An error occurred during the query22222222222222");
log.debug("query obligations end...222222222222222");
}
}
二 接着是logback-spring.xml 的配置
<?xml version="1.0" encoding="UTF-8"?>
<configuration debug="true" scan="false">
<springProperty scop="context" name="spring.application.name" source="spring.application.name" defaultValue="pig"/>
<property name="log.path" value="logs/${spring.application.name}"/>
<!-- Log file debug output -->
<appender name="debug" class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>${log.path}/ObligationService.log</file>
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
<fileNamePattern>${log.path}/ObligationService-%d{yyyy-MM-dd}.log</fileNamePattern>
</rollingPolicy>
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{5} - %msg%n</pattern>
</encoder>
</appender>
<appender name="debug1" class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>${log.path}/ObligationDao.log</file>
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
<fileNamePattern>${log.path}/ObligationDao-%d{yyyy-MM-dd}.log</fileNamePattern>
</rollingPolicy>
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{5} - %msg%n</pattern>
</encoder>
</appender>
<appender name="debug2" class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>${log.path}/common.log</file>
<filter class="com.example.bootstart.logfilter.SampleFilter"/>
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
<fileNamePattern>${log.path}/common-%d{yyyy-MM-dd}.log</fileNamePattern>
</rollingPolicy>
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{5} - %msg%n</pattern>
</encoder>
</appender>
<springProfile name="dev">
<root level="DEBUG">
<appender-ref ref="debug2"/>
</root>
<logger name="com.example.bootstart.log.ObligationService" level="DEBUG">
<appender-ref ref="debug"/>
</logger>
<logger name="com.example.bootstart.log2.ObligationDao" level="DEBUG">
<appender-ref ref="debug1"/>
</logger>
</springProfile>
</configuration>
<logger name="com.example.bootstart.log.ObligationService"> 这个属性指明了哪个包或者哪个类使用特殊的日志配置.大家可能注意到了filter,filter我只在debug2这个日志配置中使用,目的就是为了过滤掉下面两个已经日志特殊化处理的类.
三 filter的配置
public class SampleFilter extends Filter<ILoggingEvent> {
@Override
public FilterReply decide(ILoggingEvent event) {
if (getPackName(event.getLoggerName()).equals("com.example.bootstart.log")
||getPackName(event.getLoggerName()).equals("com.example.bootstart.log2"))
{
return FilterReply.DENY;
} else{
return FilterReply.ACCEPT;
}
}
public String getPackName(String className){
String packName = className.substring(0,className.lastIndexOf("."));
return packName;
}
}
这是一个简单的fiter的配置,大家初次看的话可能对这段if不太理解.
if (getPackName(event.getLoggerName()).equals("com.example.bootstart.log")
||getPackName(event.getLoggerName()).equals("com.example.bootstart.log2"))
{
return FilterReply.DENY;
}
这段if语句主要是为了判断每行日志都是一个event,其中有很多属性,LoggerName就是打印这一行日志的这个类,我通过字符串截取的方法获得这个类的包,然后再使用基本的equals语句去与我所要过滤的包比较,若是true,则返回FilterReply.DENY,表示不打印这段日志,而FilterReply.ACCEPT则表示打印这段日志.
四 测试用例
最后就是启动我自己的测试用例,就可以在log文件夹中输出对应的类的日志.
@RunWith(SpringRunner.class)
@SpringBootTest
public class dispatchByPackageTest {
@Autowired
private ObligationService obligationService;
@Test
public void dispatchByPackageTest() {
obligationService.obligate();
}
}
日志的截图的话就只上一个.
五 总结
参考了很多博客,谢谢大家.