【问题标题】:How to get OpenJPA jars loaded by tomcat如何让tomcat加载OpenJPA jars
【发布时间】:2013-09-06 18:22:48
【问题描述】:

我有一个使用 openjpa 2.1.1 作为其持久性框架的 spring mvc 应用程序。它是作为 STS 中的 Maven 项目开发的,并在 vFaric TC Server (Tomcat 7) 上本地运行。

当我们第一次将战争部署到 Websphere 8.5 时,我们遇到了类加载器与我们战争文件中的以下 3 个 openjpa jar 的冲突:

geronimo-jpa_2.0_spec-1.1.jar geronimo-jta_1.1_spec-1.1.1.jar 验证-api-1.0.0.GA.jar

从战争中删除这些并推迟到 Websphere 捆绑的 openjpa 工作正常,所以我将 openjpa POM 依赖范围从“编译”更改为“提供”(这样这些 jar 就不会被打包到战争文件中)。

由于 Tomcat 7 不兼容 Java EE,我将 3 个 jars 放在 Tomcat\lib 中(还尝试了 vfabric-tc-server lib - 它包装了 tomcat),但应用程序在启动时看不到 JPA 类( noclassdeffound 控制台中的异常)。

我还尝试从 STS 中的“启动配置”将 jars 添加到服务器类路径 - 那里也没有运气。

是否需要在 Tomcat 中的某个位置设置类加载器顺序,以便 JPA 在应用程序之前加载?

我需要的是一个可以在部署到 Tomcat 或 Websphere 时工作的构建。

任何帮助将不胜感激。

【问题讨论】:

    标签: maven tomcat7 openjpa websphere-8


    【解决方案1】:

    如果这对任何人都有帮助,NoClassDefFoundError 指的是一个 JPA 类,但不是我包含的 3 个 jar 中的一个。我跑了mvn tree,发现整个JPA依赖链是:

    openjpa-2.1.1.jar commons-lang-2.4.jar commons-collections-3.2.1.jar geronimo-jta_1.1_spec-1.1.1.jar geronimo-jpa_2.0_spec-1.1.jar

    我还需要补充:

    serp-1.12.0.jar

    我最初也在 tomcat/lib 中包含了validation-api-1.0.0.GA.jar,因为它必须从战争中删除才能使 websphere 工作,但是将它放在 tomcat/lib 中会导致“javax. validation.ValidationException: Unable to find default provider" 所以我把它拿出来了,这意味着只需要添加上面的 6 个 jars。

    【讨论】:

    • 对于任何感兴趣的人,这是我的 Tomcat+AutomanagedEM+OpenJPA 包装器。请参阅 jar 所在的 example_webapp/web-inf/lib/ 文件夹。对于任何使用 Tomcat+JPA 技术的人来说,这可能是一个很好的参考。 github.com/Murmur/ScopedEntityManager
    【解决方案2】:

    @user2743197 - 首先,您需要在 Maven pom.xml 中定义单独的配置文件。为 WAS 定义一个配置文件并通过以下方式使用其 OpenJPA 依赖项:

        <dependency>
            <groupId>javax</groupId>
            <artifactId>javaee-api</artifactId>
            <version>6.0</version>
            <scope>provided</scope>
        </dependency>
    

    这就是我使用与 WAS v8.x.x 捆绑的 OpenJPA-2.1.1-SNAPSHOT 二进制文件的方式

    为 Tomcat 定义另一个 Maven 配置文件,该配置文件显式获取您需要的所有依赖项,除了 Tomcat 确实提供的少数与 JavaEE 相关的规范。因此,将 OpenJPA-2.1.1-SNAPSHOT 定义为依赖项(当然不是“提供”)。

    现在,至于在部署到 Tomcat(不使用 Spring)的 war 项目中引导 JPA,我通常会创建一个这样的类:

    @WebListener
    public class ApplicationLifeCycleListener implements ServletContextListener {
        @Override
        public void contextInitialized(ServletContextEvent sce) {
           ...
           // Do some OpenJPA bootstrapping here
           // Get an EntityManager.
           EntityManager em = PersistenceUtil.getEntityManager();
        }
        @Override
        public void contextDestroyed(ServletContextEvent sce) {
            //throw new UnsupportedOperationException("Not supported yet.");
            PersistenceUtil.closeEntityManagerFactory();
        }
    }
    

    这就是我为引导 Hibernate/JPA 所做的工作。我的 PersistenceUtil 处理 EntityManagerFactory 的创建、我的 EntityManager 的交付等。

    您可能需要考虑使用 TomEE。在 JPA 方面,它将为您提供与 WebSphere 8.x.x 相同的功能。两者都严重依赖 Apache 产品。 WebSphere 8.x.x 和 TomEE 将允许您使用 EJB 3.x,无论有没有 CDI,它都更容易与 JPA 实现一起使用。使用 Tomcat,您必须自己处理事务管理或弄清楚如何利用 CDI 或 Spring 来管理事务。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-09-22
      • 2012-01-24
      • 1970-01-01
      • 1970-01-01
      • 2012-02-01
      • 1970-01-01
      • 2013-03-15
      • 2013-10-01
      相关资源
      最近更新 更多