web-dev-qa-db-ja.com

Hibernateアノテーションの継承?

Javaアノテーションを使用してHibernate継承マッピングを構成するにはどうすればよいですか?アノテーションで継承を使用する利点は何ですか?

29
stical

3つの可能なタイプ:

1。クラス階層ごとの単一テーブル戦略:

 @Entity
 @Inheritance(strategy=InheritanceType.SINGLE_TABLE)
 @DiscriminatorColumn(      name="planetype",
  discriminatorType=DiscriminatorType.STRING      )
 @DiscriminatorValue("Plane")
 public class Plane { ... }

 @Entity
 @DiscriminatorValue("A320")
 public class A320 extends Plane { ... }     


 <hibernate-mapping>
 <subclass name="DomesticCat" extends="Cat" discriminator-value="D">
      <property name="name" type="string"/>
 </subclass>
  • 長所:最もシンプル。 JOINは必要ありません
  • 短所:nullは使用できません。列の数は、オブジェクトグラフの深さとともに増加します。

2。結合されたサブクラス戦略:

データベーステーブル

CREATE TABLE SUPER_TABLE(
id_col number primary key,
sup_Name varchar2(20));

CREATE TABLE  SUB_TABLE(
SUP_ID primary key,
sub_name varchar2(20),
constraint SUB_TABLE_fk foreign key (sup_Id)  references    super_table(id_col));


@Entity
@Table(name= "SUPER_TABLE")
@Inheritance(strategy= InheritanceType.JOINED)
    public class TestSuperClass {
@Id
@GeneratedValue(
        strategy=GenerationType.SEQUENCE, 
        generator="SEQ_GEN")
    @SequenceGenerator(
        name="SEQ_GEN",
        sequenceName="hibernate_sequence"
    )
    @Column(name ="id_col")
private long idcol;
@Column(name ="sup_name")
private String supName;


@Entity 
@Table(name="SUB_TABLE")
@PrimaryKeyJoinColumn(name="SUP_ID")

<class name="Payment" table="PAYMENT">
<id name="id" type="long" column="PAYMENT_ID">
    <generator class="native"/>
</id>
<property name="amount" column="AMOUNT"/>
...
<joined-subclass name="CreditCardPayment" table="CREDIT_PAYMENT">
    <key column="PAYMENT_ID"/>
    <property name="creditCardType" column="CCTYPE"/>
    ...
</joined-subclass>
<joined-subclass name="CashPayment" table="CASH_PAYMENT">
    <key column="PAYMENT_ID"/>
    ...
</joined-subclass>

public class TestSubClass extends TestSuperClass{ 
    private String sub_name; 
}

テストモジュール

TestSubClass sub = new TestSubClass("sub1");
sub.setSupName("supersuper"); session1.save(sub);

SQL生成

 Hibernate: insert into SUPER_TABLE (sup_name, id_col) values (?, ?)    
 Hibernate: insert into SUB_TABLE (sub_name, SUP_ID) values (?, ?)
  • 長所:正規化されたデータ構造。
  • 短所:結合は常に必須です。

。具体的なクラス戦略ごとのテーブル:

create table CREDIT_CARD( payment_id number primary key, amount
number, creditCardType varchar2(2) );


  @Entity
  @Inheritance(strategy=InheritanceType.TABLE_PER_CLASS)
  public abstract class Payment {
@Id
@GeneratedValue(
        strategy=GenerationType.SEQUENCE, 
        generator="SEQ_GEN")
    @SequenceGenerator(
        name="SEQ_GEN",
        sequenceName="hibernate_sequence"
    )
@Column(name = "payment_id")
private long id;

private double amount;



 @Entity
 @Table(name="CREDIT_CARD")
 public class CreditCardPayment extends Payment {
private String creditCardType;


 <class name="Payment">
<id name="id" type="long" column="PAYMENT_ID">
    <generator class="sequence"/>
</id>
<property name="amount" column="AMOUNT"/>
...
<union-subclass name="CreditCardPayment" table="CREDIT_PAYMENT">
    <property name="creditCardType" column="CCTYPE"/>
    ...
</union-subclass>

テストモジュール

CreditCardPayment credit = new CreditCardPayment("C",1.0);
session1.save(credit);

SQL生成

  Hibernate: insert into CREDIT_CARD (amount, creditCardType, payment_id) values (?, ?, ?)

アプリケーションで使用した@MappedSuperClassもあります。

52
Achow

これは非常に一般的な質問ですが、以下のリソースをご覧になることをお勧めします。

しかし、あなたの質問に対する非常に基本的な答えは、@Inheritanceアノテーション、次のように:

@Entity
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public class Flight implements Serializable {
   ...
}
7

@MappedSuperclassではなく@Inheritanceアノテーションを使用することをお勧めします。 @MappedSuperclassが継続的なメンテナンスのニーズに十分に柔軟であるという問題が過去にありました。

0
Matt Sidesinger