【问题标题】:How do I set log4j level on the command line?如何在命令行上设置 log4j 级别?
【发布时间】:2011-10-30 21:37:04
【问题描述】:

我想将一些 log.debug 语句添加到我正在处理的类中,并且我希望在运行测试时在输出中看到它。我想在命令行上覆盖 log4j 属性,如下所示:

-Dlog4j.logger.com.mypackage.Thingie=DEBUG

我经常做这种事情。我只对在命令行上传递它的方法感兴趣。我知道如何使用配置文件来做到这一点,但这不适合我的工作流程。

【问题讨论】:

    标签: java log4j


    【解决方案1】:

    作为 jvm 参数的一部分,您可以设置 -Dlog4j.configuration=file:"<FILE_PATH>"。其中 FILE_PATH 是 log4j.properties 文件的路径。

    请注意,从log4j2 开始,要使用的新系统变量是log4j.configurationFile,并且您输入文件的实际路径(即不带file: 前缀),它将根据配置文件的扩展名:

    -Dlog4j.configurationFile=/path/to/log4jconfig.{ext}
    

    【讨论】:

    • FILE_PATH 实际上是在 CLASSPATH 上搜索的,包括里面的 jar 文件。
    • 如果是磁盘上的文件,需要在路径前加上“file:”。换句话说... -Dlog4j.configuration=file:stackoverflow.com/questions/778933/…
    • 这和宣传的一样;但是我试图覆盖 jar 中的属性文件的设置,而后者似乎是在之后设置的。有什么建议吗?
    【解决方案2】:

    这些答案实际上阻止了我尝试最简单的事情!只需在 log4j.configuration 中为附加程序(例如“控制台”)指定一个阈值,如下所示:

    log4j.appender.console.threshold=${my.logging.threshold}
    

    然后,在命令行中包含系统属性-Dlog4j.info -Dmy.logging.threshold=INFO。我假设任何其他属性都可以通过这种方式进行参数化,但这是全局提高或降低日志记录级别的最简单方法。

    【讨论】:

    • 我很确定这是原始问题的最简单解决方案!
    • @Droj 也许是这样,但 OP 想在代码中完成这一切。查村儿子痛风。
    • 就我而言,我也想从命令行设置它,但我已经有了一个配置。我只是不想编辑文件以获得不同的日志记录。我没有把它读成“全部在代码中”,但也许是这样......
    • 只是一个小改进:yaml Loggers:\n Logger:\n name: stuff \n level: ${sys:my.log.level:-INFO}
    • 我喜欢上面的 YAML,但是 IIRC Spring 不会对 YAML 做变量插值。
    【解决方案3】:

    使用 Log4j2,这可以通过添加到您的代码中的以下实用方法来实现。

    private static void setLogLevel() {
      if (Boolean.getBoolean("log4j.debug")) {
        Configurator.setLevel(System.getProperty("log4j.logger"), Level.DEBUG);
      }
    }
    

    你需要这些导入

    import org.apache.logging.log4j.Level;
    import org.apache.logging.log4j.core.config.Configurator;
    

    现在在 main() 或任何适当的地方调用 setLogLevel 方法,并传递命令行参数 -Dlog4j.logger=com.mypackage.Thingie-Dlog4j.debug=true

    【讨论】:

    • 既然软件包已更新,这应该是公认的答案。感谢您提供更新的答案——当涉及到长期存在的问题时,我非常感谢更新的答案。你救了我不少挫折。
    【解决方案4】:

    log4j 不直接支持这个。

    由于您不需要配置文件,因此您很可能使用编程配置。我建议您考虑扫描所有系统属性,并在此基础上明确编程您想要的内容。

    【讨论】:

      【解决方案5】:

      根据 Thorbjørn Ravn Andersens 的建议,我编写了一些代码来完成这项工作

      在 main 方法的早期添加以下内容,现在可以从命令行设置日志级别。这已经在我的一个项目中进行了测试,但我是 log4j 的新手,可能犯了一些错误。如果有请指正。

          Logger.getRootLogger().setLevel(Level.WARN);
          HashMap<String,Level> logLevels=new HashMap<String,Level>();
          logLevels.put("ALL",Level.ALL);
          logLevels.put("TRACE",Level.TRACE);
          logLevels.put("DEBUG",Level.DEBUG);
          logLevels.put("INFO",Level.INFO);
          logLevels.put("WARN",Level.WARN);
          logLevels.put("ERROR",Level.ERROR);
          logLevels.put("FATAL",Level.FATAL);
          logLevels.put("OFF",Level.OFF);
          for(String name:System.getProperties().stringPropertyNames()){
              String logger="log4j.logger.";
              if(name.startsWith(logger)){
                  String loggerName=name.substring(logger.length());
                  String loggerValue=System.getProperty(name);
                  if(logLevels.containsKey(loggerValue))
                      Logger.getLogger(loggerName).setLevel(logLevels.get(loggerValue));
                  else
                      Logger.getRootLogger().warn("unknown log4j logg level on comand line: "+loggerValue);
              }
          }
      

      【讨论】:

        【解决方案6】:

        在我相当标准的设置中,当作为 VM 选项(Java 中的类之前的命令行,或 IDE 中的 VM 选项)传入时,我已经看到以下工作正常:

        -Droot.log.level=TRACE
        

        【讨论】:

          【解决方案7】:

          基于@lijat,这是一个简化的实现。在我基于 spring 的应用程序中,我只是将它作为 bean 加载。

          public static void configureLog4jFromSystemProperties()
          {
            final String LOGGER_PREFIX = "log4j.logger.";
          
            for(String propertyName : System.getProperties().stringPropertyNames())
            {
              if (propertyName.startsWith(LOGGER_PREFIX)) {
                String loggerName = propertyName.substring(LOGGER_PREFIX.length());
                String levelName = System.getProperty(propertyName, "");
                Level level = Level.toLevel(levelName); // defaults to DEBUG
                if (!"".equals(levelName) && !levelName.toUpperCase().equals(level.toString())) {
                  logger.error("Skipping unrecognized log4j log level " + levelName + ": -D" + propertyName + "=" + levelName);
                  continue;
                }
                logger.info("Setting " + loggerName + " => " + level.toString());
                Logger.getLogger(loggerName).setLevel(level);
              }
            }
          }
          

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2019-11-21
            • 1970-01-01
            相关资源
            最近更新 更多