一、 Hibernate介紹
??? Hibernate是基于對象/關系映射(ORM,Object/Relational
Mapping)的一個解決方案。ORM方案的思想是將對象模型表示的對象映射到關系型數據庫中,或者反之。Hibernate目前是ORM思想在
Java中最成功、最強大的實現。它于2001年的年末發布第一個版本,立即引起了廣泛的注意。2003年6月,Hibernate2發表,并且獲得
Jolt大獎,進而被JBoss吸納成為它的一個子項目。2005年3月,Hibernate
3發表,其中做了一些比較重大的改進。本文以Hibernate3為基礎編寫。
??? 另外,Hibernate除了可以在J2EE容器中運行外,還可以運行在Java應用程序中。本文就是以Java應用程序為例來介紹它。
二、配置開發環境
??? 本文以一個Java應用程序(Java Application)為例,介紹如何使用Hibernate來進行數據庫操作。
??? 在進行Hibernate開發之前,需要首先獲得Hibernate類庫、相應數據庫的JDBC驅動類庫。Hibernate類庫可以從http://www.hibernate.org中下載,目前的版本是3.0。而JDBC驅動可以根據不同的數據庫來選擇,在這個例子中,使用的是Oracle數據庫,那么相應的JDBC驅動可以從Oracle安裝目錄\ora92\jdbc下獲得。其他的數據庫請根據相關的說明獲得。
???
下載Hibernate包后,可以將它解壓到一個文件夾,此處假設為C:\hibernate-3.0,然后將C:\hibernate-3.0\下的
hibernate.jar和C:\hibernate-3.0\lib下的那些第三方類庫也放到環境變量CLASSPATH中。(通常,只需要
dom4j、cglig、commons-logging、commons-collections、log4j、ehcache、asm、jta、
antlr這些類庫就可以了)
??? 做完這些配置后,就可以在此基礎上進行基于Hibernate的Java程序開發了。
三、開發基于Hibernate的應用
??? 現在假設我們在Oracle數據庫中創建了一個表Student,它的字段如下表所示:
字段?說明
Student_ID?學員編號,整型,PK,自動增長
Student_Name?學員姓名,字符串類型
Student_Age?學員年齡,整型
如果我們在Oracle中定義這個數據庫表,我們可以定義一個創建數據庫表的SQL腳本如下:
create table Student(
?Student_ID? number(6) NOT NULL PRIMARY KEY,
?Student_Name varchar2(10) NOT NULL,
?Student_Age number(2) NOT NULL
);
??? 另外,因為在Oracle中沒有“自動增長”類型的字段,所以通常情況下我們需要定義一個sequence來作為自動增長類型字段的數據。在這里,我們也可以定義一個sequence來給Student_ID字段提供數據。創建sequence的SQL腳本如下:
CREATE SEQUENCE student_sequence
INCREMENT BY 1
START WITH 1000
NOMAXVALUE
NOCYCLE
CACHE 10;
??? 我們在這里創建了一個student_sequence,準備用來作為Student_ID字段的值。
??? 接著,我們需要一個hibernate.cfg.xml或者屬性文件hibernate.properties來指定Hibernate所使用的數據庫以及用戶名、密碼等其他相關的配置,我們在此使用xml文件,它的內容如下:
源文件:hibernate.cfg.xml
<!DOCTYPE hibernate-configuration PUBLIC
?"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
?"<hibernate-configuration>
?<session-factory>
<!--程序執行的時候是否顯示真正的sql語句-->
??<property name="show_sql">true</property>
??<!--使用的SQL對應的“方言”,此處是Oracle9的“方言”-->
<property name="dialect">org.hibernate.dialect.Oracle9Dialect
</property>
??<!--連接數據庫的Driver-->
<property name="connection.driver_class">
oracle.jdbc.driver.OracleDriver
</property>
??<!--數據庫連接url-->
<property name="connection.url">
jdbc:oracle:thin:@localhost:1521:nitpro
</property>
??<!--用戶名-->
<property name="connection.username">system</property>
<!--密碼-->
??<property name="connection.password">manager</property>
?</session-factory>
</hibernate-configuration>
??? 做完前面的這些準備工作后,下面就讓我們進入激動人心的Hibernate編程吧!
??? 首先,我們需要定義一個用于表示“學生”對象的Student類:
源文件:Student.java
public class Student
{
??? private int student_id;
??? private String student_name;
??? private int student_age;
???
??? public int getStudent_id()
??? {
??????? return student_id;
??? }
??? public String getStudent_name()
??? {
??????? return student_name;
??? }
??? public int getStudent_age()
??? {
??????? return student_age;;
??? }
??? public void setStudent_id(int id)
??? {
??????? this.student_id = id;
??? }
??? public void setStudent_name(String name)
??? {
??????? this.student_name = name;
??? }
??? public void setStudent_age(int age)
??? {
??????? this.student_age = age;
??? }
}
??? 這個類很簡單,就是一個典型的JavaBean的定義:有三個屬性:student_id、student_name和student_age,分別對應數據庫表Student中的三個字段,并且在這個類中定義了對應各個屬性的setter/getter方法。
??? 接下來,我們需要給這個類定義一個XML映射文件“Student.hbm.xml”,文件內容如下:
源文件:Student.hbm.xml
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-mapping
???? PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
???? "<hibernate-mapping>????
??? <class name="Student" table="Student">????????
??????? <id name="student_id" column="student_id" type="java.lang.Integer">????????????
??????????? <generator class="native">????????
??????????????? <param name="sequence">student_sequence</param>
??????????? </generator>
??????? </id>????????
??????? <property name="student_name" column="Student_Name"
?type="java.lang.String"/>
??????? <property name="student_age" column="Student_Age"
type="java.lang.Integer"/>
??? </class>
</hibernate-mapping>
???
注意,在這個xml文件中,我們首先使用class元素定義了我們定義的Java類和數據庫表之間的關系,在這里,我們定義的Java類和數據庫表名稱都
是Student,然后,我們使用id元素定義了主鍵名稱、類型等,它有一個子元素generator來說明主鍵的產生方式,此處指定的是
“native”,表示根據數據庫來選擇,比如,對于Oracle數據庫,它會去尋找一個sequence(默認情況下,它會去尋找一個名為
“hibernate_sequence”的sequence),我們可以用參數param來指定一個sequence。而property用來指定
Student.java類中的屬性和Student數據庫表之間的對應關系,以及各個字段的數據類型。在這個例子中,我們指定的數據類型是Java語言
中的數據類型(此時需要指定引用類型數據),我們也可以使用Hibernate中自定義的數據類型,限于篇幅,在本文中不一一講解。
??? 然后,我們需要在hibernate.cfg.xml中加入這個文件的映射,可以在</session-factory>之前加入下面的語句:
<mapping resource="Student.hbm.xml"/>
最后,我們需要編寫一個測試類來測試一下,能否通過Hibernate和前面我們定義的相關程序,完成對數據庫的操作。我們編寫一個測試類如下:
源文件:Test.java
import org.hibernate.*;
import org.hibernate.cfg.*;
public class Test
{
??? public static void main(String[] args)
??? {
??????? try
??????? {
??????????? //通過Configuration獲得一個SessionFactory對象
SessionFactory sf
= new Configuration().configure().buildSessionFactory();
??????????? //打開一個Session
??????????? Session session = sf.openSession();
??????????? //開始一個事務
??????????? Transaction tx = session.beginTransaction();
??????????? //創建一個Student對象
??????????? Student stu = new Student();
??????????? //通過Student的setter方法改變它的屬性
??????????? //注意student_id不用我們設置
??????????? stu.setStudent_name("zhangsan");
??????????? stu.setStudent_age(18);
??????????? //通過session的save()方法將Student對象保存到數據庫中
??????????? session.save(stu);
??????????? //提交事務
??????????? tx.commit();
??????????? //關閉會話
??????????? session.close();
??????? }
??????? catch(Exception e)
??????? {
??????????? e.printStackTrace();
??????? }
??? }???
}
??? 編譯并運行這個程序,如果前面的配置和程序都沒有問題,應該可以正確的往數據庫表Student中插入一條數據,并且在控制臺上能夠得到如下輸出(只列出部分輸出內容):
Hibernate: select student_sequence.nextval from dual
Hibernate: insert into Student (Student_Name, Student_Age, student_id) values (?,?,?)
??? 可以看到,雖然我們自己沒有編寫SQL語句進行插入數據的操作,但是其實Hibernate還是要使用SQL語句來進行數據庫的操作,只是這個過程對程序員來說是透明的。