JPA中的一对一双向联系关系(二)

JPA中的一对一双向关联(二)

IDCard.java

Java代码 JPA中的一对一双向联系关系(二)
  1. package cn.itcast.bean;   
  2.   
  3. import javax.persistence.CascadeType;   
  4. import javax.persistence.Column;   
  5. import javax.persistence.Entity;   
  6. import javax.persistence.GeneratedValue;   
  7. import javax.persistence.Id;   
  8. import javax.persistence.OneToOne;   
  9.   
  10. @Entity  
  11. public class IDCard {   
  12.     private Integer id;   
  13.     private String cardNo;   
  14.     private Person person;   
  15.   
  16.     public IDCard() {   
  17.     }   
  18.   
  19.     public IDCard(String cardNo) {   
  20.         this.cardNo = cardNo;   
  21.     }   
  22.   
  23.     @Id  
  24.     @GeneratedValue  
  25.     public Integer getId() {   
  26.         return id;   
  27.     }   
  28.   
  29.     public void setId(Integer id) {   
  30.         this.id = id;   
  31.     }   
  32.   
  33.     @Column(length = 18,nullable=false)   
  34.     public String getCardNo() {   
  35.         return cardNo;   
  36.     }   
  37.   
  38.     public void setCardNo(String cardNo) {   
  39.         this.cardNo = cardNo;   
  40.     }   
  41.   
  42.     @OneToOne(mappedBy = "idCard", cascade = { CascadeType.PERSIST,   
  43.             CascadeType.MERGE, CascadeType.REFRESH } /*,optional = false*/)   
  44.     public Person getPerson() {   
  45.         return person;   
  46.     }   
  47.     /*  
  48.     mappedBy:如何把IDCard指定为关系被维护端? 就是通过这属性。使用了这属性的类,就是关系被维护端。被维护端没有权力去更新外键字段。  
  49.       
  50.     cascade:  
  51.         CascadeType.REMOVE:删除身份证,需要把这个人干掉吗? 不用,所以这个属性不设。  
  52.         CascadeType.PERSIST:一出生就有身份证号。  
  53.         CascadeType.MERGE:在游离状态的时候,修改了身份证号码,需要对人员的信息进行修改么?如果有这种业务需求,就设上去。  
  54.         CascadeType.REFRESH:重新获取idCard的数据的时候,需不需要获取person的数据呢?  
  55.     这些级联的定义,一定是根据你们的业务需求来定的。用不用是根据你的业务来决定的,业务需要就用,业务不需要就不用。  
  56.     optional:是否可选,是否允许为null?反映在业务上,就是有身份证,是否一定要有这个人呢?  
  57.     因為在Person里已经指定了idCard是必须要存在的,外键由person表维护,那么这里这个属性就是可选的的。设不设置这个person属性都行。那么在这里option这属性就可以不再进行设置了,不设置不对我们的数据构成任何影响,person可有可无不对关系(外键)存在影响。  
  58.     外键由Person的option属性决定,就算你设置了这属性,其实它也不看你这属性。在设外键字段是否允许为空的时候,也不看这属性,而是看关系维护端的设定。  
  59.     fetch:加载行为默认为立刻记载,凭one。  
  60.     */  
  61.   
  62.     public void setPerson(Person person) {   
  63.         this.person = person;   
  64.     }   
  65. }  

 
Person.java 

Java代码 JPA中的一对一双向联系关系(二)
  1. package cn.itcast.bean;   
  2.   
  3. import javax.persistence.CascadeType;   
  4. import javax.persistence.Column;   
  5. import javax.persistence.Entity;   
  6. import javax.persistence.GeneratedValue;   
  7. import javax.persistence.Id;   
  8. import javax.persistence.JoinColumn;   
  9. import javax.persistence.OneToOne;   
  10.   
  11. @Entity  
  12. public class Person {   
  13.     private Integer id;   
  14.     private String name;   
  15.     private IDCard idCard;   
  16.   
  17.     public Person() {   
  18.     }   
  19.   
  20.     @Id  
  21.     @GeneratedValue  
  22.     // 采用数据库Id自增长方式来生成主键值。   
  23.     public Integer getId() {   
  24.         return id;   
  25.     }   
  26.   
  27.     public void setId(Integer id) {   
  28.         this.id = id;   
  29.     }   
  30.   
  31.     @Column(length = 10, nullable = false)   
  32.     public String getName() {   
  33.         return name;   
  34.     }   
  35.   
  36.     public void setName(String name) {   
  37.         this.name = name;   
  38.     }   
  39.   
  40.     @OneToOne(optional = false, cascade = CascadeType.ALL)   
  41.     @JoinColumn(name = "idCard_id")   
  42.     public IDCard getIdCard() {   
  43.         return idCard;   
  44.     }   
  45.   
  46.     public void setIdCard(IDCard idCard) {   
  47.         this.idCard = idCard;   
  48.     }   
  49.   
  50.     public Person(String name) {   
  51.         this.name = name;   
  52.     }   
  53. }   


OneToOneTest.java 

Java代码 JPA中的一对一双向联系关系(二)
  1. package junit.test;   
  2.   
  3. import javax.persistence.EntityManager;   
  4. import javax.persistence.EntityManagerFactory;   
  5. import javax.persistence.Persistence;   
  6.   
  7. import org.junit.BeforeClass;   
  8. import org.junit.Test;   
  9.   
  10. import cn.itcast.bean.IDCard;   
  11. import cn.itcast.bean.Person;   
  12.   
  13. public class OneToOneTest {   
  14.   
  15.     @BeforeClass  
  16.     public static void setUpBeforeClass() throws Exception {   
  17.     }   
  18.   
  19.     @Test  
  20.     public void save() {   
  21.         EntityManagerFactory factory = Persistence   
  22.                 .createEntityManagerFactory("itcast");   
  23.         EntityManager em = factory.createEntityManager();   
  24.         em.getTransaction().begin();   
  25.   
  26.         Person person = new Person("小叶");   // person是关系维护端。   
  27.         person.setIdCard(new IDCard("19881210"));    // 通过person把idCard放进去,这关系就由person来维护了。   
  28.         em.persist(person); // 先保存idCard,得到保存记录的id,用id作为外键的值,再保存person。因为person表里的外键值是idcard表里面的主键,只有先生成主键值才有外键值。   
  29.   
  30.         em.getTransaction().commit();   
  31.         em.close();   
  32.         factory.close();   
  33.     }   
  34.   
  35. }  

 
   谁是关系维护端,谁就负责外键字段的更新。
   Person是关系维护端,IDCard是关系被维护端,怎么维护更新呢?往Person里面设置idCard,这样就相当于把关系建立起来了;如果通过IDCard设置person的话,那么这种关系是建立不起来的,因为IDCard是关系被维护端