`

hibernate的一个BUG

阅读更多
BUG简单描述:在Criteria联表查询中,Hibernate装组出无效的SQL。
版本:3.25GA,在最新版3.50rc2上BUG存在那个类中未发现有更改。


    下面是简单的示例代码:

    两个类:某类(FlexLink)和组织类(Organization),关系为多对一。

//创建查询器
		DetachedCriteria c = DetachedCriteria.forClass(FlexLink.class, "_link");
		//再创建一个子属性别名
		c.createAlias("_link.organization", "organization");
		//子属性的条件
		c.add(Restrictions.eq("organization.orgName", "xxx"));
		//只查部份属性
		ProjectionList projectionList = Projections.projectionList();
		projectionList.add(Projections.property("organization.orgName").as("organization.orgName"));
		c.setProjection(projectionList);
		//调用SPRING提供的DAO查询
		flexLinkDAO.getHibernateTemplate().findByCriteria(c);
		
		//生成的SQL:
		select
        	organizati1_.ORGANIZATION_NAME as y0_ 
	    from
	        BIS_FLEX_LINK this_ 
	    inner join
	        SYS_ORGANIZATION organizati1_ 
	            on this_.ORGANIZATION_ID=organizati1_.ORGANIZATION_ID 
	    where
	        y0_=?//问题就出在这里,这里可以用organizati1_.ORGANIZATION_NAME=?,但不能用y0_这个别名


    上面的SQL在ORACLE和MYSQL上都是不能执行的,y0_这别名不能用作条件关键字,但是可以用在order by 名子中,如order by y0_。
     那么是哪个类出错了?最直观看到的就是CriteriaQueryTranslator类的getColumnsUsingProjection方法:

/**
	 * Get the names of the columns constrained
	 * by this criterion.
	 * 此方法在criteria查中,把查询对象翻译成SQL时要用到,
	 * 用于取得JAVA属性名对应的SQL的字段名或SQL别名
	 * 在这里,getWhereCondition调用此方法组装where条件
	 */
	public String[] getColumnsUsingProjection(
			Criteria subcriteria,
	        String propertyName) throws HibernateException {

		//first look for a reference to a projection alias
		final Projection projection = rootCriteria.getProjection();
		//就是这一行有问题,就是这里返回了y0_这个别名,这里也不全错,上面说是order by y0_是可以的,
		//Hibernate组装order by 句子的时也要调用此方法,
		String[] projectionColumns = projection == null ?
		                             null :
		                             projection.getColumnAliases( propertyName, 0 );

		if ( projectionColumns == null ) {
			//it does not refer to an alias of a projection,
			//look for a property
			try {
				return getColumns( propertyName, subcriteria );
			}
			catch ( HibernateException he ) {
				//not found in inner query , try the outer query
				if ( outerQueryTranslator != null ) {
					return outerQueryTranslator.getColumnsUsingProjection( subcriteria, propertyName );
				}
				else {
					throw he;
				}
			}
		}
		else {
			//it refers to an alias of a projection
			return projectionColumns;
		}
	}


    改BUG方案:

     方案一,改源码:就把那行有问题的直接改成String[] projectionColumns = null就可以,或者直接保留try catch块就可以了,不影响。
     方案二,避免此问题:此问题的根本原因在于select句中为orgName这个字段建立了别名,所以在组装条件句时才取到别名,那如果select句中不查orgName这个字段就不会有这个问题。

    如果有更好的解决方法,欢迎讨论。
1
0
分享到:
评论

相关推荐

    hibernate的xml文件bug

    在IT行业中,Hibernate是一个非常流行的Java对象关系映射(ORM)框架,它允许开发者使用面向对象的编程方式来操作数据库,极大地简化了数据访问层的开发。然而,有时候在使用Hibernate的过程中,可能会遇到一些问题...

    Hibernate 3.2.4+ bug

    NULL 博文链接:https://imp9527.iteye.com/blog/438677

    Hibernate Synchronizer 插件重大缺陷改正

    然而,在实际应用中,用户遇到了一个严重的bug,该bug导致了程序无法正常启动,具体表现为log4j警告信息的输出和Hibernate配置解析失败。 ### 关键知识点分析 #### 1. Log4j警告信息 在日志中,首先出现的是关于...

    HIbernate免注解实现操作数据库 及Hibernate3连接SQL的BUG解决办法

    SessionFactory是线程安全的,整个应用生命周期只需一个实例。 3. **获取Session**: 通过SessionFactory获取`Session`实例,Session是与数据库交互的主要接口。 4. **实体类和数据表的映射**: 在XML映射文件中,...

    hibernate-release-5.2.10

    5.2.10版本是一个稳定版本,提供了一些bug修复和可能的新功能。对于开发者来说,这个版本意味着可以享受到稳定性和兼容性的保障。 在解压"hibernate-release-5.2.10.Final"后,我们可以找到以下关键组件: 1. **源...

    hibernate-3.13.zip

    Hibernate 是一个开源的对象关系映射(ORM)框架,它允许开发者使用面向对象的编程语言(如 Java)来处理数据库操作,极大地简化了数据访问层的开发。Hibernate 3.13 版本是 Hibernate 发展历程中的一个重要里程碑,...

    hibernate各个版本下载地址

    - **3.0 final (2005-03-31)**:3.0.x系列的初始版本,是Hibernate发展过程中的一个重要里程碑,引入了许多重要的新特性。 #### 下载地址 上述所有版本的下载地址均为:...

    Hibernate 中文手册 3.2.pdf

    Hibernate 3.2 版本是Hibernate历史上的一个重要版本,它引入了很多新的特性,例如注解支持,提高了开发的便捷性。注解允许开发者通过在Java类、方法、字段上使用元数据标记,来描述对象的持久化属性,而无需通过XML...

    hibernate-release-5.3.7.Final

    2. **changelog.txt**:这是一个非常重要的文件,它记录了从上一个版本到5.3.7.Final的所有改动,包括新功能、改进、修复的bug等。通过阅读此文件,开发者可以了解更新的内容和是否需要升级现有项目。 3. **lgpl....

    hibernate-release-4.2.4.Final.zip

    5. **Eclipse插件**:Eclipse是一个流行的Java集成开发环境(IDE),Hibernate为Eclipse提供了插件支持,使得开发者可以直接在IDE中配置、管理和调试Hibernate项目,提供图形化的HBM(Hibernate Mapping)文件编辑,...

    hibernate资料 3.6.6版本

    Hibernate是一个广泛使用的Java对象关系映射(ORM)工具,它允许开发人员用面向对象的方式来处理数据库交互,而无需直接编写SQL语句。在3.6.6这个版本中,可能会包含一些特定的功能、改进和修复的bug。 描述部分...

    hibernate5.2.6-compiled

    **hibernate5.2.6-compiled** 这个标题表明我们正在讨论的是Hibernate ORM框架的一个特定版本,即5.2.6的编译版本。Hibernate是一个流行的Java对象关系映射(ORM)工具,它允许开发人员使用面向对象的方式来处理...

    Hibernate的事务处理机制和flush方法的用法.docx

    当开始一个事务(`beginTransaction`),Hibernate会开启一个数据库事务,允许你在多个操作之间保持数据的一致性。在所有操作完成后,调用`commit`方法将提交事务,此时,Hibernate会清除缓存并更新数据库。 接下来...

    hibernate 2 升级参考文档

    与`SessionFactory`的配置一样,这个Bean的类路径也需更新,从`org.springframework.orm.hibernate.HibernateTransactionManager`更改为`org.springframework.orm.hibernate3.HibernateTransactionManager`,以利用...

    Middlegen-Hibernate-r5

    【Middlegen-Hibernate-r5】是一个开源项目,主要针对Java开发者,特别是那些在Web开发中使用Hibernate框架的程序员。Middlegen是该工具的名字,它是一个自动化数据库模型到Hibernate映射的工具,而Hibernate则是一...

    hibernate4.2.1

    Hibernate是一个开源的对象关系映射(ORM)框架,它允许Java开发者将数据库操作转换为对对象的操作,使得在处理数据库时可以使用面向对象的方式,大大简化了开发工作。 描述中提到"我是用的最新版本的hibernate,...

    hibernate4.2.2最终版jar包

    4. **Primary Key**:每个实体类通常有一个@Id注解的属性,作为主键,对应数据库表的主键字段。 5. **配置文件**:Hibernate的配置文件(hibernate.cfg.xml)定义了数据源、实体类扫描路径、方言、缓存策略等信息。...

    hibernate最新完整版5.3.0

    总的来说,“hibernate最新完整版5.3.0”提供了一个全面的ORM解决方案,适用于各种Java应用程序。开发者可以利用它来减少与数据库交互的复杂性,提高开发效率,同时享受官方发布的稳定性和兼容性。在使用时,确保...

    Hibernate3.2连接池

    Hibernate,作为一个流行的对象关系映射(ORM)框架,提供了多种连接池的集成方式。本文将详细阐述如何在Hibernate 3.2中配置和使用连接池,包括C3P0、DBCP和通过JNDI从容器获取连接池。 1. **使用Hibernate自带的...

    hibernate 4.1.4

    首先,Hibernate 4.1.4是Hibernate框架的一个稳定版本,它包含了众多的性能优化和新特性。此版本的主要改进在于对JPA 2.1规范的支持,这意味着开发者可以利用更多的标准API来处理数据,提高了代码的可移植性。此外,...

Global site tag (gtag.js) - Google Analytics