これは Hibernate公式チュートリアル からです:
代替案があります
<composite-id>
複合キーでレガシーデータへのアクセスを許可する宣言。それ以外の用途には使用しないことを強くお勧めします。
複合キーが推奨されないのはなぜですか?私は、すべての列が外部キーであり、モデルで意味のある関係である主キーを形成する3列のテーブルの使用を検討しています。これが悪い考えである理由はわかりません。特に、インデックスを使用することになります。
代替は何ですか?自動生成された追加の列を作成し、それを主キーとして使用しますか?とにかく3つの列を照会する必要があります!?
要するに、なぜこの声明は真実なのでしょうか?そして、より良い代替手段は何ですか?
彼らはいくつかの理由でそれらを思いとどまらせます:
代わりに、他の3つの列に加えて、自動生成された単一列の主キーを使用することもできます。 3つの列のタプルを一意にする場合は、一意制約を使用します。
質問に答えるのが遅すぎる場合でも、ここでは、Hibernateが代理キーを使用する必要性(本当にアドバイスですか?)について別の観点(もっと適度に期待します)を示したいと思います。
まず最初に、両方という事実を明確にしたい代理キー(人工的に自動生成されたもの)と自然キー(ドメインの意味を持つ列で構成される)には、prosとcons。あるキータイプが他のキータイプよりも優れているとは言いません。私はあなたの要件によっては、自然な鍵が代理の鍵よりも良い選択であるかもしれないと言っています。
代理キーは次のとおりです。
Java Persistence with Hibernateリファレンスに記載されているように:
より経験豊富なHibernateユーザーは、saveOrUpdate()のみを使用します。特に混合状態のオブジェクトのより複雑なネットワークでは、Hibernateに新しいものと古いものを判断させる方がはるかに簡単です。排他的なsaveOrUpdate()の唯一の(それほど深刻ではない)欠点は、データベースでSELECTを実行せずにインスタンスが古いか新しいかを推測できない場合があることです。たとえば、クラスが自然な複合キーでマップされている場合、バージョンまたはタイムスタンププロパティはありません。
limitationのいくつかの症状(これは、私たちはそれを呼び出す必要があると思います)を見つけることができます here 。
あなたの意見をあまりにも二乗しないでください。適切な場合は自然キーを使用し、適切な場合は代理キーを使用します。
これが誰かを助けたことを願っています!
設計の観点から問題を考えます。 Hibernateがそれらを良いか悪いかと考えるだけではありません。本当の質問は次のとおりです:自然なキーは私のデータの良い識別子になるための良い候補ですか?
今日のビジネスモデルでは、一部のデータでレコードを識別するのが便利ですが、ビジネスモデルは時間とともに進化します。そして、これが発生すると、自然キーがデータを一意に識別するために適合しなくなることがわかります。そして、他のテーブルの参照整合性により、これは物事を[〜#〜] much [〜#〜]変更しにくくします。
ストレージでのデータの識別方法とビジネスモデル構造を連鎖させないため、代理PKがあると便利です。
シーケンスから自然キーを生成することはできません。データで識別できないデータの場合は、 much より頻繁です。これは、自然キーがストレージキーとは異なることを示す証拠であり、一般的な(そして適切な)アプローチと見なすことはできません。
代理キーを使用すると、アプリケーションとデータベースの設計が簡単になります。それらは使いやすく、より高性能で、完璧な仕事をします。
自然キーは欠点のみをもたらします。自然キーを使用することの単一の利点を考えることはできません。
そうは言っても、Hibernateには自然な(構成された)キーに関する実際の問題はないと思います。しかし、休止状態のコミュニティは代理キーの利点を広く認めているため、おそらくいくつかの問題(またはバグ)や、ドキュメントの問題やヘルプの取得を見つけることになるでしょう。したがって、複合キーを選択した理由について、適切な回答を用意してください。
Hibernateのドキュメントが正しく理解されている場合:
「複合キーを使用してレガシーデータへのアクセスを許可する別の<composite-id>
宣言があります。それ以外の場合は使用しないでください。」
トピック5.1.4についてidタグxml <id>
を使用すると、主キーマッピングが早すぎるため、休止状態のドキュメントでは、複合主キーマッピングに<composite-id>
xmlタグではなく<id>
を使用しないようにできます。 [〜#〜] not [〜#〜]複合主キーを使用するには、参照を負にします。
ツールとしてデータベースを使用して開発されたアプリケーションは、クエリの最適化にクラスター化されたインデックスを使用して、代理キーのワークフローを維持するのに間違いなく有益です。
データウェアハウジングとOLAPスタイルのシステムですが、大規模なファクトテーブルを使用してディメンションの代理キーを結び付けるために特別な注意が必要です。この場合、データによって、ダッシュボード/アプリケーションがレコードを維持するために使用できます。
したがって、1つのメソッドが別のメソッドよりも好ましいのではなく、おそらく1つのディレクティブが別のメソッドよりも有利であることが重要です。SSASシステムインスタンスへの直接アクセスを利用するHibernateアプリを簡単に開発することはできません。
私は両方の主要な混合物を使用して開発し、クラスター化されたインデックスを持つサロゲートが通常、最初の選択肢です。
そのため、OPやその他の見方について:(Hibernateが専門とする)開発でdbを不変のままにしたい場合-サロゲートメソッドを使用し、データの読み取りが遅くなる傾向がある場合、または特定のクエリのドレインに気付いた場合パフォーマンス、特定のデータベースに戻し、クエリの順序を最適化する複合クラスター化インデックスを追加します。