我们花了很多时间开发我们自己的自定义日志记录系统(对与错,这是上级决定的!),我被要求编写一个自定义SLF4J绑定(API实现),这样我们的许多使用SLF4J的组件(如Apache Camel)将开始记录到我们新的国产系统。
我已经按照SLF4J网站上的说明创建了一个"T",创建:
- SLF4J在运行时用于绑定到
Loggers
和LoggerFactory
类的StaticLoggerBinder
- 将用于将
org.slf4j.Logger
调用"转发"到的记录器适配器 - 记录器工厂(由静态记录器绑定器使用)
一切都很好。我将其jar起来,并将其与slf4j-api-1.6.2.jar
(他们希望我使用的版本)一起添加到测试项目的lib
目录中。我在Eclipse中将这两个JAR都添加到了构建路径中。
我为测试项目创建了一个新的Run Configuration,在Run Configuration的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
吗?我在这里没有主意。提前感谢!
您的jar需要org.slf4j.impl.StaticLoggerBinder
的自定义实现,并且该实现的完全限定类名必须恰好是org.slf4j.impl.StaticLoggerBinder
。静态绑定使SLF4J API针对org.slf4j.impl.StaticLoggerBinder
的存根版本进行编译,然后在运行时类加载器将从SLF4J绑定加载实际版本。SLF4J的每个绑定具有适用于该特定绑定的类别org.slf4j.impl.StaticLoggerBinder
的不同版本。
与其完全从头开始,不如根据您的需要调整例如slf4j-simple.jar。所有的绑定代码都在那里,您只需要调整代码来进行实际的日志记录。
您可以在项目中创建org.slf4j.impl包,并在该包中实现名为StaticLoggerBinder的类,就像在http://javaeenotes.blogspot.com/2011/12/custom-slf4j-logger-adapter.html(我刚刚这么做了,对我来说效果很好)。
请注意,您不需要为此构建一个jar文件,只需要在类路径中有一个可访问的org.slf4j.impl.StaticLoggerBinder类(它可以在jar中,但这不是强制性的)。