SLF4J自定义绑定不起作用

时间:2012-01-14 16:57:10

标签: java eclipse classpath slf4j

我们花了很多时间开发自己的自定义日志记录系统(对或错,这就是高层决定的!)并且我被要求编写自定义SLF4J绑定(API实现)以便我们的许多人利用SLF4J的组件(例如Apache Camel)将开始登录我们新的本土系统。

我已按照SLF4J网站上的说明操作“T”,创建:

  • SLF4J在运行时使用StaticLoggerBinder绑定到LoggersLoggerFactory
  • 用于“转发”org.slf4j.Logger来电
  • 的记录器适配器
  • 记录器工厂(由静态记录器活页夹使用)

一切都很好。我将它装箱并将其添加到测试项目的lib目录中,以及slf4j-api-1.6.2.jar(他们希望我使用的版本)。我在Eclipse中的构建路径中添加了两个JAR。

我为测试项目创建了一个新的运行配置,在运行配置的Classpath选项卡式窗格下,我看到它有User Entries >> TestBinding >> Slf4jBinding.jar and slf4j-api-1.6.2.jar

因此,似乎两个JAR都在Run Configuration的类路径中。

在项目中运行如下所示的驱动程序:

public static void main(String[] args) {
    Logger logger = LoggerFactory.getLogger(TestDriver.class);
    logger.error("Test");
}

我收到以下运行时错误:

  

SLF4J:无法加载类“org.slf4j.impl.StaticLoggerBinder”。   SLF4J:默认为无操作(NOP)记录器实现   SLF4J:有关详细信息,请参阅http://www.slf4j.org/codes.html#StaticLoggerBinder

转到该引用的网站,似乎SLF4J在StaticLoggerBinder内的类路径上找不到我的Slf4jBinding.jar,但不在JAR的根级别。

我查看了SLF4J的LoggerFactory.java源文件,发现了抛出此类错误的代码:

private final static void bind() {
    try {
        // the next line does the binding
        StaticLoggerBinder.getSingleton();
        INITIALIZATION_STATE = SUCCESSFUL_INITILIZATION;
        emitSubstituteLoggerWarning();
    } catch (NoClassDefFoundError ncde) {
        String msg = ncde.getMessage();
        if (messageContainsOrgSlf4jImplStaticLoggerBinder(msg)) {
            INITIALIZATION_STATE = NOP_FALLBACK_INITILIZATION;
            Util
            .report("Failed to load class \"org.slf4j.impl.StaticLoggerBinder\".");
            Util.report("Defaulting to no-operation (NOP) logger implementation");
            Util.report("See " + NO_STATICLOGGERBINDER_URL
            + " for further details.");
        } // ...

显然,try块(StaticLoggerBinder.getSingleton())顶部的调用会抛出NoClassDefFoundError。我只是不明白为什么。

我选择不在此处粘贴代码,因为我认为这只是一个类路径问题。在我能够通过此问题之前,我的代码是否正确遵守SLF4J的绑定策略仍然未知。

在Eclipse中需要采取额外的步骤来配置类路径吗?出于某种原因,我的Slf4jBinding.jar根本需要StaticLoggerBinder吗?我在这里没有想法。提前谢谢!

3 个答案:

答案 0 :(得分:5)

您的jar需要org.slf4j.impl.StaticLoggerBinder的自定义实现,并且该实现的完全限定类名必须是org.slf4j.impl.StaticLoggerBinder。静态绑定使用针对存根版本org.slf4j.impl.StaticLoggerBinder编译的SLF4J API,然后在运行时,类加载器将从SLF4J绑定加载实际版本。 SLF4J的每个绑定都具有适合该特定绑定的类org.slf4j.impl.StaticLoggerBinder的不同版本。

答案 1 :(得分:4)

而不是完全从头开始然后只是适应,例如slf4j-simple.jar满足您的需求。所有绑定代码都在那里,你只需要调整代码进行实际的日志记录。

答案 2 :(得分:0)

您可以在项目中创建一个org.slf4j.impl包,并在该包中实现一个名为StaticLoggerBinder的类,就像在http://javaeenotes.blogspot.com/2011/12/custom-slf4j-logger-adapter.html上所解释的那样(我只是这样做,它对我来说很好)。

请注意,您不需要为此构建jar文件,只需要在类路径中访问org.slf4j.impl.StaticLoggerBinder类(它可以在jar中但不是必需的)。< / p>