王朝网络
分享
 
 
 

Struts+Spring+Hibernate上传下载 --之二

王朝other·作者佚名  2006-12-30
宽屏版  字体: |||超大  

数据持久层

1、领域对象及映射文件

您可以使用Hibernate Middlegen、HIbernate Tools、Hibernate Syhchronizer等工具或手工的方式,编写Hibernate的领域对象和映射文件。其中对应T_FILE表的领域对象Tfile.java为:

代码 1 领域对象Tfile

1. package sshfile.model;

2. public class Tfile

3.{

4. private String fileId;

5. private String fileName;

6. private byte[] fileContent;

7. private String remark;

8. …//getter and setter

9. }

特别需要注意的是:数据库表为Blob类型的字段在Tfile中的fileContent类型为byte[]。Tfile的Hibernate映射文件Tfile.hbm.xml放在Tfile .java类文件的相同目录下:

代码 2 领域对象映射文件

1. <?xml version="1.0"?>

2. <!DOCTYPE hibernate-mapping PUBLIC

3. "-//Hibernate/Hibernate Mapping DTD 3.0//EN"

4. "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd" >

5. <hibernate-mapping>

6. <class name="sshfile.model.Tfile" table="T_FILE">

7. <id name="fileId" type="java.lang.String" column="FILE_ID">

8. <generator class="uuid.hex"/>

9. </id>

10. <property name="fileContent"

11. type="org.springframework.orm.hibernate3.support.BlobByteArrayType"

12. column="FILE_CONTENT" lazy="true"/>

13. …//其它一般字段的映射

14. </class>

15. </hibernate-mapping>

fileContent字段映射为Spring所提供的BlobByteArrayType类型,BlobByteArrayType是用户自定义的数据类型,它实现了Hibernate 的org.hibernate.usertype.UserType接口。BlobByteArrayType使用从sessionFactory获取的Lob操作句柄lobHandler将byte[]的数据保存到Blob数据库字段中。这样,我们就再没有必要通过硬编码的方式,先insert然后再update来完成Blob类型数据的持久化,这个原来难伺候的老爷终于被平民化了。关于lobHandler的配置请见本文后面的内容。

此外lazy="true"说明地返回整个Tfile对象时,并不返回fileContent这个字段的数据,只有在显式调用tfile.getFileContent()方法时才真正从数据库中获取fileContent的数据。这是Hibernate3引入的新特性,对于包含重量级大数据的表字段,这种抽取方式提高了对大字段操作的灵活性,否则加载Tfile对象的结果集时如果总是返回fileContent,这种批量的数据抽取将可以引起数据库的"洪泛效应"。

2、DAO编写和配置

Spring强调面向接口编程,所以我们将所有对Tfile的数据操作的方法定义在TfileDAO接口中,这些接口方法分别是:

·findByFildId(String fileId)

·save(Tfile tfile)

·List findAll()

TfileDAOHibernate提供了对TfileDAO接口基于Hibernate的实现,如代码 3所示:

代码 3 基于Hibernate 的fileDAO实现类

1. package sshfile.dao;

2.

3. import sshfile.model.*;

4. import org.springframework.orm.hibernate3.support.HibernateDaoSupport;

5. import java.util.List;

6.

7. public class TfileDAOHibernate

8. extends HibernateDaoSupport implements TfileDAO

9. {

10. public Tfile findByFildId(String fileId)

11. {

12. return (Tfile) getHibernateTemplate().get(Tfile.class, fileId);

13. }

14. public void save(Tfile tfile)

15. {

16. getHibernateTemplate().save(tfile);

17. getHibernateTemplate().flush();

18. }

19. public List findAll()

20. {

21. return getHibernateTemplate().loadAll(Tfile.class);

22. }

23. }

TfileDAOHibernate通过扩展Spring提供的Hibernate支持类HibernateDaoSupport而建立,HibernateDaoSupport封装了HibernateTemplate,而HibernateTemplate封装了Hibernate所提供几乎所有的的数据操作方法,如execute(HibernateCallback action),load(Class entityClass, Serializable id),save(final Object entity)等等。

所以我们的DAO只需要简单地调用父类的HibernateTemplate就可以完成几乎所有的数据库操作了。

由于Spring通过代理Hibernate完成数据层的操作,所以原Hibernate的配置文件hibernate.cfg.xml的信息也转移到Spring的配置文件中:

代码 4 Spring中有关Hibernate的配置信息

1. <beans>

2. <!-- 数据源的配置 //-->

3. <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"

4. destroy-method="close">

5. <property name="driverClassName" value="oracle.jdbc.driver.OracleDriver"/>

6. <property name="url" value="jdbc:oracle:thin:@localhost:1521:ora9i"/>

7. <property name="username" value="test"/>

8. <property name="password" value="test"/>

9. </bean>

10. <!-- Hibernate会话工厂配置 //-->

11. <bean id="sessionFactory"

12. class="org.springframework.orm.hibernate3.LocalSessionFactoryBean">

13. <property name="dataSource" ref="dataSource"/>

14. <property name="mappingDirectoryLocations">

15. <list>

16. <value>classpath:/sshfile/model</value>

17. </list>

18. </property>

19. <property name="hibernateProperties">

20. <props>

21. <prop key="hibernate.dialect">org.hibernate.dialect.OracleDialect</prop>

22. <prop key="hibernate.cglib.use_reflection_optimizer">true</prop>

23. </props>

24. </property>

25. </bean>

26. <!-- Hibernate 模板//-->

27. <bean id="hibernateTemplate"

28. class="org.springframework.orm.hibernate3.HibernateTemplate">

29. <property name="sessionFactory" ref="sessionFactory"/>

30. </bean>

31. <!--DAO配置 //-->

32. <bean id="tfileDAO" class="sshfile.dao.TfileDAOHibernate">

33. <property name="hibernateTemplate" ref="hibernateTemplate" />

34. </bean>

35. …

36. </beans>

第3~9行定义了一个数据源,其实现类是apache的BasicDataSource,第11~25行定义了Hibernate的会话工厂,会话工厂类用Spring提供的LocalSessionFactoryBean维护,它注入了数据源和资源映射文件,此外还通过一些键值对设置了Hibernate所需的属性。

其中第16行通过类路径的映射方式,将sshfile.model类包目录下的所有领域对象的映射文件装载进来,在本文的例子里,它将装载进Tfile.hbm.xml映射文件。如果有多个映射文件需要声明,使用类路径映射方式显然比直接单独指定映射文件名的方式要简便。

第27~30行定义了Spring代理Hibernate数据操作的HibernateTemplate模板,而第32~34行将该模板注入到tfileDAO中。

需要指定的是Spring 1.2.5提供了两套Hibernate的支持包,其中Hibernate 2相关的封装类位于org.springframework.orm.hibernate2.*包中,而Hibernate 3.0的封装类位于org.springframework.orm.hibernate3.*包中,需要根据您所选用Hibernate版本进行正确选择。

3、Lob字段处理的配置

我们前面已经指出Oracle的Lob字段和一般类型的字段在操作上有一个明显的区别--那就是你必须首先通过Oracle的empty_blob()/empty_clob()初始化Lob字段,然后获取该字段的引用,通过这个引用更改其值。所以要完成对Lob字段的操作,Hibernate必须执行两步数据库访问操作,先Insert再Update。

使用BlobByteArrayType字段类型后,为什么我们就可以象一般的字段类型一样操作Blob字段呢?可以确定的一点是:BlobByteArrayType不可能逾越Blob天生的操作方式,原来是BlobByteArrayType数据类型本身具体数据访问的功能,它通过LobHandler将两次数据访问的动作隐藏起来,使Blob字段的操作在表现上和其他一般字段业类型无异,所以LobHandler即是那个"苦了我一个,幸福十亿人"的那位幕后英雄。

LobHandler必须注入到Hibernate会话工厂sessionFactory中,因为sessionFactory负责产生与数据库交互的Session。LobHandler的配置如代码 5所示:

代码 5 Lob字段的处理句柄配置

1. <beans>

2. …

3. <bean id="nativeJdbcExtractor"

4. class="org.springframework.jdbc.support.nativejdbc.CommonsDbcpNativeJdbcExtractor"

5. lazy-init="true"/>

6. <bean id="lobHandler"

7. class="org.springframework.jdbc.support.lob.OracleLobHandler" lazy-init="true">

8. <property name="nativeJdbcExtractor">

9. <ref local="nativeJdbcExtractor"/>

10. </property>

11. </bean>

12. …

13. </beans>

首先,必须定义一个能够从连接池中抽取出本地数据库JDBC对象(如OracleConnection,OracleResultSet等)的抽取器:nativeJdbcExtractor,这样才可以执行一些特定数据库的操作。对于那些仅封装了Connection而未包括Statement的简单数据连接池,SimpleNativeJdbcExtractor是效率最高的抽取器实现类,但具体到apache的BasicDataSource连接池,它封装了所有JDBC的对象,这时就需要使用CommonsDbcpNativeJdbcExtractor了。Spring针对几个著名的Web服务器的数据源提供了相应的JDBC抽取器:

·WebLogic:WebLogicNativeJdbcExtractor

·WebSphere:WebSphereNativeJdbcExtractor

·JBoss:JBossNativeJdbcExtractor

在定义了JDBC抽取器后,再定义lobHandler。Spring 1.2.5提供了两个lobHandler:

·DefaultLobHandler:适用于大部分的数据库,如SqlServer,MySQL,对Oracle 10g也适用,但不适用于Oracle 9i(看来Oracle 9i确实是个怪胎,谁叫Oracle 公司自己都说Oracle 9i是一个过渡性的产品呢)。

·OracleLobHandler:适用于Oracle 9i和Oracle 10g。

由于我们的数据库是Oracle9i,所以使用OracleLobHandler。

在配置完LobHandler后, 还需要将其注入到sessionFactory的Bean中,下面是调用后的sessionFactory Bean的配置:

代码 6 将lobHandler注入到sessionFactory中的配置

1. <beans>

2. …

3. <bean id="sessionFactory"

4. class="org.springframework.orm.hibernate3.LocalSessionFactoryBean">

5. <property name="dataSource" ref="dataSource"/>

6. <!-- 为处理Blob类型字段的句柄声明 //-->

7. <property name="lobHandler" ref="lobHandler"/>

8. …

9. </bean>

10. …

11. </beans>

如第7所示,通过sessionFactory的lobHandler属性进行注入。

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
2023年上半年GDP全球前十五强
 百态   2023-10-24
美众议院议长启动对拜登的弹劾调查
 百态   2023-09-13
上海、济南、武汉等多地出现不明坠落物
 探索   2023-09-06
印度或要将国名改为“巴拉特”
 百态   2023-09-06
男子为女友送行,买票不登机被捕
 百态   2023-08-20
手机地震预警功能怎么开?
 干货   2023-08-06
女子4年卖2套房花700多万做美容:不但没变美脸,面部还出现变形
 百态   2023-08-04
住户一楼被水淹 还冲来8头猪
 百态   2023-07-31
女子体内爬出大量瓜子状活虫
 百态   2023-07-25
地球连续35年收到神秘规律性信号,网友:不要回答!
 探索   2023-07-21
全球镓价格本周大涨27%
 探索   2023-07-09
钱都流向了那些不缺钱的人,苦都留给了能吃苦的人
 探索   2023-07-02
倩女手游刀客魅者强控制(强混乱强眩晕强睡眠)和对应控制抗性的关系
 百态   2020-08-20
美国5月9日最新疫情:美国确诊人数突破131万
 百态   2020-05-09
荷兰政府宣布将集体辞职
 干货   2020-04-30
倩女幽魂手游师徒任务情义春秋猜成语答案逍遥观:鹏程万里
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案神机营:射石饮羽
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案昆仑山:拔刀相助
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案天工阁:鬼斧神工
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案丝路古道:单枪匹马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:与虎谋皮
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:李代桃僵
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:指鹿为马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:小鸟依人
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:千金买邻
 干货   2019-11-12
 
>>返回首页<<
推荐阅读
 
 
频道精选
 
静静地坐在废墟上,四周的荒凉一望无际,忽然觉得,凄凉也很美
© 2005- 王朝网络 版权所有