logback日志框架源码分析

目录

(一)入口:slf4j选择日志框架

(二)日志框架初始化

(1)logback的3种配置方式

a、BasicConfigurator默认配置

b、SPI方式配置的Configurator实现类

c、通过配置文件初始化

(2)xml配置文件初始化

(三)Logger的创建

(四)打印日志


本文源码基于:logback版本:1.2.11

在我们使用logback日志框架时,通常都会通过配置logback.xml定制化我们的日志需求。但你是否对loback日志如何加载配置感到好奇?如果没有logback.xml,logback的默认配置又是什么样的?配置文件中定义的appender和logger又是什么关系呢?在这一篇章我们会通过深入logback源码进行分析

(一)入口:slf4j选择日志框架

logback也是基于slf4j的一个日志框架实现。可以从maven的依赖中可以看到logback-classic依赖了slf4j-api。

 所以我们使用logback日志也是使用slf4j的接口:

private static final Logger logger = LoggerFactory.getLogger(LogTest.class);

而日志的配置加载就在首次调用LoggerFactory.getLogger时进行,具体是在LoggerFactory.getLogger-》getILoggerFactory():获取LoggerFactory时进行初始化,可以看到一个如下的performInitialization()方法。从名字可以看出这个方法就是去执行初始化的,而且使用状态位保证只初始化一次

我们接着看performInitialization方法中的bind方法:

我们知道slf4j只是定义了日志的接口,是一个日志接口协议。它将具体的日志框架实现交给各个日志框架,比如log4j2、logback等主流日志框架。这样在使用的时候,我们都是统一使用slf4j的接口,如果我们需要替换日志框架,那么只需要切换依赖,以及加上对应日志框架的配置日志就行。而之所以切换如此丝滑,就在于slf4j内部实现了日志框架实现的自动发现,即上图标红位置。

它的自动发现也很简单,只是去查找org/slf4j/impl/StaticLoggerBinder.class这个类,这个就是slf4j和具体实现框架的一个约定。如果我们想自己实现一个基于slf4j的日志框架实现,那么首先我们就得提供这么一个静态日志绑定类。

上面只是发现静态日志绑定类,如果有多个(可能同时引入了多个slf4的日志实现框架),那么会输出错误日志到控制台。并没有实际发生任何绑定动作。

实际的绑定动作是执行StaticLoggerBinder.getSingleton();

这里哪个日志框架的StaticLoggerBinder类被调用,就实际用哪个日志框架实现。

(二)日志框架初始化

上面已经讲了slf4j如何选择日志框架,最终取决于StaticLoggerBinder是哪个日志框架,这也是logback 初始化的入。接下来讲讲logback实际的初始化。

StaticLoggerBinder将绑定ILoggerFactory,使用单例模式,通过StaticLoggerBinder.getSingleton().getLoggerFactory()获取ILoggerFactory对象。它的初始化是在静态代码块中调用单例的初始化方法:SINGLETON.init();

它初始化了一个ContextInitializer,并传入StaticLoggerBinder中的默认LoggerContext,所有的初始化配置都是LoggerContext管理,实际上getLoggerFactory也是返回的此对象,所以它实际也是logger的工厂类。之后调用autoConfig,进行配置。我们重点看一下autoConfig:

(1)logback的3种配置方式

从上述代码可以看到3种配置方式的选择顺序:一个是通过获取配置文件,如果没有配置文件,那么就尝试加载SPI方式配置的Configurator实现类。如果也没有,那么会使用默认BasicConfigurator。三种配置都有两个关键步骤:

configurator.setContext(loggerContext);
configurator.doConfigure(loggerContext);

首先设置日志上下文,因为所有的配置都是围绕上下文的,所以它是配置器不可或缺的。第二步就是调用doConfigure,执行上下文执行实际的配置。

下面我们从简单到复杂一一介绍:

a、BasicConfigurator默认配置

默认配置很简单:

将ConsoleAppender附加到root logger,ConsoleAppender的layout设置为TTLLLayout,它等同于%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n"。所以它等同于使用如下配置文件:

<configuration><!-- Appenders --><appender name="CONSOLE" class="ch.qos.logback.core.ConsoleAppender"><encoder><pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n</pattern></encoder></appender><!-- Root Logger --><root><appender-ref ref="CONSOLE"/></root>
</configuration>

日志级别没有指定,默认是debug级别

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/64676.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

国产数据库OceanBase从入门到放弃教程

1. 介绍 是由蚂蚁集团&#xff08;Ant Group&#xff0c;原蚂蚁金服&#xff09;自主研发的分布式关系型数据库。它旨在解决海量数据存储和高并发访问的问题&#xff0c;特别适合金融级应用场景&#xff0c;如支付宝等对数据一致性、可靠性和性能有极高要求的服务。以下是关于…

连接Milvus

连接到Milvus 验证Milvus服务器正在侦听哪个本地端口。将容器名称替换为您自己的名称。 docker port milvus-standalone 19530/tcp docker port milvus-standalone 2379/tcp docker port milvus-standalone 192.168.1.242:9091/api/v1/health 使用浏览器访问连接地址htt…

机器学习中的欠拟合

当模型不能够准确地表达输入与输出的关系时&#xff0c;就是欠拟合。它在训练集和未见过的数据都会产生高误差率。过度拟合则在训练集表现出低误差率&#xff0c;只有对未见过的数据表现出高误差率。 当模型太过于简单时&#xff0c;它需要更多的训练时间、更多的输入特征、更…

安卓入门二 Kotlin基础

Kotlin Kotlin的历史 Kotlin由Jet Brains公司开发设计&#xff0c;2011年公布第一版&#xff0c;2012年开源。 2016年发布1.0正式版&#xff0c;并且Jet Brains在IDEA加入对Kotlin的支持&#xff0c;安卓自此又有新的选择。 2019年谷歌宣布Kotlin成为安卓第一开发语言&#x…

淺談Cocos2djs逆向

前言 簡單聊一下cocos2djs手遊的逆向&#xff0c;有任何相關想法歡迎和我討論^^ 一些概念 列出一些個人認為比較有用的概念&#xff1a; Cocos遊戲的兩大開發工具分別是CocosCreator和CocosStudio&#xff0c;區別是前者是cocos2djs專用的開發工具&#xff0c;後者則是coco…

STM32驱动NRF24L01

一、NRF24L01的相关介绍 1.2 引脚的介绍 关于SPI的引脚就不再说了&#xff0c;这里介绍其余的两个引脚&#xff1a; CE 模块控制引脚&#xff1a;芯片开启信号&#xff0c;激活RX或TX模式 IRQ 模块中断信号输出引脚&#xff1a;其低电平有效&#xff0c;也就是中断时变为低电平…

【Python】 glob批处理模块的学习

1.什么是glob模块&#xff1f; 在 Python 中&#xff0c;glob模块是一个用于文件路径名的模式匹配的工具。它使用简单的通配符规则来匹配文件和目录的路径&#xff0c;这些通配符规则类似于在命令行中使用的文件搜索规则。这使得在处理文件系统中的多个文件或目录时非常方便&am…

Android 系统 AlarmManager 系统层深度定制

Android 系统 AlarmManager 系统层深度定制 目录 引言AlarmManager 概述AlarmManager 系统架构AlarmManager 核心代码解读AlarmManager 深度定制方法 修改 AlarmManagerService 修改定时任务调度策略增加定时任务类型定制内核层 修改定时触发精度增加定时触发类型优化定时任务…

解决vue-i18n在非.vue文件中,在其他js文件中无法使用的问题

其实很简单&#xff0c;把i18n直接挂载到window上&#xff0c;全局可使用。下面请看详细。 一、安装 npm install vue-i18n9二、在vue的main.js中引入 import Vue from "vue" import VueI18n from vue-i18n Vue.use(VueI18n)//注入到所有的子组件&#xff0c;就是…

线性代数期末复习 [基础篇]

关于第六点: AXB 在期末考试中一般A都是可逆的 我们可以先把A的逆求出来,X A − 1 B A^-1B A−1B,或者 (A,B) -> r (E, A − 1 B A^-1B A−1B) 如果A矩阵不可逆,转变为方程组求解问题,假设都是二维矩阵 A(x1,x2) (b1,b2) Ax1 b1,Ax2 b2 XAB 如果A可逆,直接XB A − 1 A^-…

C++ —— 数据类型转换和数据类型的别名

数据类型转换 引言自动类型转换强制类型转换数据类型的别名 引言 计算机进行运算时&#xff0c;要求各操作数的数据类型、大小和存储方式都要相同。&#xff08;例如&#xff1a;8字节的整数和8字节的浮点数&#xff0c;虽然占用内存大小一样&#xff0c;但是存储方式不同&…

Kali 自动化换源脚本编写与使用

1. 背景与需求 在使用 Kali Linux 的过程中&#xff0c;软件源的配置对系统的更新与软件安装速度至关重要。 Kali 的默认官方源提供了安全且最新的软件包&#xff0c;但有时由于网络条件或地理位置的限制&#xff0c;使用官方源可能会出现速度较慢的问题。 为了解决这一问题&a…

设计模式-创建型-工厂方法模式

什么是工厂方法模式&#xff1f; 工厂方法模式&#xff08;Factory Method Pattern&#xff09;是 创建型设计模式之一&#xff0c;目的是通过定义一个用于创建对象的接口&#xff0c;让子类决定实例化哪个类。简而言之&#xff0c;工厂方法模式通过延迟对象的创建过程到子类来…

【Unity3D】ECS入门学习(十二)IJob、IJobFor、IJobParallelFor

IJob&#xff1a;开启单个线程进行计算&#xff0c;线程内不允许对同一个数据进行操作&#xff0c;也就是如果你想用多个IJob分别计算&#xff0c;将其结果存储到同一个NativeArray<int>数组是不允许的&#xff0c;所以不要这样做&#xff0c;如下例子就是反面教材&#…

Spring 创建和管理 Bean 的原理,以及Spring 的单例模式是否线程安全?(有无状态Bean)

Spring 是一个轻量级的开源框架&#xff0c;广泛应用于 Java 企业级应用的开发。它提供了一个全面的、基于 IOC&#xff08;控制反转&#xff09;和 AOP&#xff08;面向切面编程&#xff09;的容器&#xff0c;可以帮助开发者更好地管理应用程序中的对象。 Spring 创建和管理…

Docker容器镜像制作

Docker镜像的基本概念 1. 什么是Docker镜像&#xff1f; Docker镜像是一种轻量级、可执行的软件包&#xff0c;包含运行某个应用所需的所有代码、库、依赖项和配置文件。它的形成是一种“打包”和“快照”过程&#xff0c;使得应用能够在不同环境中保持一致的功能表现。 2. …

InfoNCE Loss详解(上)

引言 InfoNCE对比学习损失是学习句嵌入绕不开的知识点&#xff0c;本文就从头开始来探讨一下它是怎么来的。 先验知识 数学期望与大数定律 期望(expectation&#xff0c;expected value&#xff0c;数学期望&#xff0c;mathematical expectation)是随机变量的平均值&#…

.Net加密与Java互通

.Net加密与Java互通 文章目录 .Net加密与Java互通前言RSA生成私钥和公钥.net加密出数据传给Java端采用java方给出的公钥进行加密采用java方给出的私钥进行解密 .net 解密来自Java端的数据 AES带有向量的AES加密带有向量的AES解密无向量AES加密无向量AES解密 SM2(国密)SM2加密Sm…

工作中常用Vim的命令

Hi, 我是你们的老朋友&#xff0c;主要专注于嵌入式软件开发&#xff0c;有兴趣不要忘记点击关注【码思途远】 目录 0. ctags -R 1.认识 Vim的几种工作模式 2.高频使用命令 2.1 修改文件 2.2 关于行号 2.3 删除多行&#xff0c;删除部分 2.4 复制粘贴 2.5 光标移动 2.…

如何在 Vue 2 中使用 Swiper 5.4.5 处理静态与后端数据不能切换问题

一、文章大纲 1.前言 介绍 Swiper 作为一款强大的轮播组件,常用于处理图片、文章、商品等内容的滑动展示。 在 Vue.js 项目中集成 Swiper,尤其是在 Vue 2 中使用,常见的两种数据来源:静态数据与后端数据。 在 Vue 2 项目中集成 Swiper 5.4.5 2.如何通过 npm 安装 Swiper…