diff --git a/hibernate-core/src/main/antlr/hql.g b/hibernate-core/src/main/antlr/hql.g index 96e52d2f6f..df2e763825 100644 --- a/hibernate-core/src/main/antlr/hql.g +++ b/hibernate-core/src/main/antlr/hql.g @@ -684,7 +684,7 @@ identPrimary aggregate : ( SUM^ | AVG^ | MAX^ | MIN^ ) OPEN! additiveExpression CLOSE! { #aggregate.setType(AGGREGATE); } // Special case for count - It's 'parameters' can be keywords. - | COUNT^ OPEN! ( STAR { #STAR.setType(ROW_STAR); } | ( ( DISTINCT | ALL )? ( path | collectionExpr ) ) ) CLOSE! + | COUNT^ OPEN! ( STAR { #STAR.setType(ROW_STAR); } | ( ( DISTINCT | ALL )? ( path | collectionExpr | caseExpression ) ) ) CLOSE! | collectionExpr ; diff --git a/hibernate-core/src/test/java/org/hibernate/test/hql/ASTParserLoadingTest.java b/hibernate-core/src/test/java/org/hibernate/test/hql/ASTParserLoadingTest.java index 42e5d6f48a..1512cc13d6 100644 --- a/hibernate-core/src/test/java/org/hibernate/test/hql/ASTParserLoadingTest.java +++ b/hibernate-core/src/test/java/org/hibernate/test/hql/ASTParserLoadingTest.java @@ -23,6 +23,15 @@ */ package org.hibernate.test.hql; +import static org.hibernate.testing.junit4.ExtraAssertions.assertClassAssignability; +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertFalse; +import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertNull; +import static org.junit.Assert.assertSame; +import static org.junit.Assert.assertTrue; +import static org.junit.Assert.fail; + import java.math.BigDecimal; import java.math.BigInteger; import java.sql.Date; @@ -35,9 +44,6 @@ import java.util.Iterator; import java.util.List; import java.util.Map; -import org.jboss.logging.Logger; -import org.junit.Test; - import org.hibernate.Hibernate; import org.hibernate.HibernateException; import org.hibernate.Query; @@ -87,15 +93,8 @@ import org.hibernate.transform.Transformers; import org.hibernate.type.ComponentType; import org.hibernate.type.ManyToOneType; import org.hibernate.type.Type; - -import static org.hibernate.testing.junit4.ExtraAssertions.assertClassAssignability; -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertFalse; -import static org.junit.Assert.assertNotNull; -import static org.junit.Assert.assertNull; -import static org.junit.Assert.assertSame; -import static org.junit.Assert.assertTrue; -import static org.junit.Assert.fail; +import org.jboss.logging.Logger; +import org.junit.Test; /** * Tests the integration of the new AST parser into the loading of query results using @@ -550,6 +549,75 @@ public class ASTParserLoadingTest extends BaseCoreFunctionalTestCase { s.close(); } + @Test + @TestForIssue( jiraKey = "HHH-4150" ) + public void testSelectClauseCaseWithSum() { + Session s = openSession(); + Transaction t = s.beginTransaction(); + + Human h1 = new Human(); + h1.setBodyWeight( 74.0f ); + h1.setDescription( "Me" ); + s.persist( h1 ); + + Human h2 = new Human(); + h2.setBodyWeight( 125.0f ); + h2.setDescription( "big persion #1" ); + s.persist( h2 ); + + Human h3 = new Human(); + h3.setBodyWeight( 110.0f ); + h3.setDescription( "big persion #2" ); + s.persist( h3 ); + + s.flush(); + + Number count = (Number) s.createQuery( "select sum(case when bodyWeight > 100 then 1 else 0 end) from Human" ).uniqueResult(); + assertEquals( 2, count.intValue() ); + count = (Number) s.createQuery( "select sum(case when bodyWeight > 100 then bodyWeight else 0 end) from Human" ).uniqueResult(); + assertEquals( h2.getBodyWeight() + h3.getBodyWeight(), count.floatValue(), 0.001 ); + + t.rollback(); + s.close(); + } + + @Test + @TestForIssue( jiraKey = "HHH-4150" ) + public void testSelectClauseCaseWithCountDistinct() { + Session s = openSession(); + Transaction t = s.beginTransaction(); + + Human h1 = new Human(); + h1.setBodyWeight( 74.0f ); + h1.setDescription( "Me" ); + h1.setNickName( "Oney" ); + s.persist( h1 ); + + Human h2 = new Human(); + h2.setBodyWeight( 125.0f ); + h2.setDescription( "big persion" ); + h2.setNickName( "big #1" ); + s.persist( h2 ); + + Human h3 = new Human(); + h3.setBodyWeight( 110.0f ); + h3.setDescription( "big persion" ); + h3.setNickName( "big #2" ); + s.persist( h3 ); + + s.flush(); + + Number count = (Number) s.createQuery( "select count(distinct case when bodyWeight > 100 then description else null end) from Human" ).uniqueResult(); + assertEquals( 1, count.intValue() ); + count = (Number) s.createQuery( "select count(case when bodyWeight > 100 then description else null end) from Human" ).uniqueResult(); + assertEquals( 2, count.intValue() ); + count = (Number) s.createQuery( "select count(distinct case when bodyWeight > 100 then nickName else null end) from Human" ).uniqueResult(); + assertEquals( 2, count.intValue() ); + + t.rollback(); + s.close(); + } + @Test public void testInvalidCollectionDereferencesFail() { Session s = openSession();