4

次の要件を満たすHibernateIDジェネレーターを使用することにしました。-ドメインが異なるアプリケーション(異なるJVM)からアクセスされる場合の安全なID生成-ID間隔を使用します(新しいIDが発生するたびにデータベースにクエリを実行しないでください)必要)

いくつかの調査の後、私は2つの休止状態の拡張識別子ジェネレーターの1つを選択しました。

org.hibernate.id.enhanced.TableGenerator

問題は、このアルゴリズムが利用可能な次の値ではなく、利用可能な次の間隔の終わりをデータベースに保持することです。したがって、increment_size 10のIDジェネレーターがあるとすると、IDを要求すると、間隔1-を受け取ります。 10ですが、データベースには値11ではなく21が格納されています。この動作では、特定のテーブルにマップするすべてのクラスで、increment_sizeを同じに保つ必要があります。なぜこの動作をするのですか?これを修正する方法はありますか?

4

2 に答える 2

4

org.hibernate.id.enhanced.TableGeneratorは、複数の値を同時に生成できるテーブルを定義します。複数のエンティティの単一の値から識別子を生成させようとしているように聞こえます。これを利用したい場合は、「segment_value」TableGenerator構成設定によって制御されます。

そして、値に関しては、「修正」するものは何もありません。その壊れていません。別の動作が必要な場合は、別の動作を構成します。これは、TableGeneratorの「オプティマイザー」構成設定によって定義されるオプティマイザーと呼ばれるものによって制御されます。これはすべてマニュアルで説明されています:http : //docs.jboss.org/hibernate/orm/4.1/manual/en-US/html_single/#mapping-declaration-id特に「5.1.2.3。拡張識別子ジェネレータ」のセクションを参照してください。 "および"5.1.2.3.1。識別子ジェネレータの最適化"。マニュアルでは、利用可能なすべてのオプティマイザについて説明しているわけではありません。必要なもののように聞こえますが、「pooled-lo」と呼ばれます。これは「pooled」と同じですが、高い値ではなくloの値を格納します。

于 2012-07-09T19:04:19.260 に答える
1

この投稿は古いですが、同じ種類の問題を抱えている可能性のある他の人にとっては。

Steve Ebersoleが示しているように、ケースでは「pooled-lo」オプティマイザーを使用する必要があります。Hibernateバージョンも確認してください。以前のバージョンで問題があったため、>=4.3.11である必要があります。

説明のために、pooled-loオプティマイザを使用すると、データベースに格納されている値は、使用可能な次の間隔の低い値になります。

したがって、永続化された最後のエンティティのIDが[1; 10]にある場合、次に使用可能な間隔は[11,20]であり、データベースに格納される値は予想どおり11になります。

したがって、Hibernateを使用せず、Hibernate構成で定義された増分サイズを認識していない別のプログラムがある場合でも、シーケンスを中断せずにエンティティを挿入できます。

シーケンス値をアトミックに取得してインクリメントし、挿入する新しいエンティティIDとして値retrieve(「インクリメント」の前)を使用するだけです。この例では、1行を挿入するために、シーケンス値を12に更新し、IDが11の新しいエンティティを追加します。したがって、hibernateがメモリ内の現在の間隔の最後のID(10)に達すると、クエリを実行します。データベースを作成し、値22を格納して、ID[12;21]の新しい間隔を保持します。

于 2017-01-22T15:38:35.113 に答える