显示标签为“Hibernate”的博文。显示所有博文
显示标签为“Hibernate”的博文。显示所有博文

2009年4月20日星期一

Hibernate与MS sql server配合异常

  • 应用环境
两表Ta、Tb关联;在Ta中设有set集合
HBM文件中设有lazy="true"或lazy="false"
  • 现象:
当lazy设为true时,报异常no session or session is closed.
当lazy设为false时,报异常ResultSet can not re-read row data for column 1。
  • 探究
对于lazy为true时,Hibernate采用延迟检索,即仅在缓存中保存关联的外键,而没有其他的字段或属性的内容,只在需要使用时才去检索,而这时Hibernate的session已经被关闭,从而导致异常;
对于lazy为false时,Hibernate采用立即检索,即会在查询主表时同时填充其关联表的属性内容;而这时有可能会引发“结果集某列不能重复读”的异常,其原因在于MS的驱动。详情请见http://support.microsoft.com/kb/824106。前人总结如下:
(1)如果采用jdbc-odbc驱动,那么就必须按照查询顺序来一次读取(不论有没有p_w_picpath或text类型)
(2)如果采用微软提供的ms sql server jdbc driver,如果查询语句中,不存在p_w_picpath或text类型字段,那么可以按照无序获取
(3)如果采用微软提供的ms sql server jdbc driver,如果查询语句中,存在p_w_picpath或text类型字段,那么就必须按照顺序读取,否则就会报告Driver]ResultSet can not re-read row data for column之类的错误
(4)如果想不查询语句中有没有p_w_picpath或text类型字段,都可以不按照顺序获取,或重复获取。
其意思就是要求在读取Resultset是尽量按照查询顺序读取【且只能读一次】,尤其是在字段中含有文本等类型时。
  • 解决途径:
当lazy设为true时,报异常no session or session is closed.
  1. Open session in view:
  2. 在web.xml中添加过滤器<filter>
    <filter-name>hibernateFilter</filter-name>
    <filter-class>
    org.springframework.orm.hibernate3.support.
    OpenSessionInViewFilter
    </filter-class>
    <init-param>
    <param-name>singleSession</param-name>
    <param-value>false</param-value>
    </init-param>
    </filter>
    <filter-mapping>
    <filter-name>hibernateFilter</filter-name>
    <url-pattern>/*</url-pattern>
    </filter-mapping>
同时去掉struts配置中的plug-in节中有关Spring的配置,使用web.xml中的listener配置Spring。

对于不能重复读的异常【网络搜集】:
  1. 自己调整sql代码或者是JAVA代码,确保顺序一致,从左到右严格读取,应该就没有问题;
  2. 修改数据库设计:将表中text\image等字段能修改的前提下更改掉,如text类型可以替换成varchar等;
  3. 在connection url后面加上SelectMethod=cursor【测试无效,可能由于采用数据源配置,无法传递后续参数?】
  4. 把所有的outer-join="auto"
    改为
    outer-join="false"【适用于Hibernate2.Hibernate3没有测试】
  5. 更换sql驱动,采用第三驱动,要使用jTDS驱动,配置要做一些变动: 数据库URL:jdbc:jtds:sqlserver://localhost:1433;DatabaseName=XXX
驱动类:net.sourceforge.jtds.jdbc.Driver 其在sourceforge上的介绍中写到:
Open source pure Java JDBC 2.1 driver for the Microsoft SQL Server series (6.5, 7.0 and 2000). jTDS is the fastest JDBC driver for MSSQL Server and is a complete implementation of the JDBC spec.
项目页:http://sourceforge.net/projects/jtds/http://jtds.sourceforge.net/

总体说来,建议采用jTDS驱动;考虑Open session in view。


2009年2月27日星期五

基于MyEclipse 6.0实现SSH整合:Struts(1.2)+Spring(2.0)+Hibernate(3.0)

给出一个简单示例:用户登录
  1. 新建Web project...
  1. 添加Struts能力
  1. 添加Spring能力
  2. 修改web.xml,添加listener和context-param节点

  3. org.springframework.web.context.ContextLoaderListener


    contextConfigLocation
    /WEB-INF/classes/applicationContext.xml


  4. 设计数据库,建立数据源
  5. 添加Hibernate能力

  6. 切至数据库透视,生成Hibernate配置文件
  7. 重构所有DAO类到DAO包
  8. 修改applicationContext.xml,添加相应的DAO bean
  9. 创建Form,Action和JSP
  10. 修改Action配置,class改为Spring的代理
  11. 修改Action类,添加服务Service作为属性
  12. 创建服务接口IService和相应的实现ServiceImpl类
  13. 修改applicationContext.xml,添加服务Service bean
  14. 修改applicationContext.xml,添加Action bean
  15. 在src目录下添加log4j.xml或log4j.properties,添加ehcache.xml
  16. 修改工程部署属性,设置成仅仅部署用户库
  17. 部署应用程序,启动Tomcat服务器
  18. 测试
  19. 小结