hibernate的主键生成策略

 hibernate的主键生成器

   generator元素:表示了一个主键生成器,它用来为持久化类实例生成唯一的标识 。

  

  1.不同的控制类型

  1.1 assigned:  程序员自己控制,与数据库自增无关
  1.2 identity(标识列/自动增长)  sequence  数据库控制自增,与程序员赋值无关
  1.4 increment:   hibernate控制,与程序员赋值无关,与数据库自增也无关,但值是根据数据库最后一位自增
      uuid/uuid.hex: hibernate控制,生成String类型的id
 
 

2.实例代码

2.1 新建实体类

 Student

 1 package com.yuan.two.entity;
 2 
 3 public class Student {
 4 
 5     private Integer sid;
 6     private String sname;
 7     public Integer getSid() {
 8         return sid;
 9     }
10     public void setSid(Integer sid) {
11         this.sid = sid;
12     }
13     public String getSname() {
14         return sname;
15     }
16     public void setSname(String sname) {
17         this.sname = sname;
18     }
19     @Override
20     public String toString() {
21         return "Student [sid=" + sid + ", sname=" + sname + "]";
22     }
23     public Student(Integer sid, String sname) {
24         super();
25         this.sid = sid;
26         this.sname = sname;
27     }
28     public Student() {
29         super();
30         // TODO Auto-generated constructor stub
31     }
32     
33     
34 }

  Worker  

package com.yuan.two.entity;

public class Worker {

    private String  wid;
    private String wname;
    public String getWid() {
        return wid;
    }
    public void setWid(String wid) {
        this.wid = wid;
    }
    public String getWname() {
        return wname;
    }
    public void setWname(String wname) {
        this.wname = wname;
    }
    @Override
    public String toString() {
        return "Worker [wid=" + wid + ", wname=" + wname + "]";
    }
    public Worker(String wid, String wname) {
        super();
        this.wid = wid;
        this.wname = wname;
    }
    public Worker() {
        super();
        // TODO Auto-generated constructor stub
    }
    
    
    
}

  2.2 配置实体类对应的映射文件

  Student.hbm.xml

 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <!DOCTYPE hibernate-mapping PUBLIC 
 3     "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
 4     "http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
 5 <hibernate-mapping>
 6     <class name="com.yuan.two.entity.Student" table="t_hibernate_student">
 7         <id name="sid" type="java.lang.Integer" column="sid">
 8             <!-- <generator class="assigned" /> -->
 9             <!-- <generator class="identity" /> -->
10              <!-- <generator class="increment" /> -->
11              <generator class="sequence" /> 
12             <!-- <generator class="sequence" > <param name="sequence_name">aaa</param> 
13                 </generator> -->
14             <!-- <generator class="com.javaxl.two.id.Myts" /> -->
15         </id>
16         <property name="sname" type="java.lang.String" column="sname">
17         </property>
18     </class>
19 </hibernate-mapping>

  Worker.hbm.xml

 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <!DOCTYPE hibernate-mapping PUBLIC 
 3     "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
 4     "http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
 5 <hibernate-mapping>
 6     <class name="com.yuan.two.entity.Worker" table="t_hibernate_worker">
 7         <id name="wid" type="java.lang.String" column="wid">
 8             <!-- <generator class="assigned" /> -->
 9             <generator class="uuid" />
10              <!-- <generator class="com.yuan.two.id.MyTsGenerator" />  -->
11             <!-- <generator class="sequence" > <param name="sequence_name">aaa</param> 
12                 </generator> -->
13             <!-- <generator class="com.javaxl.two.id.Myts" /> -->
14         </id>
15 
16         <property name="wname" type="java.lang.String" column="wname">
17         </property>
18     </class>
19 </hibernate-mapping>

  2.3 将实体映射文件配置到核心配置文件中  -  -  主键生成策略

  hibernate.cfg.xml

 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <!DOCTYPE hibernate-configuration PUBLIC
 3     "-//Hibernate/Hibernate Configuration DTD 3.0//EN"
 4     "http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">
 5     <hibernate-configuration>
 6       <session-factory>
 7         <!-- 1. 数据库相关 -->
 8         <property name="connection.username">root</property>
 9         <property name="connection.password">123</property>
10         <property name="connection.url">jdbc:mysql://localhost:3306/xm_sc?useUnicode=true&amp;characterEncoding=UTF-8
11         </property>
12         <property name="connection.driver_class">com.mysql.jdbc.Driver</property>
13         <property name="dialect">org.hibernate.dialect.MySQLDialect</property>
14 
15         <!-- 配置本地事务(No CurrentSessionContext configured!) -->
16         <property name="hibernate.current_session_context_class">thread</property>
17 
18         <!-- 2. 调试相关 -->
19         <property name="show_sql">true</property>
20         <property name="format_sql">true</property>
21 
22         <!-- 3. 添加实体映射文件 -->
23         <mapping resource="com/yuan/one/entity/User.hbm.xml" />
24         <!-- 主键生成策略 -->
25         <mapping resource="com/yuan/two/Student.hbm.xml" />
26         <mapping resource="com/yuan/two/Worker.hbm.xml"/>
27       </session-factory>
28     </hibernate-configuration>

2.4编写dao层测试类

DemoDao

 1 package com.yuan.two.dao;
 2 
 3 import org.hibernate.Session;
 4 import org.hibernate.Transaction;
 5 
 6 import com.yuan.two.entity.Student;
 7 import com.yuan.two.entity.Worker;
 8 import com.yuan.two.util.SessionFactoryUtils;
 9 
10 /**
11  * hibernate中的主键生成策略
12  * 1、人工控制
13  * 2、数据库控制
14  * 3、hibernate控制
15  * 4、自定义主键生成策略
16  * @author ly
17  *
18  */
19 public class DemoDao {
20 
21     /**
22      * 新增学生
23      * @param stu
24      */
25     public void addStudent(Student stu) {
26         //调用工厂助手类获取session会话
27         Session session = SessionFactoryUtils.openSession();
28         //获取事务对象
29         Transaction transaction = session.beginTransaction();
30         //操作数据库
31         session.save(stu);
32         //提交事务
33         transaction.commit();
34         //关闭session
35         SessionFactoryUtils.closeSession();
36     }
37     
38     /**
39      * 新增工人
40      * @param worker
41      */
42     public void addWorker(Worker worker) {
43         Session session = SessionFactoryUtils.openSession();
44         Transaction transaction = session.beginTransaction();
45         session.save(worker);
46         transaction.commit();
47         SessionFactoryUtils.closeSession();
48     }
49     
50         //测试代码
51     public static void testStudent() {
52         DemoDao dao = new DemoDao();
53         Student stu = new Student();
54         stu.setSname("源 2");
55         stu.setSid(76);
56         dao.addStudent(stu);
57     }
58     public static void main(String[] args) {
59         DemoDao dao = new DemoDao();
60         Worker worker = new Worker();
61         worker.setWname("小源儿ya");
62         dao.addWorker(worker);
63     }
64     
65     
66 }

    工厂辅助类

 

 1 package com.yuan.two.util;
 2 
 3 import org.hibernate.Session;
 4 import org.hibernate.SessionFactory;
 5 import org.hibernate.cfg.Configuration;
 6 
 7 
 8 /**
 9  * 仅在学习hibernate的工程中使用,当进入spring的学习后就没用了,后面会有ssh来替代它
10  * 作用:
11  *    用来检测hibernate中的配置文件的准确性,(hibernate.cfg.xml和*.hbm.xml)
12  * 
13  * 
14  * @author 刘源
15  *
16  */
17 public class SessionFactoryUtils {
18     private static SessionFactory sessionFactory;
19     static {
20         Configuration cfg = new Configuration().configure("/hibernate.cfg.xml");
21         sessionFactory = cfg.buildSessionFactory();
22     }
23     
24     public static Session openSession() {
25         //从本地的线程中获取session会话,第一次肯定是获取不到的,那么需要重新让sessionfactory创建一个session出来
26         //第二次就能够对第一次创建的session反复利用,节约性能
27         Session session = sessionFactory.getCurrentSession();
28         if(session == null) {
29             session = sessionFactory.openSession();
30         }
31         return session;
32     }
33     
34     public static void closeSession() {
35         Session session = sessionFactory.getCurrentSession();
36         if(session != null && session.isOpen()) {
37             session.close();
38         }
39     }
40     
41     public static void main(String[] args) {
42         Session session = SessionFactoryUtils.openSession();
43         session.beginTransaction();
44         System.out.println(session.isConnected());
45         SessionFactoryUtils.closeSession();
46         System.out.println(session.isConnected());
47     }
48 }

 

 

2.5  测试

assigned: 程序员自己控制,与数据库自增无关

映射文件内容

<id name="sid" type="java.lang.Integer" column="sid">
             <generator class="assigned" /> 
</id>

测试内容

public static void main(String[] args) {
        DemoDao dao = new DemoDao();
        Student stu = new Student();
        stu.setSname("源");
        stu.setSid(70);
        dao.addStudent(stu);
    }

测试结果

 

identity(标识列/自动增长)   sequence  (二选一)可自行测试不同,

--  数据库控制自增,与程序员赋值无关

identity 实体映射文件

 

<id name="sid" type="java.lang.Integer" column="sid">
            <generator class="identity" />
</id>

 

测试内容

public static void main(String[] args) {
        DemoDao dao = new DemoDao();
        Student stu = new Student();
        stu.setSname("源 2");
        stu.setSid(76);
        dao.addStudent(stu);
    }

测试结果    因误删数据导致数据多了一位 

 

increment   hibernate控制,与程序员赋值无关,

与数据库自增也无关,但值是根据数据库最后一位自增

 实体映射文件

 

<id name="sid" type="java.lang.Integer" column="sid">
            <generator class="increment" />
</id>

 

测试内容

public static void main(String[] args) {
        DemoDao dao = new DemoDao();
        Student stu = new Student();
        stu.setSname("xiao源");
        stu.setSid(76);
        dao.addStudent(stu);
    }

测试结果  

 

uuid/uuid.hex: hibernate控制,生成String类型的id

实体映射文件

<id name="sid" type="java.lang.Integer" column="sid">
            <generator class="uuid" />
</id>

 

测试内容

public static void main(String[] args) {
        DemoDao dao = new DemoDao();
        Worker worker = new Worker();
        worker.setWname("小源儿ya2");
        dao.addWorker(worker);
    }

测试结果

 

3.自定义主键生成器

新建 MyTsGenerator.java 并实现org.hibernate.id.IdentifierGenerator接口即可

 1 package com.yuan.two.id;
 2 
 3 import java.io.Serializable;
 4 import java.text.SimpleDateFormat;
 5 import java.util.Date;
 6 
 7 import org.hibernate.HibernateException;
 8 import org.hibernate.engine.spi.SharedSessionContractImplementor;
 9 import org.hibernate.id.IdentifierGenerator;
10 
11 public class MyTsGenerator implements IdentifierGenerator {
12 
13     @Override
14     public Serializable generate(SharedSessionContractImplementor arg0, Object arg1) throws HibernateException {
15         SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
16         
17         return "book_order_"+sdf.format(new Date());
18     }
19 
20 }

 实体映射文件填入类的全路径

<id name="sid" type="java.lang.Integer" column="sid">
            <generator class="com.yuan.two.id.MyTsGenerator" />
</id>

 

 测试内容

public static void main(String[] args) {
        DemoDao dao = new DemoDao();
        Worker worker = new Worker();
        worker.setWname("小源儿ya3");
        dao.addWorker(worker);
    }

测试结果

 

 谢谢观看!!!

 

posted @ 2019-08-03 22:24  Me*源  阅读(212)  评论(0编辑  收藏  举报