2012-06-09 17 views
14

मेरे पास दो वर्ग Foo और Bar हैं। डेटाबेस में तालिकाओं इस तरह दिखेगा:समग्र प्राथमिक कुंजी, विदेशी कुंजी। ऑब्जेक्ट या कुंजी का संदर्भ?

|Foo| 
|id : INT (PK) | bar_id : INT (PK, FK) | 

|Bar| 
|id : INT (PK) | 

आम तौर पर मैं इसे इस तरह के नक्शे होगा:

@Entity 
public class Bar 
{ 
    @Id 
    @Column(name = "id") 
    private int id; 

    @OneToMany 
    private Set<Foo> foo; 
} 

@Entity 
public class Foo 
{ 
    @EmbeddedId 
    private FooPK key; 

    @MapsId("barId") 
    @ManyToOne 
    @JoinColumn(name = "bar_id", referencedColumnName = "id") 
    private Bar bar; 
} 

@Embeddable 
public class FooPK 
{ 
    @Column(name = "id") 
    private int id; 
    @Column(name = "bar_id") 
    private int barId; 
} 

हालांकि FooPK में आईडी के शिथिल मैप किया और मैन्युअल रूप से कनेक्ट करने की आवश्यकता कर रहे हैं। मैं एक समाधान पसंद करूंगा जो ढीले आईडी के स्थान पर ऑब्जेक्ट्स का उपयोग कर मानचित्र बनाता है। मैंने कोशिश की निम्नलिखित लेकिन यह काम नहीं किया है (बेशक), लेकिन मैं इसे मैं प्राप्त करना चाहते हैं की एक विचार देता है लगता है:

@Entity 
public class Bar 
{ 
    @Id 
    @Column(name = "id") 
    private int id; 

    @OneToMany 
    private Set<Foo> foo; 
} 

@Entity 
public class Foo 
{ 
    @EmbeddedId 
    private FooPK key; 

    @MapsId("barId") 
    @ManyToOne 
    @JoinColumn(name = "bar_id", referencedColumnName = "id") 
    @Access(AccessType.FIELD) 
    private Bar getBar() 
    { 
     return key.getBar(); 
    } 
} 

@Embeddable 
public class FooPK 
{ 
    @Column(name = "id") 
    private int id; 

    @Transient 
    private Bar bar; 

    //.... 

    @Column(name = "bar_id") 
    @Access(AccessType.PROPERTY) 
    private int getBarId 
    { 
     return bar.getId(); 
    } 
} 

बाद समाधान के साथ एक और समस्या यह है कि में getBarId() विधि FooPK को setBarId(Int) विधि की आवश्यकता है। आईडी का उपयोग करके ऑब्जेक्ट को सेट करना डेटा एक्सेस लेयर तक पहुंच कर किया जा सकता है, हालांकि यह (मेरी राय में) व्यवसाय/डोमेन/डेटा परतों को अलग करने का उल्लंघन करता है।

तो क्या करना है? पहले समाधान के साथ जाएं और आईडी को मैन्युअल रूप से सिंक में रखें या क्या कोई और (सर्वोत्तम) अभ्यास है?

उत्तर

23

JPA 2: composite primary key classes चर्चा का जिक्र करते हुए, फू और FooPK कक्षाओं में निम्न परिवर्तन:

@Entity 
public class Foo { 

    @EmbeddedId 
    private FooPK key; 

    @MapsId("barId") //references EmbeddedId's property 
    @JoinColumn(name = "bar_id", referencedColumnName = "id") 
    @ManyToOne 
    private Bar bar; 
} 

@Embeddable 
public class FooPK { 

    @Column(name = "id") 
    private int id; 
    @Column(name = "bar_id") 
    private int barId; 
} 

मैं पहली बार यह क्षेत्र का उपयोग के साथ काम करते हैं और उसके बाद संपत्ति का उपयोग लागू करने का सुझाव।

तो क्या करना है? पहले समाधान के साथ जाएं और आईडी को मैन्युअल रूप से सिंक में रखें या क्या कोई और (सर्वोत्तम) अभ्यास है?

दर्द से खुद को बचाएं - स्वचालित रूप से आईडी उत्पन्न करें।

+0

तो यह पहला उदाहरण है। मैंने देखा है कि यह 'जाने का रास्ता' है, मैं बस सोच रहा था कि दूसरा उदाहरण एक क्लीनर तरीका था। मुझे लगता है कि फिर कोई नहीं है? – siebz0r

+0

@ siebz0r ओह, क्षमा करें, ध्यान नहीं दिया कि पहला उदाहरण वही था; ओ। मुझे लगता है कि पीके को देखना आसान है जब आईडी हैं, वस्तुओं को मैप नहीं किया गया है। यदि आप FooPK द्वारा खोजना चाहते थे, तो आपको केवल सभी पूर्णांक की आवश्यकता होगी, न कि ऑब्जेक्ट्स सभी अनावश्यक गुणों के साथ। – JMelnik

संबंधित मुद्दे