You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

GlassFish7+JakartaEE10集成Hibernate遇NoClassDefFoundError求助

问题:GlassFish 7 + Hibernate 6.2.6 JTA数据源配置报错NoClassDefFoundError

我正在尝试让Hibernate与GlassFish 7的JDBC连接池配合工作,连接池已正确配置且ping测试通过,已将mysql-connector-j-8.0.33.jar和hibernate-core-6.2.6.Final.jar放入glassfish/domain/domain1/lib目录。

使用RESOURCE_LOCAL类型的持久化单元时一切正常,但切换到JTA数据源的持久化单元时出现以下错误:

java.lang.NoClassDefFoundError: org/hibernate/annotations/common/reflection/ReflectionManager

以下是我的相关配置和代码:

persistence.xml 配置

<?xml version="1.0" encoding="UTF-8" ?>
<persistence xmlns="https://jakarta.ee/xml/ns/persistence"
             xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
             xsi:schemaLocation="https://jakarta.ee/xml/ns/persistence https://jakarta.ee/xml/ns/persistence/persistence_3_0.xsd"
             version="3.0">

    <persistence-unit name="persistence-unit">
        <provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
        <jta-data-source>jpa1</jta-data-source>
        <class>jpa1.User</class>
        <exclude-unlisted-classes>true</exclude-unlisted-classes>
        <properties>
            <property name="hibernate.dialect" value="org.hibernate.dialect.MySQLDialect"/>
            <property name="jakarta.persistence.schema-generation.database.action" value="drop-and-create"/>
            <property name="hibernate.transaction.jta.platform" value="org.hibernate.service.jta.platform.internal.SunOneJtaPlatform"/>
            <property name="hibernate.hbm2ddl.auto" value="update"/>
        </properties>
    </persistence-unit>
    <!--
    <persistence-unit name="persistence-unit" transaction-type="RESOURCE_LOCAL">
        <provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
        <properties>
            <property name="jakarta.persistence.jdbc.driver" value="com.mysql.jdbc.Driver"/>
            <property name="jakarta.persistence.jdbc.url" value="jdbc:mysql://127.0.0.1:8889/learn_it_jpa?autoReconnect=true&amp;useSSL=false"/>
            <property name="jakarta.persistence.jdbc.user" value="root"/>
            <property name="jakarta.persistence.jdbc.password" value="root"/>
            <property name="hibernate.hbm2ddl.auto" value="update"/>
            <property name="jakarta.persistence.schema-generation.database.action" value="none"/>
            <property name="hibernate.dialect" value="org.hibernate.dialect.MySQLDialect"/>
        </properties>
    </persistence-unit>
    -->
</persistence>

pom.xml 配置

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
  <modelVersion>4.0.0</modelVersion>
  <groupId>org.example</groupId>
  <artifactId>jpa1</artifactId>
  <packaging>war</packaging>
  <properties>
    <maven.compiler.source>17</maven.compiler.source>
    <maven.compiler.target>17</maven.compiler.target>
  </properties>
  <version>1.0-SNAPSHOT</version>
  <name>jpa1 Maven Webapp</name>
  <url>http://maven.apache.org</url>
  <dependencies>
    <dependency>
      <groupId>com.mysql</groupId>
      <artifactId>mysql-connector-j</artifactId>
      <version>8.0.33</version>
    </dependency>
    <dependency>
      <groupId>jakarta.platform</groupId>
      <artifactId>jakarta.jakartaee-api</artifactId>
      <version>10.0.0</version>
      <scope>provided</scope>
    </dependency>
    <dependency>
      <groupId>jakarta.persistence</groupId>
      <artifactId>jakarta.persistence-api</artifactId>
      <version>3.1.0</version>
    </dependency>
    <dependency>
      <groupId>org.hibernate</groupId>
      <artifactId>hibernate-core</artifactId>
      <version>6.2.6.Final</version>
      <scope>provided</scope>
    </dependency>
    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>3.8.1</version>
      <scope>test</scope>
    </dependency>
  </dependencies>
  <build>
    <finalName>jpa1</finalName>
  </build>
</project>

JTA使用代码

package jpa1;

import jakarta.persistence.EntityManager;
import jakarta.persistence.EntityManagerFactory;
import jakarta.persistence.Persistence;
import jakarta.servlet.ServletException;
import jakarta.servlet.annotation.WebServlet;
import jakarta.servlet.http.HttpServlet;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;

import java.io.IOException;
import java.util.List;

@WebServlet(name = "homeServlet", value = "/start")
public class HomeServlet extends HttpServlet {

    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {

        EntityManagerFactory entityManagerFactory = Persistence.createEntityManagerFactory("persistence-unit");
        EntityManager entityManager = entityManagerFactory.createEntityManager();

        entityManager.getTransaction().begin();

        User user1 = new User("Max","Mustermann", User.Gender.MALE, 10, 50000, 1000);

        entityManager.persist(user1);
        entityManager.getTransaction().commit();

        List<User> results = entityManager
                .createQuery("Select a from User a", User.class)
                .getResultList();


        entityManager.close();
        entityManagerFactory.close();

        req.setAttribute("test", results);
        req.getRequestDispatcher("start.jsp").forward(req, resp);
    }
}

实体类代码

package jpa1;

import jakarta.persistence.*;

@Entity
public class User {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private int id;

    @Column(name = "first_name")
    private String firstName;

    @Column(name = "last_name")
    private String lastName;

    @Column(name = "gender")
    @Enumerated(EnumType.ORDINAL)
    private Gender gender;

    @Column(name = "age")
    private int age;

    @Column(name = "salary")
    private int salary;

    @Column(name = "test")
    private int test;

    public User() {

    }

    public enum Gender {
        MALE,
        FEMALE
    }

    public User(String firstName, String lastName, Gender gender, int age, int salary, int test) {
        this.firstName = firstName;
        this.lastName = lastName;
        this.gender = gender;
        this.age = age;
        this.salary = salary;
        this.test = test;
    }

    public String getFirstName() {
        return firstName;
    }

    public String getLastName() {
        return lastName;
    }

    public Gender getGender() {
        return gender;
    }

    public String getGenderStr() {
        switch (gender) {
            case MALE -> {
                return "Männlich";
            }
            case FEMALE -> {
                return "Weiblich";
            }
            default -> {
                return "";
            }
        }
    }

    public int getAge() {
        return age;
    }
}

解决方案

这个错误是因为缺少Hibernate依赖包hibernate-commons-annotations,Hibernate 6.x版本中该包是hibernate-core的间接依赖,手动放置jar包时容易遗漏。

解决步骤:

  1. 下载与Hibernate 6.2.6.Final匹配的hibernate-commons-annotations-6.0.6.Final.jar
  2. 将该jar包放入glassfish/domain/domain1/lib目录
  3. 重启GlassFish服务器

额外优化建议:

  • 移除persistence.xml中重复的DDL配置项,jakarta.persistence.schema-generation.database.action和hibernate.hbm2ddl.auto保留一个即可,推荐保留hibernate.hbm2ddl.auto="update"
  • MySQL 8.x环境下,替换方言为org.hibernate.dialect.MySQL8Dialect,兼容性更好
  • JTA模式下,可改用容器管理的实体管理器(通过@PersistenceContext注入),更符合Jakarta EE规范

内容的提问来源于stack exchange,提问作者Hendrik

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.16 06:37:08