21-Java-Hibernate框架(一)
一、Hibernate了解
Hibernate框架是Java持久层的框架,是Gavin King发明的,2001年发布的,JBoss公司的产品,2003年进入市场。
Hibernate是基于对象来操作数据库的,但他最终还是被转换为SQL去进行操作
Hibernate对JDBC进行封装,简化数据库访问操作,采用ORM(Object Relation Mapping,对象关系映射)技术的持久层框架,自动实现表记录和实体对象之间的映射。
Hibernate与JDBC的区别:
Hibernate与JDBC都应用在持久层上,但Hibernate轻量级封装JDBC
Hibernate是自动的,不需要手写SQL语句的,它自动生成SQL语句,是面向对象的;
Mybatis是半自动的;
JDBC是手动的(需手写代码与数据库建立连接,获取对象,写SQL语句,执行SQL语句,返回结果,关闭连接),是面向过程的。
Hibernate体系结构:
1.框架工具包和驱动包
2.hibernate.cfg.xml
3.主配置文件,用于定义数据库连接参数
4.实体类(以entity为例)
5.映射描述文件entity.hbm.xml(这一步可以用注解代替)
6.定义类和表对应关系,属性和字段对应关系
二、Hibernate框架搭建(想要以下内容涉及的资源包的网友评论留言私聊,我百度网盘分享)
1.加载12个Hibernate包
dom4j-1.6.jar
geronimo-jta_1.2_spec-1.0-alpha-1.jar
hibernate-commons-annotations-4.0.5.Final.jar
hibernate-core-5.0.11.specid.jar
hibernate-jpa-2.1-api-1.0.2.Final.jar
javassist-3.18.0-ga-sources.jar
jboss-logging-3.3.0.Final.jar
mysql-connector-java-5.1.46.jar
slf4j-api-2.0.0-alpha1.jar
slf4j-jdk14-1.7.7.jar
slf4j-log4j12-1.7.5.jar
antlr-2.7.6.jar
将上述12个工具包放到web项目文件夹下的WebRoot/WEB-INF/lib/下
2.Hibernate两个配置文件(这一步也可以自己建xml文件配置参数,因为我之前建过,所以直接导入两个配置文件)
配置XML文件步骤:windows->preferences->XML->XML Catelog->add->location(找到dtd的位置)->key对应配置文件键值->OK
(1)*.hbm.xml 映射文件 建议放在entity/包下
(2)hibernate.cfg.xml 主配置文件 建议放在src/下
第一步:配置hibernate.cfg.xml文件(数据库连接信息,JDBC驱动,数据库dialect方言等)
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 6 <hibernate-configuration> 7 8 <session-factory> 9 <!--hibernate 方言 区分身份 --> 10 <property name="dialect">org.hibernate.dialect.MySQLDialect</property> 11 <!-- 数据库连接信息 --> 12 <property name="connection.driver_class">com.mysql.jdbc.Driver</property> 13 <property name="connection.url">jdbc:mysql://127.0.0.1:3306/hibernatetest</property> 14 <property name="connection.username">root</property> 15 <property name="connection.password">root</property> 16 17 <!-- hibernate自动生成表 --> 18 19 <!-- hibernate在控制台显示SQL语句 --> 20 <property name="show_sql">true</property> 21 <!-- hibernate格式化SQL,控制台看起来更整齐 --> 22 <property name="format_sql">true</property> 23 <!-- 设置自动提交 --> 24 <property name="connection.autocommit">true</property> 25 26 <!-- <property name="connection.characterEncoding">UTF-8</property> --> 27 <!--加载hibernate映射 --> 28 <mapping resource="com/hibernatetest/entity/User.hbm.xml" /> 29 30 </session-factory> 31 32 33 34 </hibernate-configuration>
第二步:配置*hbm.xml文件
1 <?xml version="1.0" encoding="UTF-8"?> 2 <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" 3 "http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd"> 4 <hibernate-mapping> 5 <!-- name:对应的实体类的权限定名称,table:对应数据库表名称 --> 6 <class name="com.hibernatetest.entity.User" table="hibernateUser"> 7 <!-- id标签用于配置主键属性 8 name:对应实体类中属性名称 9 type:可以省略,如果省略默认实体类中属性的对应类型 10 --> 11 <id name="uid" type="java.lang.Integer"> 12 <!-- column用于设置对应数据库表中字段名 13 name:数据库表中的字段名 14 length:设置字段长度 15 --> 16 <column name="u_id" length="32"></column> 17 <!-- generator用于设置主键生成策略 --> 18 <generator class="native"></generator> 19 </id> 20 21 <!-- property标签用于配置其他属性 22 name:对应实体类中属性名称 23 type:可以省略,如果省略默认实体类中属性的对应类型 24 --> 25 <property name="uname" column="u_name"> 26 <!-- column用于设置对应数据库表中字段名 27 name:数据库表中的字段名 28 length:设置字段长度 29 --> 30 <column name="u_name" ></column> 31 </property> 32 33 </class> 34 </hibernate-mapping>
三.使用Hibernate框架操作数据库(Hibernate有五大核心接口一个核心类)
Configuration:从hibernate.cfg.xml文件中加载主配置信息(数据库url,用户名,密码,jdbc驱动,数据库Dialect方言,数据库连接池,hibernate映射文件等)
SessionFactory:用于创建Session对象工厂,它可通过configuration创建得到,保存了数据库的配置信息和所有的映射关系
Session:用于执行数据库增删改查基本操作
Query和Criteria接口:用于负责执行各种数据的查询,它可以使用HQL语言或SQL语句两种表达方式
Transaction:用于事务控制(默认事务不自动提交)
Hibernate框架运行原理:
1.首先通过configuration去加载hibernate.cfg.xml这个配置文件
2.根据配置文件的信息去创建SessionFactory,SessionFactory是线程安全的,是一个session工厂
3.用SessionFactory来创建session,session不是线程安全的,通过session进行数据库的各种操作
4.在进行增删查改操作的时候通过Session打开Transaction进行事务的控制
1 public static void main(String[] args) { 2 //1.加载主配置文件 3 Configuration configuration = new Configuration().configure();//此处读取默认名称“hibernate.cfg.xml”,想要读取指定名称,需.configure("xxx.xml"); 4 5 //2.建造Session工厂 6 SessionFactory sessionfactory = configuration.buildSessionFactory(); 7 8 //3.获取Session,这个对象中提供了一套增删改查的方法 9 Session sess = sessionfactory.openSession(); 10 11 //4.查询获取对象 12 User user = sess.get(User.class, 1);//在数据库数据表中获取id为1的记录 13 System.out.println(user); 14 //5.释放session 15 sess.close(); 16 }
四、Session常用接口演示及Hibernate框架使用步骤
第一步:编写hibernate工具类
1 package HibernatenateUtils; 2 3 import org.hibernate.Session; 4 import org.hibernate.SessionFactory; 5 import org.hibernate.cfg.Configuration; 6 7 public class hibernateUtils { 8 public static Session getSession(){ 9 //1.加载主配置文件 10 Configuration configuration = new Configuration().configure(); 11 12 //2.建造Session工厂 13 SessionFactory sessfactory = configuration.buildSessionFactory(); 14 15 //3.获取Session,这个对象中提供了一套增删改查的方法 16 Session session = sessfactory.openSession(); 17 18 return session; 19 } 20 }
第二步:编写实体类
1 package com.hibernatetest.entity; 2 3 public class User { 4 private Integer uid; 5 private String uname; 6 public User() { 7 super(); 8 // TODO Auto-generated constructor stub 9 } 10 public User(Integer uid, String uname) { 11 super(); 12 this.uid = uid; 13 this.uname = uname; 14 } 15 public Integer getUid() { 16 return uid; 17 } 18 public void setUid(Integer uid) { 19 this.uid = uid; 20 } 21 public String getUname() { 22 return uname; 23 } 24 public void setUname(String uname) { 25 this.uname = uname; 26 } 27 @Override 28 public int hashCode() { 29 final int prime = 31; 30 int result = 1; 31 result = prime * result + ((uid == null) ? 0 : uid.hashCode()); 32 result = prime * result + ((uname == null) ? 0 : uname.hashCode()); 33 return result; 34 } 35 @Override 36 public boolean equals(Object obj) { 37 if (this == obj) 38 return true; 39 if (obj == null) 40 return false; 41 if (getClass() != obj.getClass()) 42 return false; 43 User other = (User) obj; 44 if (uid == null) { 45 if (other.uid != null) 46 return false; 47 } else if (!uid.equals(other.uid)) 48 return false; 49 if (uname == null) { 50 if (other.uname != null) 51 return false; 52 } else if (!uname.equals(other.uname)) 53 return false; 54 return true; 55 } 56 @Override 57 public String toString() { 58 return "User [uid=" + uid + ", uname=" + uname + "]"; 59 } 60 61 62 }
第三步:进行数据库操作(此处只对Session相关常用操作进行注释)
package com.hibernatetest.test; import java.io.Serializable; import org.hibernate.Session; import com.hibernatetest.entity.User; import HibernatenateUtils.hibernateUtils; public class SessionTest { public static void main(String[] args) { Session session = hibernateUtils.getSession(); //4.数据库操作 /*save() 添加 *Update() 修改 *saveOrUpdate() 添加或修改 *createQuery() 创建Query查询对象 *delete() 删除 *get() 根据id查询,获取对象(立即加载,不管有没有访问对象,都会生成对应的SQL语句并执行) *load() 根据id查询,获取对象(延迟加载,只有当访问对象的时候,才生成对应的SQL语句并执行) *flush() 清理session缓存,在事务提交和session关闭时都会自动执行flush() *beginTransaction()开启事务 * */ //(4 - 1)save添加操作 User user1 = new User(null,"lisi"); Serializable save = session.save(user1);//将对象添加到数据库中作为表的一条记录,返回的是一个主键值 //注意:此处我hibernate.cfg.xml设置的事务自动提交为true // 事务自动提交默认为false,可在hibernate.cfg.xml中修改, // 也可通过session.beginTracsation()开启事务和session2.getTransaction().commit();//提交事务 // 如果事务自动提交为false,此时数据并未同步到数据库中 // 如果事务自动提交为true,此时数据便已经同步到数据库中 System.out.println(save); //(4 - 2)Update修改操作 session.beginTransaction();//开启事务 User user2 = session.get(User.class, 5);//先从数据库中取出数据 user2.setUname("zhangsan");//再修改数据,此处不能修改设置了主键自增长的id. session.update(user2);//最后再把数据放回去 session.getTransaction().commit();//提交事务 //(4 - 3)delete删除操作 //注意:使用delete操作必须保证删除对象在数据库中,如果数据库中没有则会报错: //Batch update returned unexpected row count from update [0]; actual row count: 0; expected: 1; session.beginTransaction();//开启事务 User user3 = new User(null,null); user3.setUid(21); session.delete(user3); session.flush(); session.getTransaction().commit();//提交事务 //(4 - 4)saveOrUpdate删除操作:如果对象中主键不为null(并且这个主键的值在数据库中存在)做修改操作,如果为null做添加操作 //注意:如果对象中的主键在数据库中不存在,会报错: //Error during managed flush [Batch update returned unexpected row count from update [0]; actual row count: 0; expected: 1] session.beginTransaction();//开启事务 User user4 = new User(17,"zhangsan"); session.saveOrUpdate(user4); User user5 = new User(null,"zhangsan"); session.saveOrUpdate(user5); session.getTransaction().commit();//提交事务 //5.释放Session session.close();//如果事务自动提交为false,此时session缓存中的数据会自动同步到数据库中,之后会自动调用flush清空缓存。 } }