log4j2动态修改日志级别及拓展性使用详解

一、供参考的完整日志配置

<?xml version="1.0" encoding="UTF-8"?>

<!-- 配置LoggerConfig,即Appenders的日志级别为WARN -->
<Configuration status="WARN">

  <!-- 定义下面的引用名 -->
  <Properties>
    <property name="basePath">${sys:vmparam}</property>
    <property name="filePath">${basePath}/app.log</property>
  </Properties>

  <!-- Appenders支持配置多个Appender,支持向不同的目标输送日志,本例为配置向控制台输出 -->
  <Appenders>
    <Console name="Console" target="SYSTEM_OUT">
      <PatternLayout pattern="%d{HH:mm:ss.SSS} [%t] %-5level %logger{36} - %msg%n" />
    </Console>

    <!-- 将日志输出到指定位置的文件中 -->
    <RollingFile name="RollingFile" fileName="${filePath}"
      filePattern="logs/$${date:yyyy-MM}/app-%d{yyyy-MM-dd-HH}-%i.log.gz">
      <Policies>
        <!-- interval单位为filePattern最后一个单位,此处为6小时,modulate若为true,
        则日志时间将以0点为边界进行偏移计算,由于加了.gz策略,所以此处意思为每隔6小时,便会新生成一个
        log4j2的压缩文件,当每个文件超过250M时,也会新生成一个log4j2的压缩文件 -->
        <TimeBasedTriggeringPolicy interval="6" modulate="true"/>
        <SizeBasedTriggeringPolicy size="250 MB"/>
      </Policies>
      <!-- 滚动策略,日志文件最多保留20个 -->
      <DefaultRolloverStrategy max="20"/>

      <!-- 最多备份30天以内||日志文件大小达到100GB的日志||文件数量超过十个
      此处为策略限制,Delete中可以按自己需要用正则表达式编写 -->
      <DefaultRolloverStrategy>
        <Delete basePath="${filePath}" maxDepth="1">
          <IfFileName glob="logs_*.log" />
          <IfLastModified age="30d" />
          <IfAccumulatedFileSize exceeds="100 GB" />
          <IfAccumulatedFileCount exceeds="10" />
        </Delete>
      </DefaultRolloverStrategy>
    </RollingFile>
  </Appenders>

  <!-- Loggers支持配置多个Logger,可引用不同的目标Appender,也可根据业务需求定制特定要求的Appender -->
  <Loggers>

    <AsyncLogger name="AsyncLogger" level="trace">
      <appender-ref ref="Console" />
      <appender-ref ref="RollingFile" />
    </AsyncLogger>

    <asyncRoot level="trace">
      <appender-ref ref="Console" />
    </asyncRoot> 

    <Root level="info">
      <!-- <AppenderRef ref="Console" /> -->
      <AppenderRef ref="RollingFile" />
    </Root>

    <!-- 第三方日志系统 -->
    <logger name="org.springframework" level="INFO" additivity="false">
      <appender-ref ref="Console" />
    </logger>
    <logger name="io.netty" level="warn"/>
    <logger name="org.apache.http" level="warn"/>
    <logger name="org.mongodb.driver" level="INFO"/>
    <logger name="org.jboss.netty" level="warn"/>
    <logger name="org.springframework.data.redis" level="INFO"/>
  </Loggers>
</Configuration>

二、动态修改日志级别

Collection<org.apache.logging.log4j.core.Logger> current = LoggerContext.getContext(false).getLoggers();
Collection<org.apache.logging.log4j.core.Logger> notcurrent = LoggerContext.getContext().getLoggers();
Collection<org.apache.logging.log4j.core.Logger> allConfig = current;
allConfig.addAll(notcurrent);
for (org.apache.logging.log4j.core.Logger log:allConfig){
  log.setLevel(Level.DEBUG);
} 

三、自定义appender

以上介绍,均依赖于log4j2提供的官方配置,当对日志的业务逻辑复杂时,光靠配置也许满足不了需要,此时我们会想自己能操控打印的日志,做日志的路由,或保存等操作,这个时候就需要有自定义的appender,可以配置的就靠配置完成,不能的就自己写代码干预,而log4j2刚好提供了这样的拓展性。

如下代码即是自定义的Appender,通过实现AbstractAppender接口,配置@Plugin注解对应的信息并在eppend方法中写自己的业务逻辑,从而实现了对日志更大自由度的控制,如下展示的log4j配置文件中的配置节点名称要和注解中配置的name属性一致,并在Configuration节点配置好自定义Appender所在的包路径即可。

package com.jyk.log4j2.log4j2_test;

import java.io.Serializable;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReadWriteLock;
import java.util.concurrent.locks.ReentrantReadWriteLock;
import org.apache.logging.log4j.core.Filter;
import org.apache.logging.log4j.core.Layout;
import org.apache.logging.log4j.core.LogEvent;
import org.apache.logging.log4j.core.appender.AbstractAppender;
import org.apache.logging.log4j.core.appender.AppenderLoggingException;
import org.apache.logging.log4j.core.config.plugins.Plugin;
import org.apache.logging.log4j.core.config.plugins.PluginAttribute;
import org.apache.logging.log4j.core.config.plugins.PluginElement;
import org.apache.logging.log4j.core.config.plugins.PluginFactory;
import org.apache.logging.log4j.core.layout.PatternLayout;

@Plugin(name = "MyAppender", category = "Core", elementType = "appender", printObject = true)
public class MyAppender extends AbstractAppender {

  /**
   * @fields serialVersionUID
   */
  private static final long serialVersionUID = -830237775522429777L;
  private final ReadWriteLock rwLock = new ReentrantReadWriteLock();
  private final Lock readLock = rwLock.readLock();

  //需要实现的构造方法,直接使用父类就行
  protected MyAppender(final String name, final Filter filter, final Layout<? extends Serializable> layout,
      final boolean ignoreExceptions) {
    super(name, filter, layout, ignoreExceptions);
  }

  @Override
  public void append(LogEvent event) {
    readLock.lock();
    try {
      final byte[] bytes = getLayout().toByteArray(event);//日志二进制文件,输出到指定位置就行

      //拿到每次打印的日志,写自己的业务逻辑
      System.out.println("enter my append...");
    } catch (Exception ex) {
      if (!ignoreExceptions()) {
        throw new AppenderLoggingException(ex);
      }
    } finally {
      readLock.unlock();
    }
  }

  // 下面这个方法可以接收配置文件中的参数信息
  @PluginFactory
  public static MyAppender createAppender(@PluginAttribute("name") String name,
      @PluginElement("Filter") final Filter filter,
      @PluginElement("Layout") Layout<? extends Serializable> layout,
      @PluginAttribute("ignoreExceptions") boolean ignoreExceptions) {
    if (name == null) {
      LOGGER.error("No name provided for MyCustomAppenderImpl");
      return null;
    }
    if (layout == null) {
      layout = PatternLayout.createDefaultLayout();
    }
    return new MyAppender(name, filter, layout, ignoreExceptions);
  }
}
<Configuration status="WARN" packages="com.jyk.log4j2.log4j2_test">

<MyAppender name="textarea">
      <PatternLayout pattern="%d{HH:mm:ss.SSS} [%t] %-5level %logger{36} - %msg%n" />
</MyAppender>

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。

(0)

相关推荐

  • log4j2日志异步打印(实例讲解)

    log4j2支持日志的异步打印,日志异步输出的好处在于,使用单独的进程来执行日志打印的功能,可以提高日志执行效率,减少日志功能对正常业务的影响. 异步日志在程序的classpath需要加载disruptor-3.0.0.jar或者更高的版本. Asynchronous Loggers是一个新增特性在Log4j 2 ,可以实现完全异步也可以和同步混合使用,还可以只异步化Appender,以提升系统性能,官方数据显示混合没有完全异步化效果好. 1,完全异步模式: 这种异步日志方式,不需要修改原来的配

  • Spring 5.0集成log4j2日志管理的示例代码

    在使用Spring框架的时候,我们可以很方便的配置log4j来进行日志管理. Spring 5.0发布一段时间了,最近将项目从Spring 4.3升级到Spring 5.0,Spring 4.3集成log4j所用的类org.springframework.web.util.Log4jConfigListener在Spring 5.0版本已经删除,而且log4j 1.x版已经不再更新.我们将log4j-1.x升级为log4j-2.x 先引入log4j 2的三个jar包 log4j-api-2.10

  • log4j2 项目日志组件的实例代码

    在项目运行过程中,常常需要进行功能调试以及用户行为的跟踪和记录,部分人习惯使用System.out,但这并不建议,它仅仅是使用方便但不便于维护也无扩展性.相比log4j的话,log4j可以控制日志信息的输送目的地.输出格式以及级别等等,使我们能够更加细致地控制日志的生成过程. Log4j2是对Log4j1的升级,在性能和功能上有显著的改进,包括多线程中吞吐量的增强.占位符的支持.配置文件自动重新加载等 一.入门介绍 1.下载jar包 pox.xml <dependencies> <dep

  • spring boot自定义log4j2日志文件的实例讲解

    背景:因为从 spring boot 1.4开始的版本就要用log4j2 了,支持的格式有json和xml两种格式,此次实践主要使用的是xml的格式定义日志说明. spring boot 1.5.8.RELEASE 引入log4j2的开发步骤如下: 1.首先把spring-boot-starter-web以及spring-boot-starter包下面的spring-boot-starter-logging排除,然后引入spring-boot-starter-log4j2包. <dependen

  • log4j2动态修改日志级别及拓展性使用详解

    一.供参考的完整日志配置 <?xml version="1.0" encoding="UTF-8"?> <!-- 配置LoggerConfig,即Appenders的日志级别为WARN --> <Configuration status="WARN"> <!-- 定义下面的引用名 --> <Properties> <property name="basePath"

  • Logback动态修改日志级别的方法

    问题提出: 一般在生产环境上,日志的级别是INFO以上,但有时候程序出现问题(如SQL报错),少量日志不能尽快定位问题,这时候可以动态修改日志级别到DEBUG,打印更多日志后可以快速定位到问题. 解决方法: 定义动态修改日志级别的接口:这种方法的好处是不用修改配置文件,排错后再次调用接口把日志级别修改回去:坏处是需要在代码中写死指定哪些包要修改日志级别.示例代码如下: @RestController public class LogController { private static Logg

  • Spring Boot Admin 动态修改日志级别的方法步骤

    [前言] 之前关于线上输出日志一直有个困惑:如何可以动态调整的日志级别,来保证系统在正常运行时性能同时又能在出现问题时打印详细的信息来快速定位问题:最近研究一下Spring Boot Admin中动态日志级别调整,并集成项目中,在此与大家共享: [动态修改日志级别]          一.生产环境日志输出的状况 1.生产环境日志输出的困惑 A.设置日志输出级别为info: (1)优点:可以详细的打印日志,有利于排错: (2)缺点:日志消耗系统的性能较大:只能针对整个系统整体设置日志输出较多,定位

  • SpringBoot动态修改日志级别的操作

    前言 为了减少日志频繁打印带来的性能影响,线上环境设置的日志级别一般都相对较高.而当出现生产问题需要排查的时候,可能需要适当降低日志级别(例如DEBUG)来打印更多的日志信息帮助定位问题. 传统的做法一般是: 1.配置里修改日志级别 2.重启应用 3.问题复现查看报错日志排查问题 这个过程需要重启应用,比较麻烦,效率较低,而且针对大型在线项目,不可能随便停机重启.那么有没有一种方式在不重启应用的情况下实现动态修改日志级别呢? 下面,让老万教你如何通过SpringBoot的actuator组件来实

  • SpringBoot如何动态改变日志级别

    前言 关于日志级别,大部分项目可能都设置为info级别,当然也可能有一些追求性能或者说包含很多敏感信息的项目直接将级别设置为warn或者error:这时候如果项目中出现一些未知异常,需要用到很详细的日志信息,此时如果项目中没有动态改变日志级别的机制,排查问题将很棘手. 日志系统 我们常用的一些日志系统包括:Log4j2.Logback.Java Util Logging:我们想动态改变日志的级别,前提是这些日志系统都支持我们直接设置日志等级,当然这些系统提供了很简单的接口: Log4j2 Log

  • springboot动态调整日志级别的操作大全

    1.springboot使用log4j2 springboot使用的common-logging,底层兼容各种日志框架如,log4j2,slf4,logback等,默认底层使用的是logback,我们可以去除logback的依赖,引入log4j2的starter, 如下: 2.指定日志配置文件和日志等级 (此配置不限于log4j2,也适用于其他日志框架) 在resources目录下加入log4j2的xml配置文件,默认spring-boot会加载classpath下面的名为log4j2.xml,

  • Java使用arthas修改日志级别详解

    目录 arthas能够更改日志的级别,下面是logger的用法 查看logger信息,更新logger level 查看所有logger信息 logger 以下面的logback.xml为例: <?xml version="1.0" encoding="UTF-8"?><configuration> <appender name="APPLICATION" class="ch.qos.logback.cor

  • jQuery动态添加.active 实现导航效果代码思路详解

     代码思路: 页面4: 页面5: 代码思路: 通过jq获取你打开页面的链接  window.location.pathname: 在HTML中给自己的li加入一个ID id的命名与网址链接中的href相同 通过jq包含方法找到相对应的li给他加入active类名 然后..就没有然后了... jq代码: $(function () { var li = $(".title_ul").children("li"); for (var i = 0; i < li.l

  • 对python修改xml文件的节点值方法详解

    这是我的xml文件结构 <?xml version='1.0' encoding='utf-8'?> <annotation> <folder>JPEGImages</folder> <filename>train_2018-05-08_1000.jpg</filename> <path>D:\all_data\2018-05-08\JPEGImages\train_2018-05-08_1000.jpg</path

  • python修改文件内容的3种方法详解

    这篇文章主要介绍了python修改文件内容的3种方法详解,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下 一.修改原文件方式 def alter(file,old_str,new_str): """ 替换文件中的字符串 :param file:文件名 :param old_str:就字符串 :param new_str:新字符串 :return: """ file_data = "&qu

随机推荐