hibernate_03_session详解
获得session对象有两种方法:
1)openSession
2)getCurrentSession
如果使用的是getCurrentSession需要在hibernate.cfg.xml文件中进行配置:
如果是本地事务(jdbc事务),按照如下方法配置:
<property name="hibernate.current_session_context_class">thread</property>
如果是全局事务(jta事务)
<property name="hibernate.current_session_context_class">jta</property>
例子:
先创建java类:
package com.imooc.hibernate;
import java.util.Date;
public class Students {
private int sid;
private String sname;
private String gender;
private Date birthday;
private String address;
public Students(int sid, String sname, String gender, Date birthday, String address) {
super();
this.sid = sid;
this.sname = sname;
this.gender = gender;
this.birthday = birthday;
this.address = address;
}
@Override
public String toString() {
return "Students [sid=" + sid + ", sname=" + sname + ", gender=" + gender + ", birthday=" + birthday
+ ", address=" + address + "]";
}
public int getSid() {
return sid;
}
public void setSid(int sid) {
this.sid = sid;
}
public String getSname() {
return sname;
}
public void setSname(String sname) {
this.sname = sname;
}
public String getGender() {
return gender;
}
public void setGender(String gender) {
this.gender = gender;
}
public Date getBirthday() {
return birthday;
}
public void setBirthday(Date birthday) {
this.birthday = birthday;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
}
java类的配置文件
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<!-- Generated 2017-5-23 0:24:09 by Hibernate Tools 3.5.0.Final -->
<hibernate-mapping>
<class name="com.imooc.hibernate.Students" table="STUDENTS">
<id name="sid" type="int">
<column name="SID" />
<generator class="assigned" />
</id>
<property name="sname" type="java.lang.String">
<column name="SNAME" />
</property>
<property name="gender" type="java.lang.String">
<column name="GENDER" />
</property>
<property name="birthday" type="java.util.Date">
<column name="BIRTHDAY" />
</property>
<property name="address" type="java.lang.String">
<column name="ADDRESS" />
</property>
</class>
</hibernate-mapping>
hibernate配置文件
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name="connection.username">root</property>
<property name="connection.password">root</property>
<property name="connection.driver_class">com.mysql.jdbc.Driver</property>
<property name="connection.url">jdbc:mysql://localhost:3306/hibernate?useUnicode=true&characterEncoding=UTF-8</property>
<property name="dialect">org.hibernate.dialect.MySQLDialect</property>
<!-- 是否将sql语句打印到控制台,编码阶段便于测试,建议设为true -->
<property name="show_sql">true</property>
<!-- 是否将sql语句进行排版,建议设为true -->
<property name="format_sql">true</property>
<!-- 生成表结构的策略。create是如果之前有表结构,先删除表结构再重建;
update:原有的基础上更新;
create-drop:先删除表结构再重建
validate:与原表进行验证,如果和原表表结构不同,则不进行创建。
一般使用create和update
-->
<property name="hbm2ddl.auto">create</property> <!-- 使用getCurrentSession方法必须在配置文件中配置 -->
<property name="hibernate.current_session_context_class">thread</property> <mapping resource="com/imooc/hibernate/Students.hbm.xml"/>
</session-factory>
</hibernate-configuration>
测试类
package com.icoom.test; import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
import org.hibernate.service.ServiceRegistry;
import org.hibernate.service.ServiceRegistryBuilder;
import org.junit.Test; public class SessionTest { /*
* 使用openSession获得session对象
*/
@Test
public void testOpenSession() {
Configuration config = new Configuration().configure();//获得配置对象(读取hibernate.cfg.xml文件)
// 获得服务注册对象
ServiceRegistry serviceRegistry = new ServiceRegistryBuilder().applySettings(config.getProperties()).buildServiceRegistry();
// 获得sessionFactory对象
SessionFactory sessionFactory = config.buildSessionFactory(serviceRegistry);
// 获得session对象
Session session = sessionFactory.openSession();
if (session != null) {
System.out.println("session创建成功");
} else {
System.out.println("session创建失败");
}
} /*
* 使用getCurrentSession获得session对象(需要在hibernate配置文件中设置)
*/
@Test
public void testGetCurrentSession() {
Configuration config = new Configuration().configure();
ServiceRegistry serviceRegistry = new ServiceRegistryBuilder().applySettings(config.getProperties()).buildServiceRegistry();
SessionFactory sessionFactory = config.buildSessionFactory(serviceRegistry);
Session session = sessionFactory.getCurrentSession();
if (session != null) {
System.out.println("session创建成功!");
} else {
System.out.println("session创建失败!");
}
}
}
那么,openSession和getCurrentSession有什么区别?
1. getCurrentSession在事务提交或者回滚之后会自动关闭,openSession需要手动关闭。如果使用openSession而没有手动关闭,多次之后会导致连接池溢出。
package com.icoom.test; import java.sql.Connection;
import java.sql.SQLException;
import java.util.Date; import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;
import org.hibernate.jdbc.Work;
import org.hibernate.service.ServiceRegistry;
import org.hibernate.service.ServiceRegistryBuilder;
import org.junit.Test; import com.imooc.hibernate.Students; public class SessionTest { @Test
public void saveStudentsByOpenSession() { // 获取配置对象
Configuration configure = new Configuration().configure();
// 获得服务注册对象
ServiceRegistry serviceRegistry = new ServiceRegistryBuilder().applySettings(configure.getProperties()).buildServiceRegistry();
/*
* 创建sessionFactory对象。sessionFactory是一种工厂模式,
* 目的是返回session,而不必new一个session。这样做比较安全。
*/
SessionFactory sessionFactory = configure.buildSessionFactory(serviceRegistry);
// 创建第一个session对象
Session session1 = sessionFactory.openSession();
// 开启事务
Transaction transaction = session1.beginTransaction();
// 生成一个学生对象
Students s = new Students(1,"张三","男",new Date(),"北京");
session1.doWork(new Work() { @Override
public void execute(Connection connection) throws SQLException {
// TODO Auto-generated method stub
System.out.println("connection's hashCode:" + connection.hashCode());
} });
session1.save(s);
// session1.close(); // 不执行close()方法,继续新建session对象
transaction.commit(); // 创建第二个session对象
Session session2 = sessionFactory.openSession();
transaction = session2.beginTransaction();
s = new Students(2,"李四","女",new Date(),"上海");
session2.doWork(new Work() { @Override
public void execute(Connection connection) throws SQLException {
// TODO Auto-generated method stub
System.out.println("connection's hashCode:" + connection.hashCode());
} });
session2.save(s);
transaction.commit();
}
}

控制台打印出两个hashcode值不同,所以使用openSession()方法而不手动关闭,每次创建都会新建一个链接,有可能导致连接池溢出。
再看getCurrentSession():
package com.icoom.test; import java.sql.Connection;
import java.sql.SQLException;
import java.util.Date; import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;
import org.hibernate.jdbc.Work;
import org.hibernate.service.ServiceRegistry;
import org.hibernate.service.ServiceRegistryBuilder;
import org.junit.Test; import com.imooc.hibernate.Students; public class SessionTest { @Test
public void saveStudentsByGetCurrentSession() { // 获取配置对象
Configuration configure = new Configuration().configure();
// 获得服务注册对象
ServiceRegistry serviceRegistry = new ServiceRegistryBuilder().applySettings(configure.getProperties()).buildServiceRegistry();
/*
* 创建sessionFactory对象。sessionFactory是一种工厂模式,
* 目的是返回session,而不必new一个session。这样做比较安全。
*/
SessionFactory sessionFactory = configure.buildSessionFactory(serviceRegistry);
// 创建第一个session对象
Session session1 = sessionFactory.getCurrentSession();
// 开启事务
Transaction transaction = session1.beginTransaction();
// 生成一个学生对象
Students s = new Students(1,"张三","男",new Date(),"北京");
session1.doWork(new Work() { @Override
public void execute(Connection connection) throws SQLException {
// TODO Auto-generated method stub
System.out.println("connection's hashCode:" + connection.hashCode());
} });
session1.save(s);
// session1.close(); // 不执行close()方法,继续新建session对象
transaction.commit(); // 创建第二个session对象
Session session2 = sessionFactory.getCurrentSession();
transaction = session2.beginTransaction();
s = new Students(2,"李四","女",new Date(),"上海");
session2.doWork(new Work() { @Override
public void execute(Connection connection) throws SQLException {
// TODO Auto-generated method stub
System.out.println("connection's hashCode:" + connection.hashCode());
} });
session2.save(s);
// session2.close();
transaction.commit();
}
}

两个hashCode一致。
2. openSession每次创建新的session对象,getCurrentSession使用现有的session对象。
package com.icoom.test; import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
import org.hibernate.service.ServiceRegistry;
import org.hibernate.service.ServiceRegistryBuilder;
import org.junit.Test; public class SessionTest { /*
* openSession每次创建新的session对象
*/
@Test
public void testOpenSession() {
Configuration config = new Configuration().configure();//获得配置对象(读取hibernate.cfg.xml文件)
// 获得服务注册对象
ServiceRegistry serviceRegistry = new ServiceRegistryBuilder().applySettings(config.getProperties()).buildServiceRegistry();
// 获得sessionFactory对象
SessionFactory sessionFactory = config.buildSessionFactory(serviceRegistry);
// 获得session对象
Session session1 = sessionFactory.openSession();
Session session2 = sessionFactory.openSession();
System.out.println(session1 == session2); // false
} /*
* getCurrentSession使用现有的session对象
*/
@Test
public void testGetCurrentSession() {
Configuration config = new Configuration().configure();
ServiceRegistry serviceRegistry = new ServiceRegistryBuilder().applySettings(config.getProperties()).buildServiceRegistry();
SessionFactory sessionFactory = config.buildSessionFactory(serviceRegistry);
Session session1 = sessionFactory.getCurrentSession();
Session session2 = sessionFactory.getCurrentSession();
System.out.println(session1 == session2); // true
}
}
hibernate_03_session详解的更多相关文章
- Linq之旅:Linq入门详解(Linq to Objects)
示例代码下载:Linq之旅:Linq入门详解(Linq to Objects) 本博文详细介绍 .NET 3.5 中引入的重要功能:Language Integrated Query(LINQ,语言集 ...
- 架构设计:远程调用服务架构设计及zookeeper技术详解(下篇)
一.下篇开头的废话 终于开写下篇了,这也是我写远程调用框架的第三篇文章,前两篇都被博客园作为[编辑推荐]的文章,很兴奋哦,嘿嘿~~~~,本人是个很臭美的人,一定得要截图为证: 今天是2014年的第一天 ...
- EntityFramework Core 1.1 Add、Attach、Update、Remove方法如何高效使用详解
前言 我比较喜欢安静,大概和我喜欢研究和琢磨技术原因相关吧,刚好到了元旦节,这几天可以好好学习下EF Core,同时在项目当中用到EF Core,借此机会给予比较深入的理解,这里我们只讲解和EF 6. ...
- Java 字符串格式化详解
Java 字符串格式化详解 版权声明:本文为博主原创文章,未经博主允许不得转载. 微博:厉圣杰 文中如有纰漏,欢迎大家留言指出. 在 Java 的 String 类中,可以使用 format() 方法 ...
- Android Notification 详解(一)——基本操作
Android Notification 详解(一)--基本操作 版权声明:本文为博主原创文章,未经博主允许不得转载. 微博:厉圣杰 源码:AndroidDemo/Notification 文中如有纰 ...
- Android Notification 详解——基本操作
Android Notification 详解 版权声明:本文为博主原创文章,未经博主允许不得转载. 前几天项目中有用到 Android 通知相关的内容,索性把 Android Notificatio ...
- Git初探--笔记整理和Git命令详解
几个重要的概念 首先先明确几个概念: WorkPlace : 工作区 Index: 暂存区 Repository: 本地仓库/版本库 Remote: 远程仓库 当在Remote(如Github)上面c ...
- Drawable实战解析:Android XML shape 标签使用详解(apk瘦身,减少内存好帮手)
Android XML shape 标签使用详解 一个android开发者肯定懂得使用 xml 定义一个 Drawable,比如定义一个 rect 或者 circle 作为一个 View 的背景. ...
- Node.js npm 详解
一.npm简介 安装npm请阅读我之前的文章Hello Node中npm安装那一部分,不过只介绍了linux平台,如果是其它平台,有前辈写了更加详细的介绍. npm的全称:Node Package M ...
随机推荐
- TCP/IP UDP 协议首部及数据进入协议栈封装的过程
数据的封装 UDP 封装 TCP 封装 IP 封装 检验和算法 当应用程序用TCP传送数据时,数据被传送入协议栈中,然后逐一通过每一层直到被当作一串比特流送入网络 注: UDP数据TCP数据基本一致. ...
- 关于PyQt5,在pycharm上的安装步骤及使用技巧
前序 之前学习了一款GUI图形界面设计的Tkinter库,但是经大佬的介绍,PyQT5全宇宙最强,一脸的苦笑 毫不犹豫的选择转战PyQT5,在学习之前需要先安装一些必须程序,在一番查阅后,发现PyQt ...
- 【Codeforces 1114B】Yet Another Array Partitioning Task
[链接] 我是链接,点我呀:) [题意] 让你把数组分成k个连续的部分 使得每个部分最大的m个数字的和最大 [题解] 把原数组降序排序 然后选取前m*k个数字打标记 然后对于原数组 一直贪心地取 直到 ...
- JavaSE 学习笔记之Import 导入(十二)
Import - 导入:类名称变长,写起来很麻烦.为了简化,使用了一个关键字:import,可以使用这个关键字导入指定包中的类.记住:实际开发时,到的哪个类就导入哪个类,不建议使用*. import ...
- [bzoj1592][Usaco09Feb]Making the Grade 路面修整_动态规划
Making the Grade 路面修整 bzoj-1592 题目大意:给你n段路,每段路有一个高度h[i],将h[i]修改成h[i]$\pm\delta$的代价为$\delta$,求将这n段路修成 ...
- 关于Spring的xml文档的简单实用配置
Spring的spring.xml文档的配置 最近在写Spring的配置文件时,发现Spring文档的配置其实没必要那么繁琐记忆,网上的很多文章都写得很繁琐,如果所有的东西按照路径去查找,可以很快的帮 ...
- 你还在苦逼地findViewById吗?使用ButterKnife从此轻松定义控件
前段时间笔者在苦逼地撸代码~最后发现有些复杂的界面在写了一屏幕的findviewbyid~~~另一堆setOnXXXListener~有没有方便一点的方法让我们简单点不用每次都定义一次.find一次, ...
- Android測试环境变量配置表
要改动的文件是~/bash_profile这个配置文件,内容例如以下: # Setting PATH for Java JAVA_HOME="/Library/Java/JavaVirtua ...
- Nginx配置httpsserver
配置HTTPS主机.必须在server配置块中打开SSL协议,还须要指定服务器端证书和密钥文件的位置: server { listen 443; #要加密的域名 server_name www.te ...
- mongodb mapreduce使用总结
文章来自本人个人博客: mongodb mapreduce使用总结 大家都知道,mongodb是一个非关系型数据库.也就是说.mongodb数据库中的每张表是独立存在的,表与表之间没有不论什么依赖 ...