通過為<id>元素增加<generator>子元素,該子元素具有class屬性。經常使用的class屬性有:
(1)increment:用于為long、short、或int類型生成唯1標識。只有在沒有其他進程往同1張表中插入數據的時候才能使用。在集群不要使用。(極少使用)
(2)native:讓數據庫自動選擇identity,sequence,或其他。
(3)uuid:128位的UUID算法,產生String類型ID
(4)identity:對DB2、MySQL、SQL Server、Sybase和HypersonicSQL的內置標識字段提供支持。返回的標識符是long、short或int類型。
sequence:在Oracel,PostgreSQL,SAP,DB,Mckio中使用序列(sequence),而在Interbase中使用生成器(generator),返回的標識符是long、short或是int類型。
小實驗1:
(1)創建Student.java
package com.zgy.hibernate.model;
public class Student {
private String id;
private String name;
private int age;
private int score;
public int getScore() {
return score;
}
public void setScore(int score) {
this.score = score;
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
(2)在Student.hbm.xml中,為<id>配置其generator的class為uuid
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-mapping⑶.0.dtd">
<hibernate-mapping package="com.zgy.hibernate.model">
<class name="Student" table="student">
<id name="id" column="id">
<generator class="uuid"></generator>
</id>
<property name="name" column="name"></property>
<property name="age" column="age"></property>
<property name="score" column="score"></property>
</class>
</hibernate-mapping>
(3)測試
package com.zgy.hibernate.model;
import static org.junit.Assert.*;
import java.util.Date;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.AnnotationConfiguration;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;
public class HibernateIDTest {
public static SessionFactory sf = null;
@BeforeClass
public static void beforeClass(){
sf = new AnnotationConfiguration().configure().buildSessionFactory();
}
@Test
public void testStudent() {
Student s = new Student();
s.setName("張3");
s.setAge(20);
s.setScore(90);
Session session = sf.openSession();
session.beginTransaction();
session.save(s);
session.getTransaction().commit();
session.close();
}
@AfterClass
public static void afterClass(){
sf.close();
}
}
(4)驗證
select * from student;
+-----------------------------------------------+--------+------+------+
| id | name | age | score |
+------------------------------------------------+------+-------+------+
| 4028dae54aa322d1014aa322d5a50000 | 張3 | 20 | 90 |
+----------------------------------+------+-----+-------+------+------+
desc student;
數據插入成功,id類型為varchar(255),主鍵
小實驗2:
(1)修改Student.java。將id修改成int類型
package com.zgy.hibernate.model;
public class Student {
private int id;
private String name;
private int age;
private int score;
public int getScore() {
return score;
}
public void setScore(int score) {
this.score = score;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
(2)在Student.hbm.xml中,為<id>配置其generator的class為native
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-mapping⑶.0.dtd">
<hibernate-mapping package="com.zgy.hibernate.model">
<class name="Student" table="student">
<id name="id" column="id">
<generator class="native"></generator>
</id>
<property name="name" column="name"></property>
<property name="age" column="age"></property>
<property name="score" column="score"></property>
</class>
</hibernate-mapping>
(3)測試(刪除student表)
(4)驗證
select * from student;
+----+------+-------+-------+
| id | name | age | score |
+----+------+-------+-------+
| 1 | 張3 | 20 | 90 |
+----+------+-----+--------+
desc student;
數據插入成功,id為int(11)類型,主鍵,Auto_increment
@GeneratedValue,默許的策略是auto,auto相當于XML中配置的native。
小實驗1:
(1)編寫Teacher.java。在getId()方法上添加@GeneratedValue
package com.zgy.hibernate.model;
import java.util.Date;
import javax.annotation.Generated;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.EnumType;
import javax.persistence.Enumerated;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Table;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;
import javax.persistence.Transient;
@Entity
@Table(name="_teacher")
public class Teacher {
private int id;
private String name;
private String title;
private String address;
private String wifeName;
private Date birth;
private ZhiCheng zhiCheng;
@Id
@GeneratedValue
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
@Column(name="_name")
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
public String getWifeName() {
return wifeName;
}
public void setWifeName(String wifeName) {
this.wifeName = wifeName;
}
@Temporal(TemporalType.DATE)
public Date getBirth() {
return birth;
}
public void setBirth(Date birth) {
this.birth = birth;
}
@Enumerated(EnumType.STRING)
public ZhiCheng getZhiCheng() {
return zhiCheng;
}
public void setZhiCheng(ZhiCheng zhiCheng) {
this.zhiCheng = zhiCheng;
}
}
(2)編寫TeacherTesting.java,用于測試
package com.zgy.hibernate.model;
import static org.junit.Assert.*;
import java.util.Date;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.AnnotationConfiguration;
import org.hibernate.cfg.Configuration;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;
public class TeacherTesting {
public static SessionFactory sf = null;
@BeforeClass
public static void beforeClass(){
sf = new AnnotationConfiguration().configure().buildSessionFactory();
}
@Test
public void test() {
Teacher t = new Teacher();
t.setName("t1");
t.setTitle("高級");
t.setAddress("北京");
t.setBirth(new Date());
t.setZhiCheng(ZhiCheng.A);
Session session = sf.openSession();
session.beginTransaction();
session.save(t);
session.getTransaction().commit();
session.close();
}
@AfterClass
public static void afterClass(){
sf.close();
}
}
(3)驗證
select * from _teacher;
desc _teacher;
數據插入成功,id為int(11),主鍵,auto_increment
在使用Annotation的時候,除使用auto策略,還可使用increment,identity,sequence,table等等。
小實驗2:
(1)修改Teacher.java.修改策略為identity
package com.zgy.hibernate.model;
import java.util.Date;
import javax.annotation.Generated;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.EnumType;
import javax.persistence.Enumerated;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;
import javax.persistence.Transient;
@Entity
@Table(name="_teacher")
public class Teacher {
private int id;
private String name;
private String title;
private String address;
private String wifeName;
private Date birth;
private ZhiCheng zhiCheng;
@Id
@GeneratedValue(strategy=GenerationType.IDENTITY)
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
@Column(name="_name")
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
public String getWifeName() {
return wifeName;
}
public void setWifeName(String wifeName) {
this.wifeName = wifeName;
}
@Temporal(TemporalType.DATE)
public Date getBirth() {
return birth;
}
public void setBirth(Date birth) {
this.birth = birth;
}
@Enumerated(EnumType.STRING)
public ZhiCheng getZhiCheng() {
return zhiCheng;
}
public void setZhiCheng(ZhiCheng zhiCheng) {
this.zhiCheng = zhiCheng;
}
}
(2)測試
(3)驗證
select * from _teacher;
desc _teacher;
使用table策略:
@javax.persistence.TableGenerator(
name="Teacher_GEN",
table="GENERATOR_TABLE",
pkColumnName="pkkey",
valueColumnName="pkvalue",
pkColumnValue="Teacher",
allocationSize=1
)
以上Annotation的意義:首先是定義了1個generator,該generator的名字叫做Teacher_GEN,生成1張表,表名為GENERATOR_TABLE,該表有兩個字段,分別為pkColumnName和valueColumnName。這個表的第1條數據是:Teacher , 1。其下1條數據的步長值,即Teacher表的下1條數據的值會是2
小實驗3:
(1)修改Teacher.java類
package com.zgy.hibernate.model;
import java.util.Date;
import javax.annotation.Generated;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.EnumType;
import javax.persistence.Enumerated;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;
import javax.persistence.Transient;
@Entity
@javax.persistence.TableGenerator(
name="Teacher_GEN",
table="GENERATOR_TABLE",
pkColumnName="pkkey",
valueColumnName="pkvalue",
pkColumnValue="Teacher",
allocationSize=1
)
public class Teacher {
private int id;
private String name;
private String title;
private String address;
private String wifeName;
private Date birth;
private ZhiCheng zhiCheng;
@Id
@GeneratedValue(strategy=GenerationType.TABLE,generator="Teacher_GEN")
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
@Column(name="_name")
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
public String getWifeName() {
return wifeName;
}
public void setWifeName(String wifeName) {
this.wifeName = wifeName;
}
@Temporal(TemporalType.DATE)
public Date getBirth() {
return birth;
}
public void setBirth(Date birth) {
this.birth = birth;
}
@Enumerated(EnumType.STRING)
public ZhiCheng getZhiCheng() {
return zhiCheng;
}
public void setZhiCheng(ZhiCheng zhiCheng) {
this.zhiCheng = zhiCheng;
}
}
(2)測試
(3)驗證
查看hibernate履行進程中產生的sql語句
Hibernate: select pkvalue from GENERATOR_TABLE where pkkey = 'Teacher' for update
Hibernate: insert into GENERATOR_TABLE(pkkey, pkvalue) values('Teacher', ?)
Hibernate: update GENERATOR_TABLE set pkvalue = ? where pkvalue = ? and pkkey = 'Teacher'
Hibernate: select pkvalue from GENERATOR_TABLE where pkkey = 'Teacher' for update
Hibernate: update GENERATOR_TABLE set pkvalue = ? where pkvalue = ? and pkkey = 'Teacher'
Hibernate: insert into Teacher (address, birth, _name, title, wifeName, zhiCheng, id) values (?, ?, ?, ?, ?, ?, ?)
查看數據表
select * from generator_table;
select * from teacher;
下一篇 A/B測試與灰度發布