java - Log4j、Tapestry 5.1、独立 Jetty 6 不兼容?

标签 java log4j jetty maven tapestry

到目前为止,我一直在使用 Maven 目标来开发 Tapestry 5.1.0.5 Web 应用程序来编译/打包/执行应用程序。我使用 mvn jetty:run 目标来运行 Jetty maven 插件。这总是运作良好。看来Maven使用的是Jetty 6.1.9。

我现在需要设置一个不使用 Maven 目标执行的生产环境。我认为 Jetty 看起来很简单,而且它已经可以与 Maven 配合使用了。我得到了 6.1.26(后来也尝试了 6.1.9,但没有成功),将我的应用程序 WAR 文件放入 webapp 目录中,然后尝试运行它......没有运气。

每次我收到此错误时,都不会改变:

2010-11-17 18:33:13.436:WARN::Error starting handlers
java.lang.NoClassDefFoundError: org/apache/log4j/Level
at org.slf4j.LoggerFactory.getSingleton(LoggerFactory.java:228)
at org.slf4j.LoggerFactory.bind(LoggerFactory.java:120)
at org.slf4j.LoggerFactory.performInitialization(LoggerFactory.java:111)
at org.slf4j.LoggerFactory.getILoggerFactory(LoggerFactory.java:269)
at org.slf4j.LoggerFactory.getLogger(LoggerFactory.java:242)
at org.slf4j.LoggerFactory.getLogger(LoggerFactory.java:255)
at org.apache.tapestry5.TapestryFilter.<init>(TapestryFilter.java:45)
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at    sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:39)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:27)
at java.lang.reflect.Constructor.newInstance(Constructor.java:513)
at java.lang.Class.newInstance0(Class.java:355)
at java.lang.Class.newInstance(Class.java:308)
at org.mortbay.jetty.servlet.Holder.newInstance(Holder.java:153)
at org.mortbay.jetty.servlet.FilterHolder.doStart(FilterHolder.java:92)
at org.mortbay.component.AbstractLifeCycle.start(AbstractLifeCycle.java:50)
at org.mortbay.jetty.servlet.ServletHandler.initialize(ServletHandler.java:713)
at org.mortbay.jetty.servlet.Context.startContext(Context.java:140)
at org.mortbay.jetty.webapp.WebAppContext.startContext(WebAppContext.java:1282)
at org.mortbay.jetty.handler.ContextHandler.doStart(ContextHandler.java:518)
at org.mortbay.jetty.webapp.WebAppContext.doStart(WebAppContext.java:499)
at org.mortbay.component.AbstractLifeCycle.start(AbstractLifeCycle.java:50)
at org.mortbay.jetty.handler.HandlerCollection.doStart(HandlerCollection.java:152)
at org.mortbay.jetty.handler.ContextHandlerCollection.doStart(ContextHandlerCollection.java:156)
at org.mortbay.component.AbstractLifeCycle.start(AbstractLifeCycle.java:50)
at org.mortbay.jetty.handler.HandlerCollection.doStart(HandlerCollection.java:152)
at org.mortbay.component.AbstractLifeCycle.start(AbstractLifeCycle.java:50)
at org.mortbay.jetty.handler.HandlerWrapper.doStart(HandlerWrapper.java:130)
at org.mortbay.jetty.Server.doStart(Server.java:224)
at org.mortbay.component.AbstractLifeCycle.start(AbstractLifeCycle.java:50)
at org.mortbay.xml.XmlConfiguration.main(XmlConfiguration.java:985)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.mortbay.start.Main.invokeMain(Main.java:194)
at org.mortbay.start.Main.start(Main.java:534)
at org.mortbay.start.Main.start(Main.java:441)
at org.mortbay.start.Main.main(Main.java:119)

我最初使用 Log4J 1.2.8 作为整个应用程序的手动依赖项的一部分。我读了这个网站http://tapestry.apache.org/tapestry5.1/jetty.html然后意识到我应该使用 1.2.12 或更高版本作为 TRACE 级别。首先,我将依赖项更新为 LOG4J 1.2.16。这不起作用。

然后我做了一些进一步的阅读,表明 apache-commons-logging 依赖项可能会由于其工作原理而导致整体日志记录问题。我检查了整个依赖层次结构,并从所有内容中排除了 apache-commons-logging。此时该应用程序仍然可以与 Maven jetty 插件一起使用,所以我这样做并没有破坏任何东西。但是当我部署 WAR 时,我仍然遇到异常,所以这不是解决方案。

下一步我意识到 Tapestry-ioc 依赖性在我的系统端 log4j 和它想要的 log4j 版本之间存在冲突。看起来它使用的是log4j 1.2.13,而依赖项中的slf4j本身使用的是编译Log4J 1.2.14。

我首先将系统依赖项更新为 1.2.14(因为 Tapestry 中的 slf4j 发生此错误),然后在 1.2.13 再次失败时。这两种情况都没有成功。

我听说过要确保 Jetty 不会使用它用于自己日志记录的较低版本覆盖您的 Log4J。然而,在 Jetty 文件中我找不到任何 log4j 依赖项。

最佳答案

我猜一下:

这“可能”是由于

  1. 当 Maven 下载 log4j 依赖项时,它失败或已损坏 - 尝试删除 Maven 存储库中的 log4j 目录(Windows:docs and settings/user/.m2/....)

  2. 存在某种依赖冲突,maven 正在通过不包含任何一个来解决它,这很糟糕 - 这不太可能,我认为它会包含最新版本

  3. 其他一些 Maven 插件或配置导致 log4j jar 被排除在 WAR 创建之外(废话)

不知道还有什么可能导致这个......

编辑评论:

啊是的,既然你提到了,我就有这个问题了!我有几个“ self 管理”(即不是 Maven 管理)jar,据我所知,将它们包含在 Maven 类路径中的唯一方法是给它们一个 system范围。你的问题变成:“我如何在 Maven 构建中包含非 Maven jar ?”

scope 的文档元素:

The scope of the dependency - compile, runtime, test, system, and provided. Used to calculate the various classpaths used for compilation, testing, and so on. It also assists in determining which artifacts to include in a distribution of this project. For more information, see the dependency mechanism.

如果您使用 systemPath 更改条目的范围,您也会在 pom 中遇到错误:

only dependency with system scope can specify systemPath.

编辑2:找到了一个很好的解决方案...

我发现this 'issue' report ,并按照最后一条评论建议的路径进行操作:

We won't do this. I guess that you might add a webresource section with an include for the files you want and a targetPath.

Here's the documentation regarding the mechanism.

所以你需要做的是:

<build>
...
    <plugins>
...

        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-war-plugin</artifactId>
            <version>2.1.1</version>
            <configuration>
                <webResources>
                    <resource>
                        <directory>unmanaged-lib</directory>
                        <targetPath>WEB-INF/lib</targetPath>
                        <includes>
                            <include>**/*.jar</include>
                        </includes>
                    </resource>
                </webResources>
            </configuration>
        </plugin>

...
    <plugins>
...
<build>

注意:在本例中,路径“unmanagement-lib”是项目根目录中的一个目录(即与 pom.xml 相同的级别)

关于java - Log4j、Tapestry 5.1、独立 Jetty 6 不兼容?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4208343/

相关文章:

java - 如何对自定义 RecordReader 和 InputFormat 类进行单元测试?

java - 如何重构内部类MouseAdapter?

Java 在 ubuntu 10.04 上的 log4j 中使用错误的时间/日期

java - 手动轮换 log4j 日志文件

jetty - 对于类似 etherpad 的应用程序,node.js 与 jetty 相比如何?

java - 禁用 Spring Boot Web 客户端日志

java - 良好的面向对象设计

java - 将位于同一包层次结构下的 2 个类的日志消息打印到 2 个不同的文件

java - 如何使用 Jetty 为 servlet 提供服务而不必担心 War 文件布局?

java - 动态配置spring的集成int-http :inbound-gateway