【问题标题】:Exception: could not find Factory: javax.faces.context.FacesContextFactory异常:找不到工厂:javax.faces.context.FacesContextFactory
【发布时间】:2011-03-10 11:39:07
【问题描述】:

我正在从 JBoss 5.1.0.GA 迁移到 JBoss 6.0.0-Final 并在 FacesServler 初始化期间遇到以下异常

2011-03-09 18:07:24,574 ERROR [org.apache.catalina.core.ContainerBase.[jboss.web].[localhost].[/].[Faces Servlet]] (http-0.0.0.0-8080-4) Allocate exception for servlet Faces Servlet: java.lang.IllegalStateException: Application was not properly initialized at startup, could not find Factory: javax.faces.context.FacesContextFactory
    at javax.faces.FactoryFinder$FactoryManager.getFactory(FactoryFinder.java:725) [:1.2_15-20100816-SNAPSHOT]
    at javax.faces.FactoryFinder.getFactory(FactoryFinder.java:239) [:1.2_15-20100816-SNAPSHOT]
    at javax.faces.webapp.FacesServlet.init(FacesServlet.java:164) [:1.2_15-20100816-SNAPSHOT]
    at org.apache.catalina.core.StandardWrapper.loadServlet(StandardWrapper.java:1208) [:6.0.0.Final]
    at org.apache.catalina.core.StandardWrapper.allocate(StandardWrapper.java:955) [:6.0.0.Final]
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:188) [:6.0.0.Final]
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191) [:6.0.0.Final]
    at org.jboss.web.tomcat.security.SecurityAssociationValve.invoke(SecurityAssociationValve.java:181) [:6.0.0.Final]
    at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:501) [:6.0.0.Final]
    at org.jboss.web.tomcat.security.JaccContextValve.invoke(JaccContextValve.java:88) [:6.0.0.Final]
    at org.jboss.web.tomcat.security.SecurityContextEstablishmentValve.invoke(SecurityContextEstablishmentValve.java:100) [:6.0.0.Final]
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127) [:6.0.0.Final]
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102) [:6.0.0.Final]
    at org.jboss.web.tomcat.service.jca.CachedConnectionValve.invoke(CachedConnectionValve.java:158) [:6.0.0.Final]
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109) [:6.0.0.Final]
    at org.jboss.web.tomcat.service.request.ActiveRequestResponseCacheValve.invoke(ActiveRequestResponseCacheValve.java:53) [:6.0.0.Final]
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:362) [:6.0.0.Final]
    at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:877) [:6.0.0.Final]
    at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:654) [:6.0.0.Final]
    at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:951) [:6.0.0.Final]
    at java.lang.Thread.run(Thread.java:619) [:1.6.0_14]

我查看了代码,发现 FactoryFinder 根据当前线程类加载器查找相应的 FactoryManager。我还发现我的 FactoryFinder.FACTORIES_CACHE 包含两个类加载器的两个条目:

* BaseClassLoader which loads my EAR and
* WebCtxLoader.ENCLoader which is used during web app running and which was current context classloaded for failed thread.

我的部署结构如下:

* deploy
      o myapplication.ear
            + lib
                  # richfaces jars (3.3.1.GA)
                  # seam jars (2.2.1.Final)
                  # openfaces jar (2.0.0)
                  # other jars
            + META-INF
                  # jboss-app.xml
                  # application.xml
            + myapplication.war
                  # WEB-INF
                        * web.xml
                        * faces-config.xml
                        * components.xml
* deployers
      o jbossweb.deployer
      o jsf.deployer
      o and others

我使用 Mojarra-1.2 作为 JSF 实现

    <param-name>org.jboss.jbossfaces.JSF_CONFIG_NAME</param-name>

    <param-value>Mojarra-1.2</param-value>

经过一些调试,我可以总结一下:

     1. all JSF initialization is made in BaseClassLoader thread, i.e. when javax.faces.FactoryFinder#setFactory(..) is invoked getClassLoader() returns EAR BaseClassLoader
     2. A servlet thread (which cause exception) tries to look FactoryManager but his current classloader ( Thread.currentThread().getContextClassLoader()) is WebCtxLoader.ENCLoader. So nothing is returned and exception is thrown.

我检查了 JBoss 5.1.0 并确保 FactoryManager 的初始化和访问是在具有相同类加载器的线程中进行的。

我尝试用谷歌搜索,但没有找到很多关于任何人有同样问题的信息 - 这让我觉得我的环境有问题。

有人可以对此发表评论或提供帮助吗?

【问题讨论】:

    标签: jsf jboss6.x


    【解决方案1】:

    这是类路径污染的标志。 JBoss 已经捆绑了 JSF。如果您也将 JSF 捆绑到 WAR 中,则可能会发生此异常。它只会碰撞。

    有两种解决方案:

    1. 在您的 WAR 中删除 jsf-apijsf-impl JAR(即它们不应在构建/部署后以 /WEB-INF/lib 结尾。

    2. 告诉 JBoss 你的 WAR 附带了它自己的 JSF 版本,这样 JBoss 就不会使用它自己的了。

      <context-param>
          <param-name>org.jboss.jbossfaces.WAR_BUNDLES_JSF_IMPL</param-name>
          <param-value>true</param-value>
      </context-param>
      

    【讨论】:

    • 感谢您的评论。我知道 JBoss 6.0.0 附带 JSF 部署程序,这就是我没有将 jsf-api 和 jsf-impl jar 包含到我的战争中的原因(就像我在 JBoss 5.1.0 中所做的那样)。您是否设法在 JBoss 6.0 中使用 Mojarra 1.2?
    • 我没有看到您的评论更新:嗯,我们在这里成功运行了 JSF 1.2 和 2.0 应用程序,它们使用 JBoss 6.0.0.Final 捆绑的 JSF 实现。至于您的问题,在 EAR/WAR 甚至 JRE/lib(/ext) 中肯定有另一个 JSF impl 与 JBoss 提供的相冲突。
    • @BalusC。我也有作为OP的错误。我的战争文件不包括 JSF impl。我不确定jre6,虽然我看了一下lib找不到任何东西。 jre6 自带 jsf impl 吗?
    • @sarah:不,JRE 默认情况下不会。您(或其他人)可能会在 JRE 的库中删除 JSF JAR。如果仍然无效,请尝试清理 JBoss 数据、临时和工作文件夹。
    • @BalusC:我终于解决了这个问题。将此添加到 web.xml 工作 ` com.sun.faces.config.ConfigureListener`
    【解决方案2】:

    我遇到了同样的问题,但使用的是嵌入式 GlassFish v3。我添加了这个并且它起作用了:

    <listener>
        <listener-class>com.sun.faces.config.ConfigureListener</listener-class>
    </listener>
    

    这是解释问题的网页:Using JSF 1.2 with Facelets on Google App Engine

    【讨论】:

    • 莎拉,非常感谢您的评论。但我现在无法验证。稍后会在这里回复。
    • 请注意,此答案特定于 GlassFish v3,而不是问题中所问的 JBoss AS。这个 GlassFish 特有的错误已在 3.1.x 中修复,因此无需显式注册配置侦听器。
    【解决方案3】:

    我在使用 Jboss EAP 6.1 和 6.3 时遇到了同样的问题。

    我正在使用 Maven,然后,我的问题是关于 EAR 文件的生成,当我使用 Maven 时,我发现我的 EAR 文件被部署了依赖项“爆炸”,也就是说,我的 EAR文件部署在一个文件夹中,该文件夹包含我的项目文件,而不是 WAR 和 JAR 文件。

    在调查展开的 EAR 目录和 EAR 存档之间的差异时,我发现您所看到的并不是 Maven 所得到的。我认为问题在于创建分解目录时没有应用用于 WAR 和 EAR 构建的各种 Maven 插件。

    为了解决这个问题,我刚刚从 EAR 的 POM 中删除了“解包”指令。

    <modules>  
            <webModule>  
                      <groupId>br.web</groupId>  
                      <artifactId>Web</artifactId>  
                      <contextRoot>/project</contextRoot>  
                      <unpack>false</unpack>
            </webModule>  
            <ejbModule>  
                      <groupId>br.ejb</groupId>  
                      <artifactId>Ejb</artifactId>  
                      <unpack>false</unpack>  
            </ejbModule>
      </modules>  
    

    另外,我不建议在 EAR 文件中使用展开的目录。

    【讨论】:

      猜你喜欢
      • 2014-04-01
      • 2011-12-14
      • 2012-01-16
      • 2012-03-05
      • 2014-09-07
      • 1970-01-01
      • 1970-01-01
      • 2015-07-03
      相关资源
      最近更新 更多