利用轻量对象关系映射技术Hibernate提高开发效率 Enhancing Development Efficiency with Hibernate a LightweightObject/Relational Mapping Technology谢挺 周维民(上海大学机电工程与自动化学院,上海 200072)摘 要 Hibernate是一种轻量对象关系映射技术。
文章通过实例,介绍了Hibernate的一些关键特性,并阐述了该技术的一些局限性。
关键词 Hibernate 对象关系映射企业级JavaBeans 持久化Abstract Hibernate is a lightweight Object/Relational Mapping(ORM) technology. Some key features of Hibernate are illustrated, and some limits of this technology are expounded.Keywords Hibernate Object/Relational Mapping (ORM) EJB Permanence0 引言随着internet的发展,应用服务程序已经从集中式、C/S模式过渡到B/S、分布式模式;无论是用户或是供应商都迫切希望缩短开发周期、提高开发效率,Hibernate应运而生。
1 Hibernate简介Hibernate是一个面向Java环境的对象/关系数据库映射工具。
对象/关系数据库映射(Object/Relational Mapping , ORM)这个术语表示一种技术,用来把对象模型表示的对象映射到基于SQL的关系模型中去。
Hibernate不仅提高Java类到数据库的映射,还提供数据查询和获取数据的方法。
Hibernate在英语中的意思是“冬眠”,顾名思义它使得商务逻辑的开发和数据库最大程度地分离,可以大幅度减少开发时人工使用SQL和JDBC处理数据的时间。
Hibernate的目标是解放开发者通常与数据持久化相关的编程任务的95%。
对于那些在基于Java的中间层应用中,它们实现面向对象的业务模型和商业逻辑的应用,Hibernate是很有用的。
图1是Hibernate的体系结构图,从图中可以Array看到,系统为3层B/S模式,应用程序在客户端运行将持久化的对象交由Hibernate。
Hibernate通过properties属性设置和XML Mapping实现商务逻辑,调用和存储低层数据库后将返回的结果送给客户端。
Hibernate对每一种数据库都有对应的Dialect进行操作优化,从而提高它在各种情况下的效率。
目前,它的版本为3.0、支持的数据库有Oracle、DB2、MySQL、PostgreSQL、Sybase,Interbase、Pointbase、Microsoft SQL Server、MckoiSQL、 Progress、SAP DB 以及HypersonicSQL。
2 Hibernate的优势由图1可以很清楚地看出,对象持久化是整个体系中最为重要的一环,为此解决方案也很多。
现今用得最多的分布式应用技术体系当然是Microsoft的.net和Sun公司基于Java的J2EE 以及OMG的CORBA,他们都已经制定出了自己的标准。
.net的对象持久化由DCOM等组件实现,J2EE则制定了EJB规范。
然而问题是.net缺乏可移植性和跨平台性。
EJB在这方面优势明显,不过仍存在以下几个缺点:① 实体Bean不支持继承,而这是面向对象的主要特征之一;② CMP Bean在关系模型表中被定义为一对一的关系,即粒度过粗,不能体现出Java丰富的对象类型。
而如果粒度太细,又会影响到EJB的可重用性。
因为可重用的组件要求定义粒度较粗的对象,这样只需要在接口处做小的改动;③ 在实际的应用程序中,实体Bean定义细粒度远程接口是不能够序列化的,因此J2EE 开发人员不得不在分布式系统中定义额外的数据传输对象(data transfer objects,DTO);④ 由于很多供应商都有生产CMP引擎的能力,使得元数据的映射有各自的特殊性。
而且EJB规范过于笨重,倒置了控制框架。
与此相比,Hibernate是站在开发人员角度上产生的技术,所以极大地提高了编程效率。
它的关系数据库持久化符合Java习惯,而且O/R(对象-关系)映射机制灵活,其特有的面向对象的查询语言(HQL)相对于结构化查询语言(SQL)更加便于使用,程序代码简洁,系统可维护性强。
APIs简洁实用提高了执行效率,并且集成在J2EE中。
3 Hibernate的持久化原理图2 Hibernate API分层结构图2是Hibernate API结构的高度概括。
从图中可以看出,业务逻辑层是在持久化层之上的。
而实现一个实例首先要使用Configuration接口配置和引导Hibernate,再通过SessionFactory接口建立会话工厂。
业务逻辑层的持久化类然后才能调用Session、Transaction、Query等接口实现业务逻辑。
上述3个API可以实现基本的业务逻辑CRUD(create, read, update, delete)和查询功能。
还有一些接口如UserTpye, CompositeUserType和IdentifierGenerator可以用来扩展Hibernate的功能。
最后,Hibernate使用了许多现有的Java API,包括JDBC、Java 事务API(JTA)和Java命名及目录接口(JNDI)。
JDBC允许几乎所有的数据库被Hibernate支持。
JNDI和JTA允许Hibernate与J2EE应用服务器进行集成。
其中Configuration和SessionFactory是最基本的API,而后才使用Transaction、Query等API 实现和扩展功能。
下面我们通过一个实例来了解Hibernate的一些优点。
在开始Hibernate实例之前必须进行必要的配置,这里由于篇幅的关系就不具体介绍,细节可以察看Hibernate的官方网站。
本实例中使用的是Apache Tomcat servlet容器,Hibernate为最新的3.0版本,数据库使用了SQL Server。
当然Hibernate也支持大多数J2EE服务器和主流的数据库。
这里给出一个书目查询系统的实例来说明问题。
首先需要创建配置文件hibernate.cfg.xml和libruary.xml, 这两个文件将被放在classpath下,在hibernate初始化期间会自动在classpath中寻找这个文件。
hibernate.cfg.xml是对诸如数据库驱动、数据库路径、数据库名称已经事务处理等属性的配置。
<?xml version="1.0" encoding="utf-8"?><!DOCTYPE hibernate-configurationPUBLIC "-//Hibernate/Hibernate Configuration DTD//EN""/hibernate-configuration-3.0.dtd"><hibernate-configuration><!-- SessionFactory 配置 --><session-factory><!-- 数据库URL --><property name="hibernate.connection.url">jdbc:jtds:sqlserver://localhost:1433</property><!-- 数据库JDBC驱动 --><property name="hibernate.connection.driver_class">net.sourceforge.jtds.jdbc.Driver</property><!-- 数据库用户名 --><property name="ername">Login</property><!—- 数据库用户密码 --><property name="hibernate.connection.password">123</property><!--dialect ,每个数据库都有其对应的Dialet以匹配其平台特性 --><property name="dialect">net.sf.hibernate.dialect.SQLServerDialect</property>.......<!--映射文件配置,注意配置文件名必须包含其相对于根的全路径 --><mapping resource="Libruary.hbm.xml"/></session-factory></hibernate-configuration>Libruary.xml的源文件如下:<?xml version="1.0"?><!DOCTYPE hibernate mappingPUBLIC "//Hibernate/Hibernate Mapping DTD//EN""/hibernate mapping3.0.dtd"><hibernate mapping><class name="net.sf.hibernate.examples.Libruary" table="LIBRUARY"> <!-- A 32 hex character is our surrogate key. It's automatically generated by Hibernate with the UUID pattern.--><id name="id" type="string" unsaved-value="null" ><column name="BOOK_ID" sqltype="char(32)" notnull="true"/><generator class="uuid.hex"/></id><!-- A cat has to have a name, but it shouldn' be too long. ><property name="bookName"><column name="BOOKNAME" length="16" notnull="true"/></property><property name="author"><column name="AUTHOR" length="16" notnull="true"/>………</class></hibernate mapping>通过上面的例子可以看到,Hibernate技术将数据库中的表和类完全对应起来,如Libruary.class和LIBRUARY表对应,bookName对象和BOOKNAME列对应等。