役に立ちましたか?

解決

この質問は本当に古く、長い間答えられてきましたが、最近、私はこの同じ状況にあり、良い解決策を見つけました。まず最初に、Hibernateには3つの異なる組み込みUUIDタイプの実装があることがわかりました。

  1. binary-uuid :UUIDをバイナリとして保存します
  2. uuid-char :UUIDを文字シーケンスとして保存します
  3. pg-uuid :ネイティブのPostgres UUIDタイプを使用します

これらのタイプはデフォルトで登録されており、特定のフィールドに @Type アノテーションで指定できます。例:

@Column
@Type(type = "pg-uuid")
private UUID myUuidField;

Dialect のデフォルトタイプをオーバーライドするメカニズムも あります。したがって、最終展開がPostgresデータベースと通信するが、ユニットテストでHSQLを使用する場合、 pg-uuid タイプをオーバーライドして、次のようなカスタム方言を作成することにより、文字データを読み書きできます:

public class CustomHSQLDialect extends HSQLDialect {

    public CustomHSQLDialect() {
        super();

        // overrides the default implementation of "pg-uuid" to replace it
        // with varchar-based storage.
        addTypeOverride(new UUIDCharType() {
            @Override
            public String getName() {
                return "pg-uuid";
            }
        });
    }
}

カスタムダイアレクトをプラグインするだけで、両方の環境で pg-uuid タイプが使用可能になります。

他のヒント

やあ、Hibernate 4で解決策を探している人(Dialect#addTypeOverrideメソッドはもう利用できないため)のために、このSteve Ebersoleのコメント

次のようなカスタムユーザータイプを作成する必要があります。

public class UUIDStringCustomType extends AbstractSingleColumnStandardBasicType {

    public UUIDStringCustomType() {
        super(VarcharTypeDescriptor.INSTANCE, UUIDTypeDescriptor.INSTANCE);
    }

    @Override
    public String getName() {
        return "pg-uuid";
    }

}

HSQLDBダイアレクトにバインドするには、次のようにDialect#contributeTypesメソッドをオーバーライドするカスタムダイアレクトを構築する必要があります。

public class CustomHsqlDialect extends HSQLDialect {


    @Override
    public void contributeTypes(TypeContributions typeContributions, ServiceRegistry serviceRegistry) {
        super.contributeTypes(typeContributions,serviceRegistry);
        typeContributions.contributeType(new UUIDStringCustomType());
    }

}

その後、2つのデータベースで@Type(type =" pg-uuid")を使用できます。

誰かに役立つことを願っています...

@Type アノテーションを指定せずにUUIDタイプ間の問題を回避するには)そのパッケージのhibernates @TypeDef アノテーションで package-info.java を使用しています。

アプリケーションのセットアップ例は次のとおりです。
module / src / main / java / app.package.domain にエンティティが含まれていると仮定します。そして、あなたのテストは module / src / test / java / app.package に保存されます。

domain パッケージに2つの package-info.java を作成するだけです。

  

package-infoファイルが常に同じパッケージにあることを確認します(テスト用と本番用)。以下の例を参照してください。

src/main/java
  app
    package
      domain
        package-info.java 

src/test/java
  app
    package
      domain
        package-info.java 

プロダクション package-info.java のコンテンツは次のようになります(Postgres):

@TypeDef(
  name = "pg-uuid",
  defaultForType = UUID.class,
  typeClass = PostgresUUIDType.class
)
package app.package.domain;

import org.hibernate.annotations.TypeDef;
import org.hibernate.type.PostgresUUIDType;

import java.util.UUID;

これは、「構成」をテストする方法です。 (H2)のようになります:

@TypeDef(
  name = "uuid-char",
  defaultForType = UUID.class,
  typeClass = UUIDCharType.class
)
package app.package.domain;

import org.hibernate.annotations.TypeDef;
import org.hibernate.type.UUIDCharType;

import java.util.UUID;

希望する

データベースの機能に応じて正しいことを行うために、ユーザータイプにスマートを構築することができます。 Hibernate自体も、「ネイティブ」で同様のアプローチを取ります。 IDジェネレータ。使用しているデータベースのタイプに応じて動作が異なります。このようなアプローチにより、実行時にマッピングを切り替える必要がなくなります。

たとえば、データベースごとに1つの戦略クラスを作成できます。次に、ユーザータイプクラスで、最初に呼び出されたときに接続しているデータベースを検出し、そのデータベースの適切な戦略をインスタンス化してから、すべての呼び出しを戦略オブジェクトに委任します。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top