2012-02-02 2 views
132

私は休止状態にするのが初めてで、1対多と多対1の関係を使用する必要があります。それは私のオブジェクト内の双方向の関係であり、どちらの方向からでも移動することができます。それについては、mappedByがおすすめですが、わかりませんでした。誰かが私に説明してください:誰かがmappedByを休止状態で説明できますか?

  • どのような方法をお勧めしますか?
  • これはどのような目的で解決されますか?ここに私の例のため

は、注釈と私のクラスです:

  • Airlineは、多くのAirlineFlights
  • 多くAirlineFlightsONEAirline
に属し所有しています

航空

@Entity 
@Table(name="Airline") 
public class Airline { 
    private Integer idAirline; 
    private String name; 

    private String code; 

    private String aliasName; 
    private Set<AirlineFlight> airlineFlights = new HashSet<AirlineFlight>(0); 

    public Airline(){} 

    public Airline(String name, String code, String aliasName, Set<AirlineFlight> flights) { 
     setName(name); 
     setCode(code); 
     setAliasName(aliasName); 
     setAirlineFlights(flights); 
    } 

    @Id 
    @GeneratedValue(strategy=GenerationType.IDENTITY) 
    @Column(name="IDAIRLINE", nullable=false) 
    public Integer getIdAirline() { 
     return idAirline; 
    } 

    private void setIdAirline(Integer idAirline) { 
     this.idAirline = idAirline; 
    } 

    @Column(name="NAME", nullable=false) 
    public String getName() { 
     return name; 
    } 
    public void setName(String name) { 
     this.name = DAOUtil.convertToDBString(name); 
    } 

    @Column(name="CODE", nullable=false, length=3) 
    public String getCode() { 
     return code; 
    } 
    public void setCode(String code) { 
     this.code = DAOUtil.convertToDBString(code); 
    } 

    @Column(name="ALIAS", nullable=true) 
    public String getAliasName() { 
     return aliasName; 
    } 
    public void setAliasName(String aliasName) { 
     if(aliasName != null) 
      this.aliasName = DAOUtil.convertToDBString(aliasName); 
    } 

    @OneToMany(fetch=FetchType.LAZY, cascade = {CascadeType.ALL}) 
    @JoinColumn(name="IDAIRLINE") 
    public Set<AirlineFlight> getAirlineFlights() { 
     return airlineFlights; 
    } 

    public void setAirlineFlights(Set<AirlineFlight> flights) { 
     this.airlineFlights = flights; 
    } 
} 

AirlineFlights:

@Entity 
@Table(name="AirlineFlight") 
public class AirlineFlight { 
    private Integer idAirlineFlight; 
    private Airline airline; 
    private String flightNumber; 

    public AirlineFlight(){} 

    public AirlineFlight(Airline airline, String flightNumber) { 
     setAirline(airline); 
     setFlightNumber(flightNumber); 
    } 

    @Id 
    @GeneratedValue(generator="identity") 
    @GenericGenerator(name="identity", strategy="identity") 
    @Column(name="IDAIRLINEFLIGHT", nullable=false) 
    public Integer getIdAirlineFlight() { 
     return idAirlineFlight; 
    } 
    private void setIdAirlineFlight(Integer idAirlineFlight) { 
     this.idAirlineFlight = idAirlineFlight; 
    } 

    @ManyToOne(fetch=FetchType.LAZY) 
    @JoinColumn(name="IDAIRLINE", nullable=false) 
    public Airline getAirline() { 
     return airline; 
    } 
    public void setAirline(Airline airline) { 
     this.airline = airline; 
    } 

    @Column(name="FLIGHTNUMBER", nullable=false) 
    public String getFlightNumber() { 
     return flightNumber; 
    } 
    public void setFlightNumber(String flightNumber) { 
     this.flightNumber = DAOUtil.convertToDBString(flightNumber); 
    } 
} 

EDIT:

データベース・スキーマ:

AirlineFlightsのForeignKeyとしてidAirlineを持っている会社は何のidAirlineFlightsを持っていません。これは、AirlineFlightsを所有者/身元確認主体としていますか?

理論的には、私は航空会社が航空会社のフライトの所有者であることを希望します。

enter image description here

答えて

107

両方のモデルで@JoinColumnを指定すると、双方向の関係はありません。あなたは2つの片方向の関係を持っていて、それについては非常に混乱したマッピングがあります。両方のモデルにIDAIRLINE列を「所有」していると言っています。本当にそれらのうちの1つだけが実際には! 「普通の」ことは、@OneToMany側から@JoinColumnを完全に取り除き、代わりにmappedByを@OneToManyに追加することです。

@OneToMany(cascade = CascadeType.ALL, mappedBy="airline") 
public Set<AirlineFlight> getAirlineFlights() { 
    return airlineFlights; 
} 
Hibernateに伝えます

「行く私は設定を見つけるのコレクションを持っている事で 『航空会社』という名前のBeanのプロパティに目を通します。」

+0

私は、mappedByについて最後にあなたの説明で少し混乱しています。物事がデータベースでどのように整理されるかは重要ですか? @DB:AirlineFlightsには、外部キーとしてidAirlineがあります。航空会社はidAirlineをプライマリキーとして持っており、AirlineFlights @ DBに関する情報は得られません。 – brainydexter

+7

はい、問題ありません。 mappedByの名前は、HibernateにJoinColumnの設定を見つける場所を伝えています。 (AirlineFlightのgetAirline()メソッドについて)JoinColumnを航空会社に配置した方法は、Airlineに他のテーブルに値を保持する責任があることを伝えています。 Entityに別のテーブルのカラムを「所有」していることを伝えることができ、それを更新する責任があります。あなたが通常やりたいことではなく、SQL文が実行される順序で問題を引き起こす可能性があります。 – Affe

+0

編集をご覧ください。 DBレベルでは、airlineFlightテーブルはidAirlineを外部キー列として所有しています。したがって、JoinColumnは、対応するManytoOneのairlineFlightクラス/テーブルに置く必要があります。 – brainydexter

211

MappedBy信号は関係のためのキーが反対側にあることを休止状態。

これは、2つのテーブルをリンクしても、それらのテーブルのうち1つだけが他のテーブルに外部キー制約を持つことを意味します。 MappedByを使用すると、制約を含まないテーブルから他のテーブルにリンクすることができます。

+23

これは受け入れられた回答であったはずです。 – azizunsal

+2

もう少し明確にしていただけますか? –

+1

@Kurt Du Bois、双方向(foreign_key制約付き)を定義するのではなく、なぜ 'mappedBy'を使うのですか? –

6

mappedbyそれはそれ自身のために話す、それはこのフィールドをマッピングしないでください、このフィールド[name = "field"]によってマップされたすべての準備ができています。
フィールドは、あなたはそれが ないとHibernateは同じ関係に

をこの2つの関係をマッピングすることを行わないと、私たちが行う冬眠伝える必要があります。他のエンティティ(name of the variable in the class not the table in database)

です一方の側でのみマッピングし、それらの間で座標を合わせる。

+0

はmappedByはオプションですか?あなたはmappedByを使用しないので、私は同じ結果、すなわち双方向オブジェクトマッピング –

+0

を取得しているので、mappedByをmany2manyに対して同じものを使用しないでon2manyとmany2oneを使用することはできません。 – Cherif

+0

clear!私にいくつかの例を教えてください。 –

4

mappedby =

注」は、別のクラスで作成した同じクラスのエンティティのオブジェクト」:一つのテーブルに外部キー制約を含んでいなければならないので、唯一のクラスで使用することができるによって-mappedに適用することができるによってマッピングされた場合両方の側は、それは/ wの二つの表Bは関係がない両方のテーブルから外部キーなし外部キーを削除

注: - それは、以下の注釈のために使用することができる: - 1 @ OneTone 2 @ OneToMany 3. @ ManyToMany

注--- - 1. @ ManyToOne

1対1の場合: - マッピングのいずれかの側で実行しますが、一方の側でのみ実行します。 これは、それが適用されるクラスのテーブルの外部キー制約の余分な列を削除します。

たとえば、従業員オブジェクトのEmployeeクラスにマップされている場合、Employeeテーブルの外部キーは削除されます。

0

ManyToOneマッピングを開始した後、BiToirectionalな方法でOneToManyマッピングを配置します。 次に、OneToMany側(通常親テーブル/クラス)では、mappedBy(マッピングは子テーブル/クラスによって行われます)に言及する必要があるため、hibernateはDB内にEXTRAマッピングテーブルを作成しません(TableName = parent_childなど) 。