如何让Hibernate使用UserType来生成hbm2java代码?

lx0bsm1f  于 2023-05-12  发布在  Java
关注(0)|答案(1)|浏览(94)

我的情况是,我有一个Sping Boot 应用程序,一个PostgreSQL数据库,并使用hbm2 java hibernate Maven插件来生成实体类。数据库使用JPA/Hibernate没有匹配内置类型的类型(例如:ltree),所以我的想法是使用UserType。
我创建了一个LTreeType.java实现UserType接口的www.example.com类。如何让hbm2 java对ltree类型的每个数据库列使用它?
编辑:
到目前为止,我发现我必须创建一个reveng.xml文件或子类DefaultReverseEngineeringStrategy。我不知道如何告诉插件使用前者(如果它仍然存在-这整个混乱是完全没有文档的),或者如何实际让我的子类与Maven插件一起工作。
对于前者,<revengFile>似乎确实可以工作,尽管我最终得到了错误Execution entity-generation of goal org.hibernate.tool:hibernate-tools-maven:6.2.1.Final:hbm2java failed: Could not resolve named type
因此,如果有人知道如何告诉Maven或这个该死的插件将我的正常源文件夹添加到类路径中,这可能会解决这个问题。
最后一句忠告:如果你有选择的话,尽可能远离hibernate-tools。这是一个无证混乱。

ztigrdn8

ztigrdn81#

所以,我终于做到了。退一步说,这很复杂。
首先,您必须创建您的用户类型-确保实现UserType<>JdbcType-在本例中,我使用UserType<LTree>并创建了一个LTree类来保存值,但您也可以只使用String
然后,您需要子类化DelegatingStrategy以及您正在使用的任何SQLDialect-在我的示例中,它是PostgreSQLDialect
示例逆向工程策略:

public class ExampleReverseEngineeringStrategy extends DelegatingStrategy {
  public ExampleReverseEngineeringStrategy(RevengStrategy delegate) {
    super(delegate);
  }

  @Override
  public String columnToHibernateTypeName(TableIdentifier table, String columnName, int sqlType, int length, int precision, int scale, boolean nullable, boolean generatedIdentifier) {
    if(columnName.equals("path")) {
      return "ltree";
    } else {
      return super.columnToHibernateTypeName(table, columnName, sqlType, length, precision, scale, nullable, generatedIdentifier);
  }
}

示例PostgreSQL方言:

public class ExamplePostgreSQLDialect extends PostgreSQLDialect {
  @Override
  public void contributeTypes(TypeContributions typeContributions, ServiceRegistry serviceRegistry) {
    super.contributeTypes(typeContributions, serviceRegistry);
    typeContributions.getTypeConfiguration().getBasicTypeRegistry().register(LTreeType.INSTANCE, "ltree");
  }
}

最后,我使用了Maven antrun插件。这是迄今为止最长的代码块,所以要注意:

<plugin>
        <artifactId>maven-antrun-plugin</artifactId>
        <version>3.1.0</version>
        <dependencies>
          <dependency>
            <groupId>org.hibernate.tool</groupId>
            <artifactId>hibernate-tools-ant</artifactId>
            <version>${hibernate.version}</version>
          </dependency>
          <dependency>
            <groupId>org.hibernate.tool</groupId>
            <artifactId>hibernate-tools-orm</artifactId>
            <version>${hibernate.version}</version>
          </dependency>
          <dependency>
            <groupId>org.postgresql</groupId>
            <artifactId>postgresql</artifactId>
            <version>42.6.0</version>
          </dependency>
        </dependencies>
        <executions>
          <execution>
            <id>entity-generation-ant</id>
            <phase>generate-sources</phase>
            <configuration>
              <target>
                <echo message="Ant: Running Hibernatetool with ${project.build.sourceDirectory}" />
                <property name="maven_compile_classpath"
                refid="maven.compile.classpath" />
                <property name="maven_test_classpath"
                refid="maven.test.classpath" />
                <path id="hibernatetool.path">
                  <pathelement path="${maven_compile_classpath}" />
                  <pathelement path="${maven_test_classpath}" />
                  <pathelement path="${project.build.sourceDirectory}" />
                  <pathelement path="${project.build.outputDirectory}" />
                </path>
                <taskdef name="hibernatetool"
                classname="org.hibernate.tool.ant.HibernateToolTask"
                classpathref="hibernatetool.path" />
                <hibernatetool destdir="${project.build.directory}/generated-sources">

                  <classpath>
                    <path refid="hibernatetool.path" />
                    <path location="${project.build.outputDirectory}" />
                  </classpath>
                  <jdbcconfiguration propertyfile="src/main/resources/application.properties"
                  packagename="com.example.db"
                  reversestrategy="com.example.SparsanaReverseEngineeringStrategy">

                    <!-- revengfile="src/main/resources/hibernate.reveng.xml" > -->
                    <fileset dir="${project.build.sourceDirectory}" />
                  </jdbcconfiguration>
                  <hbm2java jdk5="true" ejb3="true" />
                </hibernatetool>
              </target>
            </configuration>
            <goals>
              <goal>run</goal>
            </goals>
          </execution>
        </executions>
      </plugin>

它也可能与“正常”的hbm2 java Maven插件一起工作,我还没有测试过,我还没有勇气。希望这能帮助像我一样处于困境的人。

相关问题