Hibernate3.x:最出色的ORM框架

一、前言

JDBC是Java操作数据库最常用的数据库接口,它隔离了数据库的复杂度,使程序员可以将主要精力放到程序逻辑上来。而JDBC也只是提供了和数据库交互的简单方式,如打开数据库表,执行SQL语句等。这对于复杂的程序也需要编写大量的代码,因此,近几年在Java数据库领域出现了许多框架,这此框架重新对JDBC进行了更高层次的封装。如早期的iBATIS。这个框架使用起来非常方便。它也没有基于复杂的面向对象模型。也不工作在复杂的关系图中。这种最初级的框架将数据库和应用程序隔离开来。使程序员只操作逻辑数据库。但由于这种框架不是基本面向对象和关系模型,在对付大规模应用程序时仍然捉襟见肘。基于这些不足,最近许多基于关系映射(ORM)的数据库框架开始流行起来。Hibernate就是其中的佼佼者。ORM的基本思想是使用外键和适当的约束将抽象不同的数据库。在最新的Hibernate3.x中,增强了对约束的控制,使用功能更强,也更容易使用。

在这些ORM框架刚兴起的时候,有很多人认为ORM框架最多只是从多选择之一。即使某个ORM框架做的非常出钯,将对象和数据库之间映射的非常完美也是如此。他们认为直接使用SQL写程序才是王道,而使用自动生成的SQL的效率低下,而且很不灵活。但随着程序规模越来越大,这种想法越来越站不住脚。这主要并不只是因为直接使用SQL将产生大量的代码,而是因为使用ORM框架,我们将操作一个完全不同的层:ORM层。直接使用SQL也可能产生其他的问题,如我们经常会遇到的N+1选择问题。而且在连接很多表时,我们会一遍一遍地重复写非常类似的SQL语句。如果我们使用Hibernate,这些问量就将荡然无存。我们可以使非常简单的HQL来完成上述复杂的问题。象Hibernate一样ORM框架还应该能进行各种优化,以使操作达到最佳化。就目前来看,这些框架的优化功能已经越来越强,正在逐步取代用JDBC和SQL操作数据库的方式。

虽然可以用ORM框架来编写大多数程序,但有时也需要直接使用SQL来操作。也许Hibernate的开发团队也意识到了这一点,也为Hibernate提供了直接执行SQL的功能。在早期的Hibernate版本中,解决方案是直接将JDBC连接暴露给用户,这样程序员就可以直接使用prepared statment来执行SQL了。但在新的Hibernate3.x中,这种情况已经被改变了。现在,Hibernate3.x可以不使用一条SQL编写整个应用程序,而且这并不会影响Hibernate的灵活性,同时也可以使用Hibernate的所有其他特性。

二、Hibernate3.x功能演示

上面说了很多Hibernate的好处,也面就让我们来体会一下Hibernate3.x在这方面的卓越表现。我们将使用一个简单的Person-Employment-Oranization模型来说明。最简单的类是Person,下面是它的定义:

INSERT INTO PERSON (NAME, ID) VALUES ( UPPER(?), ? )UPDATE PERSON SET NAME=UPPER(?) WHERE ID=?DELETE FROM PERSON WHERE ID=?

看了上面的定义,可能我们会首先注意到三个手写的SQL语句:INSERT、UPDATE和DELETE。其中的?将匹配上面所列的两个属性(这两个属性是id和name)。除了这个,这三条语句没有什么之处。

也许很多读者最感兴趣的是标签。这个标签定义了一个命名查询。这个查询在任何时候当我们使用get(),load()装载person或使用惰性关联获取数据时都会执行它。一般来讲,这个命名查询应该是一个SQL语句,如下面如示:

SELECT NAME AS {p.name}, ID AS {p.id} FROM PERSON WHERE ID=? FOR UPDATE

注:一个本地的SQL查询可能会返回多个"实体列",但本例比较简单,只返回了一个实体。

Employment相对更复杂一点,而且并不是所有的属性都包括在INSERT和UPDATE中。定义如下:

insert="false"/>INSERT INTO EMPLOYMENT(EMPLOYEE, EMPLOYER, STARTDATE, REGIONCODE, ID)VALUES (?, ?, CURRENT_DATE, UPPER(?), ?)UPDATE EMPLOYMENT SET ENDDATE=? WHERE ID=?DELETE FROM EMPLOYMENT WHERE ID=?

下面是命名查询employment的定义:

SELECT EMPLOYEE AS {emp.employee}, EMPLOYER AS {emp.employer},STARTDATE AS {emp.startDate}, ENDDATE AS {emp.endDate},REGIONCODE as {emp.regionCode}, ID AS {emp.id}FROM EMPLOYMENTWHERE ID = ?

下面的Organization的定义:

lazy="true"inverse="true">INSERT INTO ORGANIZATION (NAME, ID) VALUES ( UPPER(?), ? )UPDATE ORGANIZATION SET NAME=UPPER(?) WHERE ID=?DELETE FROM ORGANIZATION WHERE ID=?

下面是两个命名查询的定义:

SELECT NAME AS {org.name}, ID AS {org.id} FROM ORGANIZATIONWHERE ID=?SELECT {empcol.*},EMPLOYER AS {emp.employer}, EMPLOYEE AS {emp.employee},STARTDATE AS {emp.startDate}, ENDDATE AS {emp.endDate},REGIONCODE as {emp.regionCode}, ID AS {emp.id}FROM EMPLOYMENT empcolWHERE EMPLOYER = :id AND DELETED_DATETIME IS NULL

当我们看到这时,可能已经感觉到Hibernate的好处,那就是至少我们可以少维护数十行的Java代码。而且将这些代码转换成了XML配置文件,这样将使程序更加灵活和可维护。

下面的代码是我们的最后的工作,一个命名查询allOrganizationsWithEmployees的定义:

SELECT DISTINCT NAME AS {org.name}, ID AS {org.id}FROM ORGANIZATION orgINNER JOIN EMPLOYMENT e ON e.EMPLOYER = org.ID

虽然在现在为止还是有很多人喜欢直接使用SQL,这也包括我在内。但使用以Hbiernate为首的ORM框架可能会给我们带来更多的好处,如它自动产生的SQL一般会比我们手写的更优化。因此,Hibernate将成为软件大工业时代的新的操作数据库的标准。

真正的停下来,享受自我的体验时刻,也许浮光掠影,

Hibernate3.x:最出色的ORM框架

相关文章:

你感兴趣的文章:

标签云: