Hibernate入门(2):基本使用

来源:互联网 发布:ftp的默认端口 编辑:程序博客网 时间:2024/06/04 01:00

 Hibernate 基本使用


在应用程序中使用 Hibernate 框架的基本步骤如下:

1)将 Hibernate 相关依赖库导入项目中(详见http://blog.csdn.net/al_assad/article/details/77887263);
2)创建POJO(持久化实体)类,对于数据库中某个表映射为实体
3)创建配置文件(hibernate.cfg.xml),配置 数据库连接参数,选用数据库引擎 等的配置
4)创建检索或存储持久对象的类(实际使用POJO的逻辑类);

※ 其中对于 POJO 的配置推荐使用注解进行配置,当然也可以使用该POJO独立的xml配置进行配置,但是这种方法会减低项目的可维护性,所以还是推荐使用直接在 POJO 中进行注解配置;



简单示例

以下结合一个简单示例, 来讲解各个步骤,示例说明 :
本示例使用的 hibernate 版本为 5.2
使用的数据库为 MySQL 5.5;
数据库名“ioganes“,使用其中的 ”users“数据表作为示例,结构如下:


 
 由于 Hibernate 底层使用 JDBC 连接数据库,所以项目依赖中要导入 mysql-connector-java.jar,下载地址:https://dev.mysql.com/downloads/connector/j/

工程结构示意:

 

1)持久化实体类 POJO

demo.Users.java
持久化实体类(PO)类本身是一个持久化JavaBean(POJO),用于映射关系型数据库中的某个表单的数据为类对象,在POJO中使用相应的持久化注解用于标注各项持久化标注;
在新版本的hibernate中,提倡使用持久化注解来代替传统的持久化映射配置文件,这样可以增强代码的可读性;

以下是以上示例中出现的标注的解释:
@Entity :声明该类是一个 Hibernate 持久化实体(PO);
@Table:指定该类映射的表,此处映射到 users 表;
@Id: 指定该类的标识属性,即可以唯一标识该类的属性,通常映射到数据表的主键字段;
@GeneratedValue:指定主键的生成策略,这里strategy属性指定为 IDENTITY,即自动增长的主键生成策略,关于这部分详见下;
@Column:指定该类属性映射到数据表的相应字段名(不设置默认使用该属性名称);

完整的持久化注解可以参考:http://docs.jboss.org/hibernate/orm/5.2/userguide/html_single/Hibernate_User_Guide.html




2)配置文件

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://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
5
6
<hibernate-configuration>
7
    <session-factory>
8
        <!--设置数据库连接参数-->
9
        <property name="connection.driver_class">com.mysql.jdbc.Driver</property> <!--连接数据库的驱动-->
10
        <property name="connection.url">jdbc:mysql://localhost/iogames</property> <!--连接数据库的URL-->
11
        <property name="connection.username">root</property>                <!--连接数据库的用户名-->
12
        <property name="connection.password">mysql1994assad</property>      <!--连接数据库的密码-->
13
14
        <!--设置C3P0数据源参数-->
15
        <property name="hibernate.c3p0.max_size">20</property> <!--连接池的最大连接数-->
16
        <property name="hibernate.c3p0.min_size">1</property>  <!--连接池的最大连接数-->
17
        <property name="hibernate.c3p0.timeout">5000</property> <!--连接池里连接的超时时长-->
18
        <property name="hibernate.c3p0.max_statements">100</property>  <!--连接池最大缓存存放statement数量-->
19
        <property name="hibernate.c3p0.idle_test_period">3000</property>
20
        <property name="hibernate.c3p0.acquire_increment">2</property>
21
        <property name="hibernate.c3p0.validate">true</property>
22
23
        <!--设置数据库方言,本示例中使用 mysql5.5 方言-->
24
        <property name="dialect">org.hibernate.dialect.MySQL55Dialect</property>
25
        <!--根据需要自动创建数据库-->
26
        <property name="hbm2ddl.auto">update</property>
27
        <!--显示 hibernate 持久化操作所生成的 SQL-->
28
        <property name="show_sql">true</property>
29
        <!--将 SQL 脚本格式化后再输出-->
30
        <property name="hibernate.format_sql">true</property>
31
32
        <!--罗列所有的 POJO 持久化类名-->
33
        <mapping class="demo.Users" />
34
35
    </session-factory>
36
</hibernate-configuration>
37
hibernate.cfg.xml 配置文件用于配置数据库连接映射等信息的配置文件,默认放置在项目src目录下,默认命名为"hibernate.cfg.xml ",当运行构造上下文对象时,会自动调用该文件(当然也可以显式调用),当项目存在调用多个数据库时,可以将其使用多个映射配置文件,在构造上下文对象时显式调用相应文件即可;

以上的配置文件使用了 Hibernate 推荐的 c3p0 数据源代替传统的 DriverManager 来连接数据库,有助于保证最好的的数据库连接性能;

更多详细的数据库配置文件参数可以参见:http://docs.jboss.org/hibernate/orm/5.2/userguide/html_single/Hibernate_User_Guide.html#database

3)操作类

demo.UserManager.java
其中关于 Sessionfactory,Session,Transaction 等主要数据库操作对象的解释,可以参见:http://blog.csdn.net/al_assad/article/details/77887263- 结构体系

对于以上代码的优化,可以拆分出一个 HibernateUtil 专门用管理Session,如下:
HibernateUtil.java
1
import org.hibernate.*;
2
import org.hibernate.service.*;
3
import org.hibernate.boot.registry.*;
4
import org.hibernate.cfg.*;
5
6
public class HibernateUtil{
7
    public static SessionFactory sessionFactory;
8
    static{
9
        try{
10
            //根据配置文件创建连接注册对象
11
             StandardServiceRegistry registry = new StandardServiceRegistryBuilder()
12
                .configure("hibernate.cfg.xml")
13
                .build();
14
             //以连接注册对象创建 SessionFactory 对象
15
             sessionFactory = new MetadataSources(registry).buildMetadata().buildSessionFactory();
16
        }catch (Throwable ex){
17
            throw new ExceptionInInitializerError(ex);
18
        }
19
    }
20
21
    // ThreadLocal可以隔离多个线程的数据共享,因此不再需要对线程同步
22
    public static final ThreadLocal<Session> session = new ThreadLocal<Session>();
23
24
    public static Session currentSession() throws HibernateException{
25
        Session s = session.get();
26
        // 如果该线程还没有Session,则创建一个新的Session
27
        if (s == null){
28
            s = sessionFactory.openSession();
29
            // 将获得的Session变量存储在ThreadLocal变量session里
30
            session.set(s);
31
        }
32
        return s;
33
    }
34
35
    public static void closeSession() throws HibernateException{
36
        Session s = session.get();
37
        if (s != null)
38
            s.close();
39
        session.set(null);
40
    }
41
}
UserManager.java




持久化对象操作

持久化对象的状态
实际使用持久化对象 PO 过程中,要先获取 Session 对象,POJO 只有在 Session 的管理下才能完成对数据库的访问,PO 与 Session 的关联关系有以下3种:
  • 瞬态:PO 实例与 Session 从未关联过,此事 PO 实例处于瞬态;
  • 持久化:PO 实例与 Session 关联起来,该示例对应到数据库记录,则该实例处于持久化态;
  • 脱管态:PO 实例曾经与 Session 关联过,但是由于 Session 关闭等原因,PO 实例脱离了 Session 的托管,此时该实例处于脱管态;

改变持久化对象状态的方法
① 持久化实体
将瞬态对象转变为持久化对象,使用 Session 对象的 save(),persist() 方法;
1
Users user = new User();
2
user.setName("assad");
3
session.save(user);
②根据主键加载持久化实体
可以通过Session 的 get() ,load() 方法根据主键加载一个实体,不同的是如果指定主键的实体不存在,get返回null,load抛出一个HibernateException;
③更新持久化实体
1
User user = session.get(User.class,"20140302");
2
user.setName("assad");
3
session.flush();
④更新托管主体
对于一个已经脱离了 Session 管理的实体,当程序修改了托管对象的状态后,需要显式地使用新的 Session 来保存这些修改,可以使用 Session 对象的 update(),merge(),updateOrSave() 方法进行保存修改的实体;
update 方法会直接将该对象持久化,如果该对象曾经实体化过,使用update,如果没有,使用save,不确定时,使用 updateOrSave;
merge 方法区别于 update,不会直接持久化该对象,而是向将该对象拷贝一个副本,将该副本持久化,但是原来的对象不持久化,也不重新关联Session;
⑤删除持久化实体
可以使用 Session 的 delete 方法删除持久化实体,一旦删除该持久化实体,其对应的数据表记录也会被删除;
1
User user = session.get(User.class,"20140302");
2
session.delete(user);

 










原创粉丝点击