エンティティマネージャーの実装で Hibernate 4.1.4 を使用しており、非常に満足しています。単一のエンティティまたはエンティティの小さなセット (10 ~ 50 + サブエンティティ) を読み込むと、優れたパフォーマンスが得られ、すべての結合がうまく機能し、双方向です。編集・保存・削除がカンタン!
レポート用に 2500 のエンティティと関連データを読み込み中
サブエンティティとともに数百または数千のエンティティをロードしようとすると、問題が発生します。1 つの例では、2 つの 1 対 1 結合と 3 つの 1 対多結合と共に、約 2500 の基本エンティティがあります。これにより、2500 x 5 +1 クエリが発生します。データベース (DB2) での実行には約 30 秒かかります。
動的クエリとエンティティ マネージャー create query メソッドを使用します。
http://docs.jboss.org/hibernate/orm/4.1/javadocs/
http://docs.oracle.com/javaee/6/api/javax/persistence/EntityManager.html
結合を使用するように Hibernate を誘導しようとしています
私たちの観察では、何を試しても、プライマリ クエリの結合としてサブエンティティのロードを実行するために hibernate を取得できないようです。find メソッドを使用して単一のエンティティをロードし、主キーによって hibernate は結合を使用しますが、複数の基本エンティティがロードされている場合は使用しません。
同じ結果で基準APIを試しました。
クエリで複数のエンティティを取得することに成功
例:
select a,b from table1 a left join table2 b
クエリで手動で結合を行い、タプルを介して個々のエンティティを取得することに部分的に成功しましたが、これは注釈付きのエンティティ モデルをバイパスし、推奨される方法ではありません (回避できる場合)。
http://docs.jboss.org/hibernate/orm/4.1/manual/en-US/html_single/#objectstate-querying-executing
タプルで遭遇した問題は、タプルがプライマリ エンティティから切り離されており (注釈付きの関係を介して読み込まれていないため、これは論理的と思われます)、それらを再アタッチする方法がないように思われることです。エンティティのリストに 1 対多のすべてのレコードを手動で追加した後、hibernate がリストの get メソッドにヒットすると、リストのイーガー/レイジー ロードを試行します (リストが既に設定されているにもかかわらず)。
試行された最適化 - データセットのプリロード
私たちが試みたもう 1 つの最適化手法は、事前にデータ セットをプリロードすることでした。すべてのコア エンティティをロードした後、pk のリストを作成し、単一のクエリを起動して、1 対多のデータ セットをすべてロードしました。しかし、hibernate がリスト データのゲッターにヒットすると、セッションで既にプリロードされているものを無視して、リストを熱心/遅延ロードしようとします (おそらくキャッシュを有効にする必要がありますか?)。
提案?
私たちは多くの異なる方向に進んでいますが、ほとんど成功していません。誰かが正しい道を示してくれることを期待しています (または新しい道を示してください!)。