Mapping collections of value types (from 《hibernate in action》chapter 6)
這里所舉的例子,都是基于這樣的一個(gè)情景,Item中包含有Images。
<set name="images" lazy="true" table="ITEM_IMAGE">
<key column="ITEM_ID"/>
<element type="string" column="FILENAME" not-null="true"/>
</set>
這里的<key>定義了外鍵ITEM_ID,<elememt>則聲明了集合的內(nèi)部數(shù)據(jù)元素。<set>定義的集合中不可以有重復(fù)的數(shù)據(jù)。
<idbag name="images" lazy="true" table="ITEM_IMAGE">
<collection-id type="long" column="ITEM_IMAGE_ID">
<generator class="sequence"/>
</collection-id>
<key column="ITEM_ID"/>
<element type="string" column="FILENAME" not-null="true"/>
</idbag>
ITEM_IMAGE_ID為主鍵,而ITEM_ID則為外鍵,<element>元素不變,這就允許集合中的數(shù)據(jù)重復(fù)。
<list name="images" lazy="true" table="ITEM_IMAGE">
<key column="ITEM_ID"/>
<index column="POSITION"/>
<element type="string" column="FILENAME" not-null="true"/>
</list>
這里為ITEM_IMAGE表添加了index,整個(gè)表的主鍵是ITEM_ID和POSITION構(gòu)成的復(fù)合主鍵,它允許集合中的數(shù)據(jù)根據(jù)POSITION進(jìn)行排序。
<map name="images"
lazy="true"
table="ITEM_IMAGE"
sort="natural">
<key column="ITEM_ID"/>
<index column="IMAGE_NAME" type="string"/>
<element type="string" column="FILENAME" not-null="true"/>
</map>
這里為ITEM_IMAGE表添加了index,整個(gè)表的主鍵是ITEM_ID和POSITION構(gòu)成的復(fù)合主鍵,它允許集合中的數(shù)據(jù)根據(jù)sort指定的內(nèi)容進(jìn)行排序,這里允許用戶對(duì)sort進(jìn)行定制。
<map name="images"
lazy="true"
table="ITEM_IMAGE"
order-by="IMAGE_NAME asc">
<key column="ITEM_ID"/>
<index column="IMAGE_NAME" type="string"/>
<element type="string" column="FILENAME" not-null="true"/>
</map>
這里采用的是orbder-by,注意sort和order-by的區(qū)別。Sort是在內(nèi)存中使用comparator進(jìn)行排序,而order-by則是在數(shù)據(jù)庫(kù)中使用SQL語句進(jìn)行排序。
<set name="images"
lazy="true"
table="ITEM_IMAGE"
order-by="IMAGE_NAME asc">
<key column="ITEM_ID"/>
<composite-element class="Image">
<property name="name" column="IMAGE_NAME" not-null="true"/>
<property name="filename" column="FILENAME" not-null="true"/>
<property name="sizeX" column="SIZEX" not-null="true"/>
<property name="sizeY" column="SIZEY" not-null="true"/>
</composite-element>
</set>
這里定義了一個(gè)新的Image類,它不是實(shí)體類(entity class),而是一個(gè)簡(jiǎn)單的值類型(value type),僅僅是父實(shí)體的一個(gè)component,其生命周期完全由包含其的父實(shí)體 (parent entity) ITEM控制。這里Image類中包含有數(shù)據(jù)ITEM_ID、 IMAGE_NAME、FILENAME、SIZEX、和SIZEY。
<set name="images"
lazy="true"
table="ITEM_IMAGE"
order-by="IMAGE_NAME asc">
<key column="ITEM_ID"/>
<composite-element class="Image">
<parent name="item"/>
<property name="name" column="IMAGE_NAME" not-null="true"/>
<property name="filename" column="FILENAME" not-null="true"/>
<property name="sizeX" column="SIZEX" not-null="true"/>
<property name="sizeY" column="SIZEY" not-null="true"/>
</composite-element>
</set>
前面定義的IMAGE類中,并不包含有對(duì)父實(shí)體ITEM的引用。也就是說,只可以從ITEM中導(dǎo)航到IMAGE中,但是在IMAGE無法得到ITEM。這可以通過<parent>實(shí)現(xiàn)。這樣IMAGE類中就含有一個(gè)數(shù)據(jù)成員item,指向其父實(shí)體。
但是,它是無法做到真正的雙向?qū)Ш降?。例如:通過SQL查詢直接得到IMAGE后,但是如同普通的值類型一樣,IMAGE對(duì)象的item是null,你無法從component如此直接得到其父對(duì)象,這必須由通過父-子關(guān)系的entity完成。