hibernate 共享的主键关联(多个表共享一个主键)

共享的主键关联:
由主键关联而相关的两张表中的行共享相同的主键值。这种方法的主要困难在于,确保被关联的
实例在保存对象时分配了相同的主键值。
第一步:用xml映射主键关联
  1. <classname="User"
  2. ....
  3. <one-to-one name="address"class="Address"cascade="update">
  4. </one-to-one>

第二步:外标识符生成器
如果Address实例被保存,它就需要获取User对象的主键值。你无法启动一个常规的标示符生成器,
假设是数据库序列。用于Address的这个特殊的foreign标示符生成器,必须知道从哪里获取正确
的主键值。
创建Address和User之间的这个标示符绑定,起第一步是双向关联。把一个新的user属性添加
到Address属性:
  1. <classname="Address"
  2. ...
  3. <one-to-one name="user"class="User"constrained="true"/>

这个映射让关联变成了双向,constrained="true"声明了把address的主键添加到user主键的外键约束。
现在可以给Address对象使用特殊的foreign标示符生成器了:
  1. <classname="Address"table="ADDRESS">
  2. <id name="addressId"column="ADDRESS_ID"type="long">
  3. <generatorclass="foreign">
  4. <param name="property">user</param>
  5. </generator>
  6. </id>
  7. <property name="street"type="string"column="street"/>
  8. <property name="city"type="string"column="city"/>
  9. <one-to-one name="user"class="User"constrained="true"/>
  10. </class>

(当Address被保存时,从属性中提取主键值。user属性是对User对象的一个引用;因而,插入的主键值与
这个实例的主键值相同。)
需要双向才可以保存成功:
  1. User user =newUser();
  2. user.setUserName("test");
  3. Address address =newAddress("street","city");
  4. user.setAddress(address);
  5. //不添加报错:attempted to assign id from null one-to-one property: user
  6. address.setUser(user);
  7. Integer msgId = (Integer) session.save(user);





利用注解的共享主键:
JPA用@OneToOne注解支持一对一的实体关联。要映射User类中address的关联为共享主键关联,还需要@PrimaryKeyJoinColumn注解:
  1. @Entity
  2. publicclassUserimplementsSerializable {
  3. @Id
  4. @GeneratedValue
  5. privateInteger userId;
  6. @Column(name="USER_NAME",length=100)
  7. privateString userName;
  8. @OneToOne(cascade=CascadeType.PERSIST)
  9. @PrimaryKeyJoinColumn
  10. privateAddress address;

JPA规范没有包括处理共享主键生成问题的标准方法,这意味着在保存Address实例的标示符之前,你要负责正确的设置他。
hibernate的扩展注解:
  1. @Entity
  2. publicclassAddressimplementsSerializable {
  3. @Id
  4. @GeneratedValue(generator="userForeignGenerator")
  5. @org.hibernate.annotations.GenericGenerator(name="userForeignGenerator",
  6. strategy="foreign",
  7. parameters=@Parameter(name="property",value="user"))
  8. @Column(name="ADDRESS_ID")
  9. privateInteger addressId;
  10. privateString street;
  11. privateString city;
  12. @OneToOne
  13. privateUser user;

保存:
  1. User user =newUser("name");
  2. Address address =newAddress("street","city");
  3. user.setAddress(address);
  4. //不添加报错:attempted to assign id from null one-to-one property: user
  5. address.setUser(user);
  6. em.persist(user);

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值