手动配置hibernate的全过程

主流的数据库是关系型数据库,而编程的思想是面向对象的,如何将对象存储到关系型的数据库中,消除对象—>关系的阻抗,ORM(Object Relation Model)对象关系模型就出现了,而hibernate就是基于ORM的框架.下面我来聊聊hibernate的手动配置过程.
配置环境:eclipse,mysql数据库,hibernate的jar包和连接mysql数据库用的jar包.
配置前提:在mysql数据库中,名字为sqdb3的数据库,有一个叫employee的表.表的字段创建入下:

use spdb3;
create table employee(
    id int PRIMARY key auto_increment,
    username varchar(64) not null,
    email varchar(64) not null,
    hiredate date not null
);

employee表里面的内容自己可以随意添加.

配置的思想是先建立一个POJO对象,配置Employee.hbm.xml文件,最后配置hibernate.cfg.xml文件.先展示一下各个文件所在的位置.]
①先解释一下POJO的作用,它是一个类(对象类),它所用拥有的属性对应的是表中的字段,方法是set/get属性.用来映射employee.Employee.java的代码如下:

package com.hsp.domain;
import java.util.*;
import java.io.*;
//建议我们的domain对象的名称就是对应
//表的首字母大写,domain对象/javaBean/pojo
//该pojo按规范应当序列化,目的是可以唯一的标识该对象,同时可以在网络和文件上传输
public class Employee implements Serializable{
    static final long serialVersionUID=1L;
    private Integer id;
    private String username;
    private String email;
    private Date hiredate;
    public Integer getId() {
        return id;
    }
    public void setId(Integer id) {
        this.id = id;
    }
    public String getUsername() {
        return username;
    }
    public void setUsername(String username) {
        this.username = username;
    }
    public String getEmail() {
        return email;
    }
    public void setEmail(String email) {
        this.email = email;
    }
    public Date getHiredate() {
        return hiredate;
    }
    public void setHiredate(Date hiredate) {
        this.hiredate = hiredate;
    } 
}

②在与POJO同一个目录下的Employee.hbm.xml文件其实是一个对象关系映射文件.内容如下:

<?xml version="1.0" encoding="utf-8"?>
<!-- 映射文件需要一个dtd -->
<!DOCTYPE hibernate-mapping PUBLIC
    "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
    "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<!-- 该文件用于配置domain对象和表的映射关系 -->
<hibernate-mapping package="com.hsp.domain">
    <class name="Employee" lazy="true" table="employee">
        <!-- id元素用于指定主键属性 -->
        <!-- mysql的数据库表 id 主键对于设置自增长 -->
        <id name="id" type="java.lang.Integer">
            <column name="id"/>
            <generator class="identity"/>
        </id>
        <!-- 对其他属性还有配置 -->
        <property name="username" type="java.lang.String">
            <column name="username" not-null="false" />
        </property>
        <property name="email" type="java.lang.String">
            <column name="email" not-null="false"></column>
        </property>
        <property name="hiredate" type="java.util.Date">
            <column name="hiredate" not-null="false"></column>
        </property>
    </class>
</hibernate-mapping>

让我来简单解释一下这个Employee.hbm.xml文件的内容,

<hibernate-mapping package="com.hsp.domain">
    <class name="Employee" lazy="true" table="employee">

这个是将对象类(Employee)和表(employee)对应起来,其中lazy表示的是懒加载,这个作用之后在解释.

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

id这个字段是用来唯一表示表中的主键的属性,name表示的其实就是Employee.java中的属性,type表示它的类型,column对应的是表中的那个字段.<generator class="identity"/>表示这个主键是自增长的.

③下面重头戏闪亮登场.hibernate.cfg.xml文件
内容如下:

<?xml version='1.0' encoding='utf-8'?>  
<!DOCTYPE hibernate-configuration PUBLIC  
        "-//Hibernate/Hibernate Configuration DTD 3.0//EN"  
        "http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">  
<hibernate-configuration>
    <session-factory name="mySessionFactory">
        <property name="hibernate.connection.driver_class">com.mysql.jdbc.Driver</property>
        <property name="hibernate.connection.url">jdbc:mysql://localhost:3306/spdb3</property>
        <property name="hibernate.connection.username">root</property>
        <property name="connection.password">root</property>
        <!-- dialect翻译为方言 Hibernate根据你选择的“方言”,针对每种数据库,作调整,如生成不同的SQL语句等 -->
        <property name="hibernate.dialect">org.hibernate.dialect.MySQLDialect</property>
        <!-- 连接池默认配置.提供对数据库操作速度 -->
        <property name="connection.pool_size">2</property>
        <!-- 自动创建|更新|验证数据库表结构。如果不是此方面的需求建议set value="none" -->
        <property name="hibernate.hbm2ddl.auto">update</property>
        <!-- 是否要在后台.演示翻译sql 语句 -->
        <property name="show_sql">true</property>
       <!-- 按照格式化的形式输出 -->
       <property name="format_sql">true</property>
        <!-- 配置可以使用getCurrentSession 
        <property name="current_session_context_class">thread</property>
        -->
        <!-- //与实体类连接 -->
        <mapping resource="com/hsp/domain/Employee.hbm.xml" />
    </session-factory>
</hibernate-configuration>

这个文件的作用其实就是配置你所使用的数据库,url,user,passwd,方言等.在这个文件中的参数有很多,我所了解的只是皮毛,大家可以看看代码中的注释.

④我自己还写了一个获得直接获得Session的静态的方法.HibernateUtil.java.内容如下

package com.hsp.util;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;

final public class HibernateUtil {
    private static SessionFactory sessionFactory=null;
    //使用线程局部模式
    private static ThreadLocal<Session> threadLocal=new ThreadLocal<Session>();
    //私有的构造函数
    private HibernateUtil() {};
    static {
        sessionFactory=new Configuration().configure("com/hsp/config/hibernate.cfg.xml").buildSessionFactory();
    }
    //获取全新的session
    public static Session openSession() {
        return sessionFactory.openSession();
    }
    //获取和线程关联的session
    public static Session getCurrentSession() {
        Session session=threadLocal.get();
        //判断是否得到
        if(session==null) {
            session=sessionFactory.openSession();
            //把session对象设置到threadLocal,相当于该session已经和线程绑定
            threadLocal.set(session);
        }
        return session;
    }
}

在这个类中有两个静态的方法,其中openSession()方法是直接获得一个session,getCurrentSession()方法是获得一个线程安全的session(有利于事务的处理).他们之间的具体差别我就不详细解释了.
⑤.下面就是一个Test.java这个的作用就是来验证是否可以用hibernate框架来进行crud操作

package com.hsp.util;

import java.util.Date;
import java.util.List;
import com.hsp.util.*;
import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.*;
import com.hsp.domain.Employee;

public class TestMain {
    public static void main(String[] args) {
        //获取session
        Session session =HibernateUtil.getCurrentSession();
        //事务
        Transaction ts = null;
        try {
            //事务处理
            ts = session.beginTransaction();
            // do...
            Employee emp = (Employee) session.load(Employee.class, 1);
            //修改id为1的username
            emp.setUsername("dddd");
            // ....doing
            //事务提交
            ts.commit();
        } catch (Exception e) {
            //如果出错,回滚数据
            if (ts != null) {
                ts.rollback();
            }
            throw new RuntimeException(e.getMessage());
        } finally {
            // 关闭session
            if (session != null && session.isOpen()) {
                session.close();
            }
        }

    }
}

ok,在这里给初学者普及一下事务这个概念.比如银行转转,你从农行的一个账户中向工行的一个账户转钱,其业务是这样的,农行账户的钱减去100,工行账户的钱加100,这需要操作数据库,将减钱和加钱的操作同时进行完成.不能减钱完成,加钱没完成或反之这就需要事务了.它将这两操作包裹成原子操作.要么做完,要么不做.当只是执行其中一个的时候,就回滚(相当于不做).

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值