❣博主主页: 33的博客❣
▶️文章专栏分类:JavaEE◀️
🚚我的代码仓库: 33的代码仓库🚚
🫵🫵🫵关注我带你了解更多进阶知识
1.前言
⽇志对我们来说并不陌⽣, 从JavaSE部分, 我们就在使⽤ System.out.print 来打印⽇志了。通过打印⽇志来发现和定位问题, 或者根据⽇志来分析程序的运⾏过程. 在Spring的学习中, 也经常根据控制台的⽇志来分析和定位问题。那么接下来,我们就对Spring日志进行深度学习。
2.日志使用
Spring Boot在项目启动的适合默认就有日志输出:
那么和 System.out.println(“打印日志”);有什么不同,如下图缺少了很多信息
SpringBoot 内置了⽇志框架 Slf4j , 我们可以直接在程序中调⽤ Slf4j 来输出⽇志
2.1打印日志
日志打印步骤:
1.在重新中获得日志对象
2.使用日志对象输出要打印的内容
private static Logger logger= LoggerFactory.getLogger(LoggerController.class);
@RequestMapping("t1")
public void print(){
logger.info("打印日志");
}
2.2 门面模式(外观模式)
SLF4J是门面模式的典型应用(但不仅仅使用门面模式)。
门面模式又称为外观模式,提供了一个统一的接口,用来访问子系统的一群接口,主要特征是定义了定义了一个高层接口,让子系统更容易使用。
门面模式实现:
场景:回家,我们会打开各屋的灯,离开时,也会关闭各屋的灯,但是非常麻烦的,如果家里设置一个总开关,来控制整个屋的灯就会很方便。
public class FacadePatternDemo {
public static void main(String[] args) {
//调用门面
LightFacade lightFacade = new LightFacade();
lightFacade.lightOn();
}
}
//灯的门面
class LightFacade{
private Light livingRoomLight = new LivingRoomLight();
private Light hallLight = new HallLight();
private Light diningLight = new DiningLight();
public void lightOn(){
livingRoomLight.on();
hallLight.on();
diningLight.on();
}
public void lightOff(){
livingRoomLight.off();
hallLight.off();
diningLight.off();
}
}
//客厅灯
class LivingRoomLight implements Light{
@Override
public void on() {
System.out.println("打开客厅灯");
}
@Override
public void off() {
System.out.println("关闭客厅灯");
}
}
//走廊灯
class HallLight implements Light{
@Override
public void on() {
System.out.println("打开⾛廊灯");
}
@Override
public void off() {
System.out.println("关闭⾛廊灯");
}
//餐厅灯
class DiningLight implements Light{
@Override
public void on() {
System.out.println("打开餐厅灯");
}
@Override
public void off() {
System.out.println("关闭餐厅灯");
}
}
门面模式优点:
• 减少了系统的相互依赖. 实现了客户端与子系统的耦合关系, 这使得子系统的变化不会影响到调用它
的客⼾端;
• 提⾼了灵活性, 简化了客户端对子系统的使用难度, 客户端无需关心子系统的具体实现方式, 而只需要和门面对象交互即可.
• 提高了安全性. 可以灵活设定访问权限, 不在门面对象中开通方法, 就⽆法访问
2.3SLF4J框架
SLF4J就是其他日志框架的门面,SLF4J 可以理解为是提供⽇志服务的统⼀API接⼝, 并不涉及到具体的⽇志逻辑实现,日志具体的实现有log4j、JUL、logback。
不引入日志门面:
常见的⽇志框架有log4J, logback等. 如果⼀个项⽬已经使用了log4j,而你依赖的另⼀个类库,假如是Apache Active MQ, 它依赖于另外⼀个日志框架logback, 那么你就需要把logback也加载进去。
存在问题:
- 不同⽇志框架的API接口和配置文件不同, 如果多个日志框架共存, 那么不得不维护多套配置⽂件(这个配置⽂件是指用户自定义的配置文件).
- 如果要更换日志框架, 应⽤程序将不得不修改代码, 并且修改过程中可能会存在⼀些代码冲突.
- 如果引入的第三方框架, 使用了多套, 那就不得不维护多套配置.
引入日志门面
引入日志门志框架之后, 应用程序和日志框架(框架的具体实现)之间有了统⼀的API接⼝(门面日志框架实现), 此时应用程序只需要维护⼀套⽇志⽂件配置, 且当底层实现框架改变时, 也不需要更改应用程序代码。
2.4日志格式说明
⽇志级别代表着⽇志信息对应问题的严重性,日志级别有6种:FATAL、ERROR、WARN、INFO、DEBUG、TRACE。
• FATAL: 致命信息,表⽰需要⽴即被处理的系统级错误.
• ERROR: 错误信息, 级别较⾼的错误⽇志信息, 但仍然不影响系统的继续运⾏.
• WARN: 警告信息, 不影响使⽤, 但需要注意的问题
• INFO: 普通信息, ⽤于记录应⽤程序正常运⾏时的⼀些信息, 例如系统启动完成、请求处理完成等.
• DEBUG: 调试信息, 需要调试时候的关键信息打印.
• TRACE: 追踪信息, ⽐DEBUG更细粒度的信息事件(除⾮有特殊⽤意,否则请使⽤DEBUG级别替代)
打印不=不同级别的日志:
public String printLog() {
logger.trace("================= trace ===============");
logger.debug("================= debug ===============");
logger.info("================= info ===============");
logger.warn("================= warn ===============");
logger.error("================= error ===============");
return "打印不同级别的⽇志" ;
}
日志打印结果:
结果中发现日志中只出现了info,warn,erro级别的日志。这个与日志级别的配置有关,日志的输出级别默认是info,所以只会打印⼤于等于此级别的⽇志,也就是info, warn和error。
如果要修改日志的打印,可以通过配置文件进行修改:
logging.level.root: debug
在打印日志·的时候一般是输出在控制台上,然而在线上环境,我们需要把日志保存起来,一遍问题出现以后追溯问题。
日志持久化存储:
logging.file.name: spring-blog.log
配置日志分割:
// 分割后的⽇志⽂件名为:⽇志名.⽇期.索引
logging.logback.rollingpolicy.file-name-pattern=${LOG_FILE}.%d{yyyy-MM-dd}.%i
//按照1kb分割
logging.logback.rollingpolicy.max-file-size=1KB
3.@Slf4j输出日志
每次都使⽤LoggerFactory.getLogger(xxx.class) 很繁琐,且每个类都添加⼀遍,lombok给我们提供了⼀种更简单的⽅式。
1.添加lombok框架
2.使用@Slf4j注解
添加lombok依赖:
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
输出日志
@Slf4j
@RestController
public class LogController {
public void log(){
log.info("-------------要输出⽇志的内容----------------");
}
}
4.总结
⽇志是程序中的重要组成部分,使⽤⽇志可以快速的发现和定位问题,SpringBoot内容了⽇志框架,默认情况下使⽤的是info⽇志级别将⽇志输出到控制台的,我们可以通过lombok提供的@Slf4j 注解和log 对象快速的打印⾃定义⽇志.