Java 使用jdk logging/slf4j更改日志级别本地化名称

Java 使用jdk logging/slf4j更改日志级别本地化名称,java,logging,localization,slf4j,Java,Logging,Localization,Slf4j,我看到使用jdk日志记录的日志记录级别是本地化的,运行以下示例: package com.stackoverflow.tests.logging; import java.util.Locale; import java.util.logging.Logger; public class TestLogging { public static void doLog(Locale l) { Locale.setDefault(l); Logg

我看到使用jdk日志记录的日志记录级别是本地化的,运行以下示例:

package com.stackoverflow.tests.logging;

import java.util.Locale;
import java.util.logging.Logger;

public class TestLogging
{

    public static void doLog(Locale l)
    {
        Locale.setDefault(l);

        Logger logger = Logger.getLogger(TestLogging.class.getName());

        final String msg = "Hello logging world";
        logger.severe(msg);
        logger.info(msg);
        logger.config(msg);
        logger.fine(msg);
        logger.finer(msg);
        logger.finest(msg);

    }

    public static void main(String args[])
    {

        doLog(Locale.ITALY);

    //  doLog(Locale.UK);

    //  doLog(Locale.FRANCE);

    }
}
意大利语输出(使用默认记录器配置,因此只记录严重级别和信息级别)

我想为日志记录级别设置自定义本地化消息,而不是默认提供的消息

我该怎么做

  • 直接使用JDK日志记录(我看到
    Logger.getLogger
    可以使用ResourceBundle,但我没有设法让它工作,而且我不知道这个文件中应该包含什么)
  • 使用SLF4 facade(我想这意味着要调整SLF4J的
    LoggerFactory.getLogger
    函数,这是我用来获取记录器的函数)

  • 根据一些测试,JDK日志似乎不可能做到这一点

    传递给
    记录器
    的资源束名称不会影响创建本地化名称的
    级别
    对象。相反,它使用默认的资源包(
    sun.util.logging.resources.logging
    )来获取该级别的文本版本

    我的测试包含一个名为
    logmessages.properties
    的文件,其中包含:

    INFO="NEWINFO"
    testmessage="fooballs"
    
    还有一个简单的类:

    import java.util.logging.Logger;
    
    public class LocaleLoggingTest {
    
      public static void main(String[] args) throws Exception {
        Logger logger = Logger.getLogger("name", "logmessages");
        logger.info("testmessage");
      }
    }
    
    输出:

    Dec 15, 2014 10:23:39 AM LocaleLoggingTest main
    INFO: "fooballs"
    

    如果您进行调试,当您到达
    java.util.logging.SimpleFormatter.format(LogRecord)
    时,日志记录有一个
    级别的
    对象和一个默认的资源包。令人沮丧的是,呃?

    java.util.logging
    中,您可以使用不同的捆绑包名称定义自己的级别,或者根本不定义。方法是将
    java.util.logging.Level
    子类化并添加自己的常量。例如,如果需要非本地化名称,可以按如下方式创建标高:

    public class Level extends java.util.logging.Level {
        private static final long serialVersionUID = -1283674772992561191L;
    
        public static final Level OFF = new Level("OFF", Integer.MAX_VALUE);
        public static final Level SEVERE = new Level("SEVERE", 1000);
        public static final Level WARNING = new Level("WARNING", 900);
        public static final Level INFO = new Level("INFO", 800);
        public static final Level CONFIG = new Level("CONFIG", 700);
        public static final Level FINE = new Level("FINE", 500);
        public static final Level FINER = new Level("FINER", 400);
        public static final Level FINEST = new Level("FINEST", 300);
        public static final Level ALL = new Level("ALL", Integer.MIN_VALUE);
    
        protected Level(String name, int value) {
            super(name, value);
        }
    }
    
    如果要使用其他捆绑包名称,请执行以下操作:

    public class Level extends java.util.logging.Level {
        private static final long serialVersionUID = -1283674772992561191L;
    
        static final String my_bundle_name = "my.bundle.name";
    
        public static final Level OFF = new Level("OFF", Integer.MAX_VALUE, my_bundle_name);
        public static final Level SEVERE = new Level("SEVERE", 1000, my_bundle_name);
        public static final Level WARNING = new Level("WARNING", 900, my_bundle_name);
        public static final Level INFO = new Level("INFO", 800, my_bundle_name);
        public static final Level CONFIG = new Level("CONFIG", 700, my_bundle_name);
        public static final Level FINE = new Level("FINE", 500, my_bundle_name);
        public static final Level FINER = new Level("FINER", 400, my_bundle_name);
        public static final Level FINEST = new Level("FINEST", 300, my_bundle_name);
        public static final Level ALL = new Level("ALL", Integer.MIN_VALUE, my_bundle_name);
    
        protected Level(String name, int value, String resourceBundleName) {
            super(name, value, resourceBundleName);
        }
    }
    
    当然,您必须使用自定义级别而不是默认级别,因此必须使用诸如
    Logger.log(Level-Level,String-msg)
    之类的调用,在这些调用中,您可以明确指定级别,而不是始终使用默认级别的
    Logger.info(String-msg)

    编辑:我是从你那里得到这个主意的

    public class Level extends java.util.logging.Level {
        private static final long serialVersionUID = -1283674772992561191L;
    
        static final String my_bundle_name = "my.bundle.name";
    
        public static final Level OFF = new Level("OFF", Integer.MAX_VALUE, my_bundle_name);
        public static final Level SEVERE = new Level("SEVERE", 1000, my_bundle_name);
        public static final Level WARNING = new Level("WARNING", 900, my_bundle_name);
        public static final Level INFO = new Level("INFO", 800, my_bundle_name);
        public static final Level CONFIG = new Level("CONFIG", 700, my_bundle_name);
        public static final Level FINE = new Level("FINE", 500, my_bundle_name);
        public static final Level FINER = new Level("FINER", 400, my_bundle_name);
        public static final Level FINEST = new Level("FINEST", 300, my_bundle_name);
        public static final Level ALL = new Level("ALL", Integer.MIN_VALUE, my_bundle_name);
    
        protected Level(String name, int value, String resourceBundleName) {
            super(name, value, resourceBundleName);
        }
    }