Hibernate 一对一主键单向关联

1-1的关联可以基于主键关联,但基于主键关联的持久化类不能拥有自己的主键生成策略,它的主键由关联类负责生成。另外,另外,增加one-to-one元素来关联属性,必须为one-to-one元素增加constrained="true"属性,表明该类主键由关联类生成。

一、模型介绍

一个人(Person)对应一个地址(Address)。

二、实体(省略getter、setter方法)

publicclassPerson11pk{

privateintpersonid;

privateStringname;

privateintage;

privateAddress11pkaddress11pk;

publicclassAddress11pk{

privateintaddressid;

privateStringaddressdetail;

三、表模型

mysql>descaddress_11pk;

+---------------+--------------+------+-----+---------+----------------+

|Field|Type|Null|Key|Default|Extra|

+---------------+--------------+------+-----+---------+----------------+

|addressid|int(11)|NO|PRI|NULL|auto_increment|

|addressdetail|varchar(255)|YES||NULL||

+---------------+--------------+------+-----+---------+----------------+

mysql>descperson_11pk;

+----------+--------------+------+-----+---------+-------+

|Field|Type|Null|Key|Default|Extra|

+----------+--------------+------+-----+---------+-------+

|personid|int(11)|NO|PRI|||

|name|varchar(255)|YES||NULL||

|age|int(11)|YES||NULL||

+----------+--------------+------+-----+---------+-------+

四、生成的SQL脚本

/*Formattedon2007/08/2214:40(QP5v5.50)*/

CREATETABLE`address_11pk`(

`addressid`int(11)NOTNULLauto_increment,

`addressdetail`varchar(255)defaultNULL,

PRIMARYKEY(`addressid`)

)ENGINE=InnoDBAUTO_INCREMENT=2DEFAULTCHARSET=gbk;

/*Formattedon2007/08/2214:41(QP5v5.50)*/

CREATETABLE`person_11pk`(

`presonid`int(11)NOTNULL,

`name`varchar(255)defaultNULL,

`age`int(11)defaultNULL,

PRIMARYKEY(`presonid`),

KEY`FK68A882C591BB393E`(`presonid`),

CONSTRAINT`FK68A882C591BB393E`FOREIGNKEY(`presonid`)REFERENCES`address_11pk`(`addressid`)

)ENGINE=InnoDBDEFAULTCHARSET=gbk;

五、映射方法:在Person中配置id生成策略为:

<idname="personid">

<!--基于主键关联时,主键生成策略是foreign,表明根据关联类生成主键-->

<generatorclass="foreign">

<!--关联持久化类的属性名-->

<paramname="property">address11pk</param>

</generator>

</id>

......

<!--用于映射1-1关联-->

<one-to-onename="address11pk"constrained="true"/>

<hibernate-mapping>

<classname="com.lavasoft.dx._1_1_pk.Person11pk"table="PERSON_11pk">

<idname="personid"column="presonid">

<!--基于主键关联时,主键生成策略是foreign,表明根据关联类生成主键-->

<generatorclass="foreign">

<!--关联持久化类的属性名-->

<paramname="property">address11pk</param>

</generator>

</id>

<propertyname="name"/>

<propertyname="age"/>

<!--用于映射1-1关联-->

<one-to-onename="address11pk"constrained="true"/>

</class>

</hibernate-mapping>

<hibernate-mapping>

<classname="com.lavasoft.dx._1_1_pk.Address11pk"table="ADDRESS_11pk">

<idname="addressid">

<generatorclass="identity"/>

</id>

<propertyname="addressdetail"/>

</class>

</hibernate-mapping>

六、测试方法

publicclassTest_11pk{

publicstaticvoidmain(String[]args){

Person11pkp1=newPerson11pk();

p1.setAge(21);

p1.setName("p1");

Address11pkadd1=newAddress11pk();

add1.setAddressdetail("郑州市经三路");

p1.setAddress11pk(add1);

Sessionsession=HibernateUtil.getCurrentSession();

Transactiontx=session.beginTransaction();

session.save(add1);

session.save(p1);

tx.commit();

HibernateUtil.closeSession();

}

}

七、测试结果

1):正常保存.推荐这么干!

session.save(add1);

session.save(p1);

Hibernate:insertintoADDRESS_11fk(addressdetail)values(?)

Hibernate:insertintoPERSON_11fk(name,age,addressId)values(?,?,?)

2):正常保存.

session.save(p1);

session.save(add1);

Hibernate:insertintoPERSON_11fk(name,age,addressId)values(?,?,?)

Hibernate:insertintoADDRESS_11fk(addressdetail)values(?)

Hibernate:updatePERSON_11fksetname=?,age=?,addressId=?wherepersonid=?

3):正常保存.

//session.save(p1);

session.save(add1);

Hibernate:insertintoADDRESS_11fk(addressdetail)values(?)

4):发生异常,不能保存.

session.save(p1);

//session.save(add1);

Hibernate:insertintoPERSON_11fk(name,age,addressId)values(?,?,?)

Exceptioninthread"main"org.hibernate.TransientObjectException:com.lavasoft.dx._1_1_fk.Address11fk

本文出自“熔岩”博客,转载请与作者联系!

相关推荐