HHH-18584 disallow "ambiguous" queries for the deprecated createQuery() method

and add support for using 'this' alias to infer the 'select' list (JPA 3.2)

Signed-off-by: Gavin King <gavin@hibernate.org>
This commit is contained in:
Gavin King 2024-09-07 00:45:19 +02:00
parent 2630b33261
commit 306991f8d9
35 changed files with 286 additions and 194 deletions

View File

@ -36,32 +36,36 @@ public interface QueryProducer {
* is inferred:
* <ul>
* <li>if there is exactly one root entity in the {@code from}
* clause, then that root entity is the only element of the
* select list, or
* <li>otherwise, if there are multiple root entities in the
* {@code from} clause, then the select list contains every
* root entity and every non-{@code fetch} joined entity.
* clause, and it has no non-{@code fetch} joins, then that
* root entity is the only element of the select list, or
* <li>if there is an entity with the alias {@code this}, then
* that entity is the only element of the select list, or
* <li>otherwise, the query is considered ambiguous, and this
* method throws a {@link SemanticException}.
* </ul>
* <p>
* The query must have an explicit {@code from} clause, which
* can never be inferred.
*
* @deprecated The overloaded form
* {@link #createQuery(String, Class)} which takes a result type
* is strongly recommended in preference to this method, since it
* returns a typed {@code Query} object, and because it is able to
* use the given result type to infer the {@code select} list, and
* even sometimes the {@code from} clause. Alternatively,
* {@link #createSelectionQuery(String, Class)} is preferred for
* queries, and {@link #createMutationQuery(String)} for insert,
* update, and delete statements.
*
* @apiNote Returns a raw {@code Query} type instead of a wildcard
* type {@code Query<?>}, to match the signature of the JPA method
* {@link jakarta.persistence.EntityManager#createQuery(String)}.
*
* @implNote This method interprets some queries with an implicit
* {@code select} list in a quite unintuitive way. In some future
* release, this method will be modified to throw an exception
* when passed a query with a missing {@code select}. For now, use
* {@link #createQuery(String, Class)} to avoid ambiguity.
*
* @param queryString The HQL query
*
* @return The {@link Query} instance for manipulation and execution
*
* @see jakarta.persistence.EntityManager#createQuery(String)
*
* @deprecated use {@link #createQuery(String, Class)},
* {@link #createSelectionQuery(String, Class)}, or
* {@link #createMutationQuery(String)} depending on intention
*/
@Deprecated(since = "6.0") @SuppressWarnings("rawtypes")
Query createQuery(String queryString);
@ -95,11 +99,21 @@ public interface QueryProducer {
* as specified above.
* </ul>
* <p>
* If a query has no explicit {@code from} clause, and the given
* result type is an entity type, the root entity is inferred to
* be the result type.
* <p>
* Passing {@code Object.class} as the query result type is not
* recommended. In this special case, this method has the same
* semantics as the overload {@link #createQuery(String)}.
* <p>
* The returned {@code Query} may be executed by calling
* {@link Query#getResultList()} or {@link Query#getSingleResult()}.
*
* @param queryString The HQL query
* @param resultClass The type of the query result
* @param resultClass The {@link Class} object representing the
* query result type, which should not be
* {@code Object.class}
* @return The {@link Query} instance for manipulation and execution
*
* @see jakarta.persistence.EntityManager#createQuery(String,Class)
@ -247,23 +261,28 @@ public interface QueryProducer {
* select list is inferred:
* <ul>
* <li>if there is exactly one root entity in the {@code from}
* clause, then that root entity is the only element of the
* select list, or
* <li>otherwise, if there are multiple root entities in the
* {@code from} clause, then the select list contains every
* root entity and every non-{@code fetch} joined entity.
* clause, and it has no non-{@code fetch} joins, then that
* root entity is the only element of the select list, or
* <li>if there is an entity with the alias {@code this}, then
* that entity is the only element of the select list, or
* <li>otherwise, the query is considered ambiguous, and this
* method throws a {@link SemanticException}.
* </ul>
* <p>
* The query must have an explicit {@code from} clause, which
* can never be inferred.
*
* @implNote This method interprets some queries with an implicit
* {@code select} list in a quite unintuitive way. In some future
* release, this method will be modified to throw an exception
* when passed a query with a missing {@code select}. For now, use
* {@link #createSelectionQuery(String, Class)} to avoid ambiguity.
* @deprecated The overloaded form
* {@link #createSelectionQuery(String, Class)} which takes a
* result type is strongly recommended in preference to this
* method, since it returns a typed {@code SelectionQuery} object,
* and because it is able to use the given result type to infer
* the {@code select} list, and even sometimes the {@code from}
* clause.
*
* @throws IllegalSelectQueryException if the given HQL query
* is an insert, update or delete query
*
* @deprecated Use {@link #createSelectionQuery(String, Class)}
* is an {@code insert}, {@code update} or {@code delete}
* statement
*/
@Deprecated(since = "6.3")
SelectionQuery<?> createSelectionQuery(String hqlString);
@ -297,17 +316,27 @@ public interface QueryProducer {
* as specified above.
* </ul>
* <p>
* If a query has no explicit {@code from} clause, and the given
* result type is an entity type, the root entity is inferred to
* be the result type.
* <p>
* Passing {@code Object.class} as the query result type is not
* recommended. In this special case, this method has the same
* semantics as the overload {@link #createSelectionQuery(String)}.
* <p>
* The returned {@code Query} may be executed by calling
* {@link Query#getResultList()} or {@link Query#getSingleResult()}.
* @param hqlString The HQL query as a string
* @param hqlString The HQL {@code select} query as a string
* @param resultType The {@link Class} object representing the
* query result type
* query result type, which should not be
* {@code Object.class}
*
* @see jakarta.persistence.EntityManager#createQuery(String)
*
* @throws IllegalSelectQueryException if the given HQL query
* is an insert, update or delete query
* is an {@code insert}, {@code update} or {@code delete}
* statement
*/
<R> SelectionQuery<R> createSelectionQuery(String hqlString, Class<R> resultType);
@ -323,8 +352,11 @@ public interface QueryProducer {
* Create a {@link MutationQuery} reference for the given HQL insert,
* update, or delete statement.
*
* @param hqlString The HQL {@code insert}, {@code update}, or
* {@code delete} statement
*
* @throws IllegalMutationQueryException if the given HQL query
* is a select query
* is a {@code select} query
*/
MutationQuery createMutationQuery(String hqlString);

View File

@ -26,7 +26,6 @@ import java.util.ArrayList;
import java.util.Calendar;
import java.util.GregorianCalendar;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Locale;
@ -1327,20 +1326,61 @@ public class SemanticQueryBuilder<R> extends HqlParserBaseVisitor<Object> implem
final NodeBuilder nodeBuilder = creationContext.getNodeBuilder();
final SqmSelectClause selectClause;
final boolean singleEntityResult;
for ( SqmRoot<?> sqmRoot : fromClause.getRoots() ) {
if ( "this".equals( sqmRoot.getExplicitAlias() ) ) {
// we found an entity with the alias 'this'
// assigned explicitly, JPA says we should
// infer the select list 'select this'
SqmSelectClause selectClause = new SqmSelectClause( false, 1, nodeBuilder );
selectClause.addSelection( new SqmSelection<>( sqmRoot, "this", nodeBuilder) );
return selectClause;
}
}
if ( expectedResultType == null ) {
// no result type was specified
// - if there is a single root entity return the entity,
// even if it has non-fetch joins (ugh!)
// - otherwise, return all entities in an Object[] array,
// including non-fetch joins
selectClause = new SqmSelectClause( false, nodeBuilder );
singleEntityResult = fromClause.getNumberOfRoots() == 1;
if ( processingStateStack.getCurrent().getProcessingQuery() instanceof SqmSubQuery ) {
// a subquery ... the following is a bit arbitrary
final SqmSelectClause selectClause = new SqmSelectClause( false, nodeBuilder );
fromClause.visitRoots( sqmRoot -> {
selectClause.addSelection( new SqmSelection<>( sqmRoot, sqmRoot.getAlias(), nodeBuilder) );
applyJoinsToInferredSelectClause( sqmRoot, selectClause );
} );
return selectClause;
}
else {
// no result type was specified (and this isn't a subquery)
// if there's a single root entity with no non-fetch joins,
// we may safely assume the query returns that entity
if ( fromClause.getNumberOfRoots() == 1 ) {
final SqmRoot<?> sqmRoot = fromClause.getRoots().get(0);
if ( sqmRoot.hasTrueJoin() ) {
// the entity has joins, and doesn't explicitly have
// the alias 'this', so the 'select' list cannot be
// inferred
throw new SemanticException( "Query has no 'select' clause, and joins, but no result type was given"
+ " (pass an explicit result type to 'createQuery()')", query );
}
// exactly one root entity, and no joins - this includes
// the case where JPA says the entity has an implicit alias
// 'this', and that we should infer 'select this', but we
// accept even the case where the entity has an explicit
// alias, and infer 'select explicit_alias'
SqmSelectClause selectClause = new SqmSelectClause( false, 1, nodeBuilder );
selectClause.addSelection( new SqmSelection<>( sqmRoot, sqmRoot.getAlias(), nodeBuilder) );
return selectClause;
}
else {
// there's more than one entity, and no entity is 'this',
// therefore the 'select' list cannot be inferred
throw new SemanticException( "Query has no 'select' clause, and multiple root entities, but no result type was given"
+ " (pass an explicit result type to 'createQuery()')", query );
}
}
}
else {
singleEntityResult = creationContext.getJpaMetamodel().findEntityType( expectedResultType ) != null;
if ( singleEntityResult ) {
// we have an explicit result type, so we can use that to
// help infer the 'select' list
if ( creationContext.getJpaMetamodel().findEntityType( expectedResultType ) != null ) {
// the result type is an entity class
if ( fromClause.getNumberOfRoots() > 1 ) {
// multiple root entities
@ -1358,29 +1398,30 @@ public class SemanticQueryBuilder<R> extends HqlParserBaseVisitor<Object> implem
else {
// exactly one root entity, return it
// (joined entities are not returned)
selectClause = new SqmSelectClause( false, 1, nodeBuilder );
final SqmSelectClause selectClause = new SqmSelectClause( false, 1, nodeBuilder );
selectClause.addSelection( new SqmSelection<>( sqmRoot, sqmRoot.getAlias(), nodeBuilder) );
return selectClause;
}
}
}
else {
// the result type is not an entity class
// return all root entities and non-fetch joins
selectClause = new SqmSelectClause( false, nodeBuilder );
// the result type is not an entity class, and so
// it must be some sort of object which packages
// a multi-element projection list - let's return
// all root entities and non-fetch joins, and see
// later on if the result type can really hold them
final SqmSelectClause selectClause = new SqmSelectClause( false, nodeBuilder );
fromClause.visitRoots( sqmRoot -> {
selectClause.addSelection( new SqmSelection<>( sqmRoot, sqmRoot.getAlias(), nodeBuilder) );
applyJoinsToInferredSelectClause( sqmRoot, selectClause );
} );
return selectClause;
}
}
fromClause.visitRoots( (sqmRoot) -> {
selectClause.addSelection( new SqmSelection<>( sqmRoot, sqmRoot.getAlias(), nodeBuilder) );
if ( !singleEntityResult ) {
applyJoinsToInferredSelectClause( sqmRoot, selectClause );
}
} );
return selectClause;
}
private void applyJoinsToInferredSelectClause(SqmFrom<?,?> sqm, SqmSelectClause selectClause) {
sqm.visitSqmJoins( (sqmJoin) -> {
sqm.visitSqmJoins( sqmJoin -> {
if ( sqmJoin.isImplicitlySelectable() ) {
selectClause.addSelection( new SqmSelection<>( sqmJoin, sqmJoin.getAlias(), creationContext.getNodeBuilder() ) );
applyJoinsToInferredSelectClause( sqmJoin, selectClause );

View File

@ -60,6 +60,7 @@ import jakarta.persistence.metamodel.PluralAttribute;
import jakarta.persistence.metamodel.SetAttribute;
import jakarta.persistence.metamodel.SingularAttribute;
import static org.hibernate.metamodel.AttributeClassification.EMBEDDED;
import static org.hibernate.query.sqm.internal.SqmUtil.findCompatibleFetchJoin;
/**
@ -298,12 +299,20 @@ public abstract class AbstractSqmFrom<O,T> extends AbstractSqmPath<T> implements
@Override
public Set<Join<T, ?>> getJoins() {
//noinspection unchecked
return (Set<Join<T, ?>>) (Set<?>) getSqmJoins().stream()
.filter( sqmJoin -> sqmJoin instanceof SqmAttributeJoin && !( (SqmAttributeJoin<?, ?>) sqmJoin ).isFetched() )
return getSqmJoins().stream()
.filter( sqmJoin -> sqmJoin instanceof SqmAttributeJoin<?,?> attributeJoin
&& !attributeJoin.isFetched() )
.collect( Collectors.toSet() );
}
@Override
public boolean hasTrueJoin() {
return getSqmJoins().stream()
.anyMatch( sqmJoin -> sqmJoin instanceof SqmAttributeJoin<?,?> attributeJoin
&& !attributeJoin.isFetched()
&& attributeJoin.getAttribute().getAttributeClassification()!=EMBEDDED );
}
@Override
public <A> SqmSingularJoin<T, A> join(SingularAttribute<? super T, A> attribute) {
return join( attribute, JoinType.INNER );
@ -644,7 +653,8 @@ public abstract class AbstractSqmFrom<O,T> extends AbstractSqmPath<T> implements
public Set<Fetch<T, ?>> getFetches() {
//noinspection unchecked
return (Set<Fetch<T, ?>>) (Set<?>) getSqmJoins().stream()
.filter( sqmJoin -> sqmJoin instanceof SqmAttributeJoin && ( (SqmAttributeJoin<?, ?>) sqmJoin ).isFetched() )
.filter( sqmJoin -> sqmJoin instanceof SqmAttributeJoin<?,?> attributeJoin
&& attributeJoin.isFetched() )
.collect( Collectors.toSet() );
}

View File

@ -16,6 +16,7 @@ import jakarta.persistence.metamodel.MapAttribute;
import jakarta.persistence.metamodel.SetAttribute;
import jakarta.persistence.metamodel.SingularAttribute;
import org.hibernate.Incubating;
import org.hibernate.metamodel.model.domain.EntityDomainType;
import org.hibernate.query.criteria.JpaFrom;
import org.hibernate.query.sqm.SqmPathSource;
@ -100,6 +101,9 @@ public interface SqmFrom<L, R> extends SqmVisitableNode, SqmPath<R>, JpaFrom<L,
@Override
<Y> SqmEntityJoin<R, Y> join(Class<Y> entityClass, JoinType joinType);
@Incubating
boolean hasTrueJoin();
@Override
<A> SqmSingularJoin<R, A> join(SingularAttribute<? super R, A> attribute);

View File

@ -10,7 +10,6 @@ import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import org.hibernate.internal.util.collections.CollectionHelper;
import org.hibernate.query.criteria.JpaSelection;
import org.hibernate.query.sqm.NodeBuilder;
import org.hibernate.query.sqm.tree.AbstractSqmNode;
@ -18,6 +17,8 @@ import org.hibernate.query.sqm.tree.SqmCopyContext;
import org.hibernate.query.sqm.tree.expression.SqmExpression;
import org.hibernate.type.descriptor.java.JavaType;
import static org.hibernate.internal.util.collections.CollectionHelper.arrayList;
/**
* The semantic select clause. Defined as a list of individual selections.
*
@ -40,7 +41,7 @@ public class SqmSelectClause extends AbstractSqmNode implements SqmAliasedExpres
NodeBuilder nodeBuilder) {
super( nodeBuilder );
this.distinct = distinct;
this.selections = CollectionHelper.arrayList( expectedNumberOfSelections );
this.selections = arrayList( expectedNumberOfSelections );
}
@Override

View File

@ -139,7 +139,7 @@ public class EmbeddableCollectionElementWithLazyManyToOneTest {
scope.inTransaction(
session ->
assertFalse( session.createQuery(
"from Parent p join p.containedChildren c where c.child.id is not null" )
"from Parent p join p.containedChildren c where c.child.id is not null", Parent.class )
.getResultList()
.isEmpty() )

View File

@ -31,9 +31,9 @@ public class EmbeddableWithMany2OneTest {
public void testJoinAcrossEmbedded(SessionFactoryScope scope) {
scope.inTransaction(
session -> {
session.createQuery( "from Person p join p.address as a join a.country as c where c.name = 'US'" )
session.createQuery( "from Person p join p.address as a join a.country as c where c.name = 'US'", Person.class )
.list();
session.createQuery( "from Person p join p.address as a join a.country as c where c.id = 'US'" )
session.createQuery( "from Person p join p.address as a join a.country as c where c.id = 'US'", Person.class )
.list();
}
);

View File

@ -56,7 +56,7 @@ public class IdManyToOneTest extends BaseCoreFunctionalTestCase {
@TestForIssue( jiraKey = "HHH-7767" )
public void testCriteriaRestrictionOnIdManyToOne() {
inTransaction( s -> {
s.createQuery( "from Course c join c.students cs join cs.student s where s.name = 'Foo'" ).list();
s.createQuery( "from Course c join c.students cs join cs.student s where s.name = 'Foo'", Object[].class ).list();
CriteriaBuilder criteriaBuilder = s.getCriteriaBuilder();
CriteriaQuery<Course> criteria = criteriaBuilder.createQuery( Course.class );

View File

@ -29,7 +29,7 @@ public class Misc0Test {
s.persist(a);
s.persist(b);
s.createQuery("from B join entityA").getSingleResult();
s.createQuery("from B join entityA", EntityB.class).getSingleResult();
});
}

View File

@ -26,7 +26,7 @@ public class Misc1Test {
s.persist(a);
s.persist(b);
s.createQuery("from B join entityA").getSingleResult();
s.createQuery("from B join entityA", EntityB.class).getSingleResult();
});
}

View File

@ -14,8 +14,8 @@ import org.junit.jupiter.api.Test;
public class FieldWithUnderscoreTest {
@Test void test(SessionFactoryScope scope) {
scope.inSession(s -> s.createSelectionQuery("from B join _a").getResultList());
scope.inSession(s -> s.createSelectionQuery("from B left join fetch _a").getResultList());
scope.inSession(s -> s.createSelectionQuery("from B join _a", B.class).getResultList());
scope.inSession(s -> s.createSelectionQuery("from B left join fetch _a", B.class).getResultList());
}
@Entity(name = "A")

View File

@ -608,7 +608,7 @@ public class EmbeddedTest {
scope.inTransaction(
session -> {
InternetProvider internetProviderQueried =
(InternetProvider) session.createQuery( "from InternetProvider" ).uniqueResult();
session.createQuery( "from InternetProvider", InternetProvider.class ).uniqueResult();
assertFalse( Hibernate.isInitialized( internetProviderQueried.getOwner().getTopManagement() ) );
}
@ -617,8 +617,7 @@ public class EmbeddedTest {
scope.inTransaction(
session -> {
InternetProvider internetProviderQueried =
(InternetProvider) session.createQuery(
"from InternetProvider i join fetch i.owner.topManagement" )
session.createQuery( "from InternetProvider i join fetch i.owner.topManagement", InternetProvider.class )
.uniqueResult();
assertTrue( Hibernate.isInitialized( internetProviderQueried.getOwner().getTopManagement() ) );

View File

@ -135,7 +135,7 @@ public class CompositeIdTest {
}
statementInspector.assertExecutedCount( 1 );
statementInspector.clear();
iter = session.createQuery( "from Order o join o.lineItems li" ).list().iterator();
iter = session.createQuery( "from Order o join o.lineItems li", Order.class ).list().iterator();
statementInspector.assertExecutedCount( 2 );
statementInspector.clear();
while ( iter.hasNext() ) {

View File

@ -126,7 +126,7 @@ public class CompositeElementTest extends BaseNonConfigCoreFunctionalTestCase {
c = (Child) p.getChildren().iterator().next();
assertEquals( 1, c.getPosition() );
p = (Parent) s.createQuery( "from Parent p join p.children c where c.position = 1" ).uniqueResult();
p = s.createQuery( "from Parent p join p.children c where c.position = 1", Parent.class ).uniqueResult();
c = (Child) p.getChildren().iterator().next();
assertEquals( 1, c.getPosition() );

View File

@ -96,7 +96,7 @@ public class CompositePropertyRefTest {
}
session.clear();
l = session.createQuery( "from Person p left join p.accounts" ).list();
l = session.createQuery( "from Person p left join p.accounts", Person.class ).list();
for ( int i = 0; i < 2; i++ ) {
Person px = (Person) l.get( i );
Set accounts = px.getAccounts();

View File

@ -63,7 +63,7 @@ public class FormulaJoinTest extends BaseCoreFunctionalTestCase {
s = openSession();
tx = s.beginTransaction();
List l = s.createQuery("from Root m left join m.detail d").list();
List l = s.createQuery("from Root m left join m.detail d", Object[].class).list();
assertEquals( l.size(), 1 );
tx.commit();
s.close();

View File

@ -944,10 +944,10 @@ public class ASTParserLoadingTest extends BaseCoreFunctionalTestCase {
inTransaction(
s,
session -> {
s.createQuery( "from Animal a join a.offspring o where o.description = 'xyz'" ).list();
s.createQuery( "from Animal a join a.offspring o where o.father.description = 'xyz'" ).list();
s.createQuery( "from Animal a join a.offspring o order by o.description" ).list();
s.createQuery( "from Animal a join a.offspring o order by o.father.description" ).list();
s.createQuery( "from Animal a join a.offspring o where o.description = 'xyz'", Object[].class ).list();
s.createQuery( "from Animal a join a.offspring o where o.father.description = 'xyz'", Object[].class ).list();
s.createQuery( "from Animal a join a.offspring o order by o.description", Object[].class ).list();
s.createQuery( "from Animal a join a.offspring o order by o.father.description", Object[].class ).list();
}
);
@ -1285,7 +1285,7 @@ public class ASTParserLoadingTest extends BaseCoreFunctionalTestCase {
s = openSession();
s.beginTransaction();
Object [] result = ( Object [] ) s.createQuery( "from User u, Human h where u.human = h" ).uniqueResult();
Object [] result = s.createQuery( "from User u, Human h where u.human = h", Object[].class ).uniqueResult();
assertNotNull( result );
assertEquals( u.getUserName(), ( (User) result[0] ).getUserName() );
assertEquals( h.getName().getFirst(), ( (Human) result[1] ).getName().getFirst() );
@ -1650,11 +1650,11 @@ public class ASTParserLoadingTest extends BaseCoreFunctionalTestCase {
// TODO : setEntity() currently will not work here, but that would be *very* nice
// does not work because the corresponding EntityType is then used as the "bind type" rather
// than the "discovered" AnyType...
s.createQuery( "from PropertySet p where p.someSpecificProperty = :ssp" ).setParameter( "ssp", redValue ).list();
s.createQuery( "from PropertySet p where p.someSpecificProperty = :ssp", PropertySet.class ).setParameter( "ssp", redValue ).list();
s.createQuery( "from PropertySet p where p.someSpecificProperty.id is not null" ).list();
s.createQuery( "from PropertySet p where p.someSpecificProperty.id is not null", PropertySet.class ).list();
s.createQuery( "from PropertySet p join p.generalProperties gp where gp.id is not null" ).list();
s.createQuery( "from PropertySet p join p.generalProperties gp where gp.id is not null", PropertySet.class ).list();
s.remove( s.getReference( PropertySet.class, id ) );
@ -3803,7 +3803,7 @@ public class ASTParserLoadingTest extends BaseCoreFunctionalTestCase {
public SyntaxChecker checkList() {
Session s = openSession();
s.beginTransaction();
Query query = s.createQuery( hql );
Query query = s.createQuery( hql, Object[].class );
preparer.prepare( query );
query.list();
s.getTransaction().commit();
@ -3814,7 +3814,7 @@ public class ASTParserLoadingTest extends BaseCoreFunctionalTestCase {
public SyntaxChecker checkScroll() {
Session s = openSession();
s.beginTransaction();
Query query = s.createQuery( hql );
Query query = s.createQuery( hql, Object[].class );
preparer.prepare( query );
query.scroll().close();
s.getTransaction().commit();

View File

@ -17,7 +17,6 @@ import jakarta.persistence.Table;
import org.hibernate.Session;
import org.hibernate.testing.FailureExpected;
import org.hibernate.testing.TestForIssue;
import org.hibernate.testing.junit4.BaseCoreFunctionalTestCase;
import org.junit.Test;
@ -114,7 +113,7 @@ public class SubQueryTest extends BaseCoreFunctionalTestCase {
String qry = "from Root as r " +
"where r.branch.branchName = 'branch' " +
" and exists( from r.branch.leaves as s where s.leafName = 'leaf1')";
Root rootQueried = (Root) s.createQuery( qry ).uniqueResult();
Root rootQueried = s.createQuery( qry, Root.class ).uniqueResult();
assertEquals( root.rootName, rootQueried.rootName );
assertEquals( root.branch.branchName, rootQueried.branch.branchName );
assertEquals( leaf1.leafName, rootQueried.branch.leaves.get( 0 ).leafName );

View File

@ -80,29 +80,29 @@ public class WithClauseTest {
scope.inTransaction(
(session) -> {
// one-to-many
List list = session.createQuery( "from Human h inner join h.offspring as o with o.bodyWeight < :someLimit" )
List list = session.createQuery( "from Human h inner join h.offspring as o with o.bodyWeight < :someLimit", Human.class )
.setParameter( "someLimit", 1 )
.list();
assertTrue( list.isEmpty(), "ad-hoc on did not take effect" );
// many-to-one
list = session.createQuery( "from Animal a inner join a.mother as m with m.bodyWeight < :someLimit" )
list = session.createQuery( "from Animal a inner join a.mother as m with m.bodyWeight < :someLimit", Animal.class )
.setParameter( "someLimit", 1 )
.list();
assertTrue( list.isEmpty(), "ad-hoc on did not take effect" );
list = session.createQuery( "from Human h inner join h.friends f with f.bodyWeight < :someLimit" )
list = session.createQuery( "from Human h inner join h.friends f with f.bodyWeight < :someLimit", Human.class )
.setParameter( "someLimit", 25 )
.list();
assertTrue( !list.isEmpty(), "ad-hoc on did take effect" );
// many-to-many
list = session.createQuery( "from Human h inner join h.friends as f with f.nickName like 'bubba'" )
list = session.createQuery( "from Human h inner join h.friends as f with f.nickName like 'bubba'", Human.class )
.list();
assertTrue( list.isEmpty(), "ad-hoc on did not take effect" );
// http://opensource.atlassian.com/projects/hibernate/browse/HHH-1930
list = session.createQuery( "from Human h inner join h.nickNames as nicknames with nicknames = 'abc'" )
list = session.createQuery( "from Human h inner join h.nickNames as nicknames with nicknames = 'abc'", Human.class )
.list();
assertTrue( list.isEmpty(), "ad-hoc on did not take effect" );
@ -114,7 +114,7 @@ public class WithClauseTest {
public void testWithClauseWithImplicitJoin(SessionFactoryScope scope) {
scope.inTransaction(
(session) -> {
List list = session.createQuery( "from Human h inner join h.offspring o with o.mother.father = :cousin" )
List list = session.createQuery( "from Human h inner join h.offspring o with o.mother.father = :cousin", Object[].class )
.setParameter( "cousin", session.getReference( Human.class, Long.valueOf( "123" ) ) )
.list();
assertTrue( list.isEmpty(), "ad-hoc did take effect" );
@ -167,7 +167,7 @@ public class WithClauseTest {
(session) -> {
// Since friends has a join table, we will first left join all friends and then do the WITH clause on the target entity table join
// Normally this produces 2 results which is wrong and can only be circumvented by converting the join table and target entity table join to a subquery
List list = session.createQuery( "from Human h left join h.friends as f with f.nickName like 'bubba' where h.description = 'father'" )
List list = session.createQuery( "from Human h left join h.friends as f with f.nickName like 'bubba' where h.description = 'father'", Object[].class )
.list();
assertEquals( 1, list.size(), "subquery rewriting of join table did not take effect" );
}
@ -180,7 +180,7 @@ public class WithClauseTest {
scope.inTransaction(
(session) -> {
// Like testWithClauseAsSubquery but uses equal operator since it render differently in SQL
List list = session.createQuery( "from Human h left join h.friends as f with f.nickName = 'bubba' where h.description = 'father'" )
List list = session.createQuery( "from Human h left join h.friends as f with f.nickName = 'bubba' where h.description = 'father'", Object[].class )
.list();
assertEquals( 1, list.size(), "subquery rewriting of join table did not take effect" );
}
@ -194,7 +194,7 @@ public class WithClauseTest {
(session) -> {
// Since family has a join table, we will first left join all family members and then do the WITH clause on the target entity table join
// Normally this produces 2 results which is wrong and can only be circumvented by converting the join table and target entity table join to a subquery
List list = session.createQuery( "from Human h left join h.family as f with key(f) like 'son1' where h.description = 'father'" )
List list = session.createQuery( "from Human h left join h.family as f with key(f) like 'son1' where h.description = 'father'", Object[].class )
.list();
assertEquals( 1, list.size(), "subquery rewriting of join table did not take effect" );
}

View File

@ -85,7 +85,7 @@ public class IdBagTest {
session.persist( plebs );
session.persist( admins );
List l = session.createQuery( "from User u join u.groups g" ).list();
List l = session.createQuery( "from User u join u.groups g", User.class ).list();
assertEquals( 1, l.size() );
session.clear();

View File

@ -64,7 +64,7 @@ public class MappedSuperclassExtendsEntityTest {
scope.inTransaction(
s ->
s.createQuery(
"FROM TestEntity e JOIN e.parents p1 JOIN p1.entities JOIN p1.entities2 JOIN e.parents2 p2 JOIN p2.entities JOIN p2.entities2" )
"FROM TestEntity e JOIN e.parents p1 JOIN p1.entities JOIN p1.entities2 JOIN e.parents2 p2 JOIN p2.entities JOIN p2.entities2", Object[].class )
.getResultList()
);
}
@ -75,7 +75,7 @@ public class MappedSuperclassExtendsEntityTest {
// Make sure that the produced query for th
scope.inTransaction(
s ->
s.createQuery( "from TestEntity" ).list()
s.createQuery( "from TestEntity", TestEntity.class ).list()
);
}

View File

@ -65,7 +65,7 @@ public class NonPkAssociationEqualityPredicateTest {
scope.inTransaction(
entityManager -> {
// This fails because we compare a ToOne with non-PK to something with a EntityValuedModelPart which defaults to the PK mapping
entityManager.createQuery( "from Order o, Customer c where o.customer = c" ).getResultList();
entityManager.createQuery( "from Order o, Customer c where o.customer = c", Object[].class ).getResultList();
}
);
}

View File

@ -23,11 +23,9 @@ import java.util.List;
import java.util.Set;
import org.hibernate.Session;
import org.hibernate.Transaction;
import org.junit.Test;
import org.hibernate.testing.FailureExpected;
import org.hibernate.testing.TestForIssue;
import org.hibernate.testing.junit4.BaseCoreFunctionalTestCase;
@ -54,13 +52,13 @@ public class TreatKeywordTest extends BaseCoreFunctionalTestCase {
// todo : assert invalid naming of non-subclasses in TREAT statement
Session s = openSession();
s.createQuery( "from DiscriminatorEntity e join treat(e.other as DiscriminatorEntitySubclass) o" ).list();
s.createQuery( "from DiscriminatorEntity e join treat(e.other as DiscriminatorEntitySubSubclass) o" ).list();
s.createQuery( "from DiscriminatorEntitySubclass e join treat(e.other as DiscriminatorEntitySubSubclass) o" ).list();
s.createQuery( "from DiscriminatorEntity e join treat(e.other as DiscriminatorEntitySubclass) o", Object[].class ).list();
s.createQuery( "from DiscriminatorEntity e join treat(e.other as DiscriminatorEntitySubSubclass) o", Object[].class ).list();
s.createQuery( "from DiscriminatorEntitySubclass e join treat(e.other as DiscriminatorEntitySubSubclass) o", Object[].class ).list();
s.createQuery( "from JoinedEntity e join treat(e.other as JoinedEntitySubclass) o" ).list();
s.createQuery( "from JoinedEntity e join treat(e.other as JoinedEntitySubSubclass) o" ).list();
s.createQuery( "from JoinedEntitySubclass e join treat(e.other as JoinedEntitySubSubclass) o" ).list();
s.createQuery( "from JoinedEntity e join treat(e.other as JoinedEntitySubclass) o", Object[].class ).list();
s.createQuery( "from JoinedEntity e join treat(e.other as JoinedEntitySubSubclass) o", Object[].class ).list();
s.createQuery( "from JoinedEntitySubclass e join treat(e.other as JoinedEntitySubSubclass) o", Object[].class ).list();
s.close();
}
@ -81,19 +79,19 @@ public class TreatKeywordTest extends BaseCoreFunctionalTestCase {
s.beginTransaction();
// in select clause
List result = s.createQuery( "select e from DiscriminatorEntity e" ).list();
List result = s.createQuery( "select e from DiscriminatorEntity e", Object[].class ).list();
assertEquals( 2, result.size() );
result = s.createQuery( "select treat (e as DiscriminatorEntitySubclass) from DiscriminatorEntity e" ).list();
result = s.createQuery( "select treat (e as DiscriminatorEntitySubclass) from DiscriminatorEntity e", Object[].class ).list();
assertEquals( 1, result.size() );
result = s.createQuery( "select treat (e as DiscriminatorEntitySubSubclass) from DiscriminatorEntity e" ).list();
result = s.createQuery( "select treat (e as DiscriminatorEntitySubSubclass) from DiscriminatorEntity e", Object[].class ).list();
assertEquals( 0, result.size() );
// in join
result = s.createQuery( "from DiscriminatorEntity e inner join e.other" ).list();
result = s.createQuery( "from DiscriminatorEntity e inner join e.other", DiscriminatorEntity.class ).list();
assertEquals( 1, result.size() );
result = s.createQuery( "from DiscriminatorEntity e inner join treat (e.other as DiscriminatorEntitySubclass)" ).list();
result = s.createQuery( "from DiscriminatorEntity e inner join treat (e.other as DiscriminatorEntitySubclass)", DiscriminatorEntity.class ).list();
assertEquals( 0, result.size() );
result = s.createQuery( "from DiscriminatorEntity e inner join treat (e.other as DiscriminatorEntitySubSubclass)" ).list();
result = s.createQuery( "from DiscriminatorEntity e inner join treat (e.other as DiscriminatorEntitySubSubclass)", DiscriminatorEntity.class ).list();
assertEquals( 0, result.size() );
s.close();
@ -133,11 +131,11 @@ public class TreatKeywordTest extends BaseCoreFunctionalTestCase {
assertEquals( 0, result.size() );
// in join
result = s.createQuery( "from JoinedEntity e inner join e.other" ).list();
result = s.createQuery( "from JoinedEntity e inner join e.other", JoinedEntity.class ).list();
assertEquals( 1, result.size() );
result = s.createQuery( "from JoinedEntity e inner join treat (e.other as JoinedEntitySubclass)" ).list();
result = s.createQuery( "from JoinedEntity e inner join treat (e.other as JoinedEntitySubclass)", JoinedEntity.class ).list();
assertEquals( 0, result.size() );
result = s.createQuery( "from JoinedEntity e inner join treat (e.other as JoinedEntitySubSubclass)" ).list();
result = s.createQuery( "from JoinedEntity e inner join treat (e.other as JoinedEntitySubSubclass)", JoinedEntity.class ).list();
assertEquals( 0, result.size() );
s.close();

View File

@ -62,7 +62,7 @@ public class ABCTest {
getCache( scope ).evictEntityData( D.class );
getCache( scope ).evictEntityData( A.class );
assertThat(
session.createQuery( "from D d join d.reverse r join d.inverse i where i = r" )
session.createQuery( "from D d join d.reverse r join d.inverse i where i = r", Object[].class )
.list().size(),
is( 1 )
);

View File

@ -78,7 +78,7 @@ public class LockNoneWarmingTest extends BaseCoreFunctionalTestCase {
@Test
public void testQuerySetLockModeNONEDoNotLogAWarnMessageWhenTheDialectUseFollowOnLockingIsTrue() {
try (Session s = openSession();) {
final Query query = s.createQuery( "from Item i join i.bids b where name = :name" );
final Query query = s.createQuery( "from Item i join i.bids b where name = :name", Object[].class );
query.setParameter( "name", "ZZZZ" );
query.setLockMode( "i", LockMode.NONE );
query.setLockMode( "b", LockMode.NONE );

View File

@ -43,16 +43,16 @@ public class MapIndexFormulaTest {
public void testIndexFunctionOnManyToManyMap(SessionFactoryScope scope) {
scope.inTransaction(
session -> {
session.createQuery( "from Group g join g.users u where g.name = 'something' and index(u) = 'nada'" )
session.createQuery( "from Group g join g.users u where g.name = 'something' and index(u) = 'nada'", Group.class )
.list();
session.createQuery(
"from Group g where g.name = 'something' and minindex(g.users) = 'nada'" )
"from Group g where g.name = 'something' and minindex(g.users) = 'nada'", Group.class )
.list();
session.createQuery(
"from Group g where g.name = 'something' and maxindex(g.users) = 'nada'" )
"from Group g where g.name = 'something' and maxindex(g.users) = 'nada'", Group.class )
.list();
session.createQuery(
"from Group g where g.name = 'something' and maxindex(g.users) = 'nada' and maxindex(g.users) = 'nada'" )
"from Group g where g.name = 'something' and maxindex(g.users) = 'nada' and maxindex(g.users) = 'nada'", Group.class )
.list();
}
);

View File

@ -87,7 +87,7 @@ public class MultiInheritanceImplicitDowncastTest {
public void testIllegalBaseJoin(SessionFactoryScope scope) {
try {
scope.inSession(
s -> s.createQuery( "from PolymorphicPropertyBase p left join p.base b left join b.relation1" )
s -> s.createQuery( "from PolymorphicPropertyBase p left join p.base b left join b.relation1", PolymorphicPropertyBase.class )
);
}
catch (IllegalArgumentException ex) {

View File

@ -64,7 +64,7 @@ public abstract class AbstractReadWriteTests {
scope.inTransaction(
(session) -> {
session.createQuery( "from ReadWriteEntity a, ReadWriteEntity b" ).list();
session.createQuery( "from ReadWriteEntity a, ReadWriteEntity b", Object[].class ).list();
}
);
}

View File

@ -61,7 +61,7 @@ public class DeleteOneToOneOrphansTest {
assertEquals( 1, results.size() );
Employee emp = (Employee) results.get( 0 );
assertNotNull( emp.getInfo() );
results = session.createQuery( "from Employee e, EmployeeInfo i where e.info = i" ).list();
results = session.createQuery( "from Employee e, EmployeeInfo i where e.info = i", Object[].class ).list();
assertEquals( 1, results.size() );
Object[] result = (Object[]) results.get( 0 );
emp = (Employee) result[0];

View File

@ -75,7 +75,7 @@ public class DeleteOneToManyOrphansTest {
scope.inTransaction(
session -> {
Product product = ( session.get( Product.class, p.getId() ) );
Product product = session.get( Product.class, p.getId() );
assertEquals( 0, product.getFeatures().size() );
List results = session.createQuery( "from Feature" ).list();
assertEquals( 0, results.size() );

View File

@ -177,7 +177,7 @@ public class PropertyRefTest {
}
session.clear();
l = session.createQuery( "from Person p left join p.accounts a" ).list();
l = session.createQuery( "from Person p left join p.accounts a", Person.class ).list();
for ( int i = 0; i < 2; i++ ) {
Person px = (Person) l.get( i );
assertFalse( Hibernate.isInitialized( px.getAccounts() ) );

View File

@ -16,6 +16,7 @@ import org.hibernate.testing.orm.domain.StandardDomainModel;
import org.hibernate.testing.orm.domain.retail.Product;
import org.hibernate.testing.orm.domain.retail.Vendor;
import org.hibernate.testing.orm.junit.DomainModel;
import org.hibernate.testing.orm.junit.FailureExpected;
import org.hibernate.testing.orm.junit.JiraKey;
import org.hibernate.testing.orm.junit.SessionFactory;
import org.hibernate.testing.orm.junit.SessionFactoryScope;
@ -34,10 +35,32 @@ import static org.junit.jupiter.api.Assertions.assertInstanceOf;
@JiraKey( "HHH-15133" )
public class ImplicitSelectWithJoinTests {
private static final String HQL = "from Product p join p.vendor v where v.name like '%Steve%'";
private static final String HQL0 = "from Product this join this.vendor v where v.name like '%Steve%'";
private static final String HQL2 = "select p " + HQL;
private static final String HQL3 = "from Product q join q.vendor w, Product p join p.vendor v where v.name like '%Steve%' and w.name like '%Gavin%'";
@Test
public void testNoExpectedTypeWithThis(SessionFactoryScope scope) {
scope.inTransaction( (session) -> {
final SelectionQuery<?> query = session.createSelectionQuery( HQL0 );
{
final List<?> results = query.list();
assertThat( results ).hasSize( 1 );
final Object result = results.get( 0 );
assertThat( result ).isInstanceOf( Product.class );
}
try (ScrollableResults<?> results = query.scroll()) {
assertThat( results.next() ).isTrue();
final Object result = results.get();
assertThat( result ).isInstanceOf( Product.class );
assertThat( results.next() ).isFalse();
}
} );
}
@Test @FailureExpected(reason = "this functionality was disabled, and an exception is now thrown")
public void testNoExpectedType(SessionFactoryScope scope) {
scope.inTransaction( (session) -> {
final SelectionQuery<?> query = session.createSelectionQuery( HQL );
@ -79,7 +102,7 @@ public class ImplicitSelectWithJoinTests {
} );
}
@Test
@Test @FailureExpected(reason = "this functionality was disabled, and an exception is now thrown")
public void testArrayResultNoResultType(SessionFactoryScope scope) {
scope.inTransaction( (session) -> {
final SelectionQuery<?> query = session.createSelectionQuery( HQL3 );

View File

@ -23,7 +23,7 @@ public class CrossJoinTest {
final String QRY_STRING = "from SimpleEntity e1, SimpleEntity e2 where e1.id = e2.id and e1.someDate = {ts '2018-01-01 00:00:00'}";
scope.inTransaction(
session -> {
session.createQuery( QRY_STRING ).list();
session.createQuery( QRY_STRING, Object[].class ).list();
}
);
}

View File

@ -21,7 +21,6 @@ import org.hibernate.PropertyNotFoundException;
import org.hibernate.Session;
import org.hibernate.cfg.AvailableSettings;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.internal.util.ReflectHelper;
import org.hibernate.proxy.HibernateProxy;
import org.hibernate.query.Query;
import org.hibernate.query.criteria.JpaCriteriaQuery;
@ -79,9 +78,10 @@ public abstract class AbstractQueryCacheResultTransformerTest {
@Override
protected Object getResults(Session s, boolean isSingleResult) {
Query query = getQuery( s ).setCacheable( getQueryCacheMode() != CacheMode.IGNORE ).setCacheMode(
getQueryCacheMode() );
return ( isSingleResult ? query.uniqueResult() : query.list() );
Query query = getQuery( s )
.setCacheable( getQueryCacheMode() != CacheMode.IGNORE )
.setCacheMode( getQueryCacheMode() );
return isSingleResult ? query.uniqueResult() : query.list();
}
}
@ -258,8 +258,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"from Student s left join s.enrolments e left join e.course c order by s.studentNumber" )
return s.createQuery("from Student s left join s.enrolments e left join e.course c order by s.studentNumber", Student.class )
.setResultTransformer( Transformers.ALIAS_TO_ENTITY_MAP );
}
};
@ -312,8 +311,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"from Student s left join s.preferredCourse p left join s.addresses a order by s.studentNumber" )
return s.createQuery("from Student s left join s.preferredCourse p left join s.addresses a order by s.studentNumber", Student.class )
.setResultTransformer( Transformers.ALIAS_TO_ENTITY_MAP );
}
};
@ -377,8 +375,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"from Student s left join s.addresses a left join s.preferredCourse order by s.studentNumber" )
return s.createQuery("from Student s left join s.addresses a left join s.preferredCourse order by s.studentNumber", Student.class )
.setResultTransformer( Transformers.ALIAS_TO_ENTITY_MAP );
}
};
@ -910,8 +907,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select s, pc from Student s left join fetch s.enrolments left join s.preferredCourse pc order by s.studentNumber" );
return s.createQuery("select s, pc from Student s left join fetch s.enrolments left join s.preferredCourse pc order by s.studentNumber", Object[].class );
}
};
ResultChecker checker = results -> {
@ -963,9 +959,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlSelectNewMapExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select pc, s from Student s left join fetch s.enrolments left join s.preferredCourse pc order by s.studentNumber"
);
return s.createQuery("select pc, s from Student s left join fetch s.enrolments left join s.preferredCourse pc order by s.studentNumber", Object[].class);
}
};
ResultChecker checker = results -> {
@ -1075,7 +1069,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery( "from Student s left join fetch s.enrolments e order by s.studentNumber" );
return s.createQuery( "from Student s left join fetch s.enrolments e order by s.studentNumber", Student.class );
}
};
@ -1129,14 +1123,14 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutorUnaliased = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery( "from Student s left join fetch s.addresses order by s.studentNumber" );
return s.createQuery( "from Student s left join fetch s.addresses order by s.studentNumber", Student.class );
}
};
HqlExecutor hqlExecutorAliased = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery( "from Student s left join fetch s.addresses a order by s.studentNumber" );
return s.createQuery( "from Student s left join fetch s.addresses a order by s.studentNumber", Student.class );
}
};
@ -1188,7 +1182,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutorUnaliased = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery( "from Student s left join fetch s.preferredCourse order by s.studentNumber" );
return s.createQuery( "from Student s left join fetch s.preferredCourse order by s.studentNumber", Student.class );
}
};
@ -1196,7 +1190,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"from Student s left join fetch s.preferredCourse pCourse order by s.studentNumber" );
"from Student s left join fetch s.preferredCourse pCourse order by s.studentNumber", Student.class );
}
};
@ -1363,7 +1357,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select s.name, s from Enrolment e left join e.student s left join fetch s.preferredCourse order by s.studentNumber"
"select s.name, s from Enrolment e left join e.student s left join fetch s.preferredCourse order by s.studentNumber", Object[].class
);
}
};
@ -1418,13 +1412,13 @@ public abstract class AbstractQueryCacheResultTransformerTest {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select s, s.enrolments from Student s left join s.enrolments order by s.studentNumber" );
"select s, s.enrolments from Student s left join s.enrolments order by s.studentNumber", Object[].class );
}
};
HqlExecutor hqlExecutorAliased = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery( "select s, e from Student s left join s.enrolments e order by s.studentNumber" );
return s.createQuery( "select s, e from Student s left join s.enrolments e order by s.studentNumber", Object[].class );
}
};
ResultChecker checker = results -> {
@ -1467,13 +1461,13 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutorUnaliased = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery( "from Student s left join s.addresses order by s.studentNumber" );
return s.createQuery( "from Student s left join s.addresses order by s.studentNumber", Student.class );
}
};
HqlExecutor hqlExecutorAliased = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery( "from Student s left join s.addresses a order by s.studentNumber" );
return s.createQuery( "from Student s left join s.addresses a order by s.studentNumber", Student.class );
}
};
ResultChecker checker = results -> {
@ -1524,7 +1518,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
@Override
protected Query getQuery(Session s) {
return s.createQuery(
"select s, p from Student s left join s.preferredCourse p order by s.studentNumber" );
"select s, p from Student s left join s.preferredCourse p order by s.studentNumber", Object[].class );
}
};
ResultChecker checker = results -> {
@ -1563,7 +1557,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery( "select e.student as student from Enrolment e order by e.studentNumber" )
return s.createQuery( "select e.student as student from Enrolment e order by e.studentNumber", Student.class )
.setResultTransformer( Transformers.ALIAS_TO_ENTITY_MAP );
}
};
@ -1624,7 +1618,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select e.student as student, e.semester as semester, e.year as year, e.course as course from Enrolment e order by e.studentNumber" )
"select e.student as student, e.semester as semester, e.year as year, e.course as course from Enrolment e order by e.studentNumber", Object[].class )
.setResultTransformer( Transformers.ALIAS_TO_ENTITY_MAP );
}
};
@ -1689,7 +1683,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select e.student as student, e.semester, e.year, e.course as course from Enrolment e order by e.studentNumber" )
"select e.student as student, e.semester, e.year, e.course as course from Enrolment e order by e.studentNumber", Object.class )
.setResultTransformer( Transformers.ALIAS_TO_ENTITY_MAP );
}
};
@ -1745,7 +1739,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select min( e.studentNumber ) as minStudentNumber, max( e.studentNumber ) as maxStudentNumber from Enrolment e" )
"select min( e.studentNumber ) as minStudentNumber, max( e.studentNumber ) as maxStudentNumber from Enrolment e", Object[].class )
.setResultTransformer( Transformers.ALIAS_TO_ENTITY_MAP );
}
};
@ -1996,7 +1990,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select e.student, e.semester, e.year, e.course from Enrolment e where e.studentNumber = :studentNumber" )
"select e.student, e.semester, e.year, e.course from Enrolment e where e.studentNumber = :studentNumber", Object[].class )
.setParameter( "studentNumber", shermanEnrolmentExpected.getStudentNumber() );
}
};
@ -2057,7 +2051,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select e.student, e.semester, e.year, e.course from Enrolment e order by e.studentNumber" );
"select e.student, e.semester, e.year, e.course from Enrolment e order by e.studentNumber", Object[].class );
}
};
ResultChecker checker = results -> {
@ -2123,7 +2117,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select e.student as st, e.semester as sem, e.year as yr, e.course as c from Enrolment e order by e.studentNumber" );
"select e.student as st, e.semester as sem, e.year as yr, e.course as c from Enrolment e order by e.studentNumber", Object[].class );
}
};
ResultChecker checker = results -> {
@ -2214,7 +2208,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select min( e.studentNumber ) as minStudentNumber, max( e.studentNumber ) as maxStudentNumber from Enrolment e" );
"select min( e.studentNumber ) as minStudentNumber, max( e.studentNumber ) as maxStudentNumber from Enrolment e", Object[].class );
}
};
ResultChecker checker = results -> {
@ -2257,7 +2251,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery( "select st.name as studentName from Student st order by st.studentNumber" )
return s.createQuery( "select st.name as studentName from Student st order by st.studentNumber", PersonName.class )
.setResultTransformer( Transformers.aliasToBean( StudentDTO.class ) );
}
};
@ -2315,8 +2309,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select st.name as studentName, co.description as courseDescription from Enrolment e join e.student st join e.course co order by e.studentNumber" )
return s.createQuery("select st.name as studentName, co.description as courseDescription from Enrolment e join e.student st join e.course co order by e.studentNumber", Object[].class )
.setResultTransformer( Transformers.aliasToBean( StudentDTO.class ) );
}
};
@ -2370,8 +2363,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select st.name as studentName, co.description as courseDescription from Enrolment e join e.student st join e.course co order by e.studentNumber" );
return s.createQuery("select st.name as studentName, co.description as courseDescription from Enrolment e join e.student st join e.course co order by e.studentNumber", Object[].class );
}
};
ResultChecker checker = results -> {
@ -2437,8 +2429,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select st.name as studentName, 'lame description' as courseDescription from Enrolment e join e.student st join e.course co order by e.studentNumber" )
return s.createQuery("select st.name as studentName, 'lame description' as courseDescription from Enrolment e join e.student st join e.course co order by e.studentNumber", Object[].class )
.setResultTransformer( Transformers.aliasToBean( StudentDTO.class ) );
}
};
@ -2494,8 +2485,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select st.name as studentName, co.description as courseDescription from Enrolment e join e.student st join e.course co order by e.studentNumber" )
return s.createQuery("select st.name as studentName, co.description as courseDescription from Enrolment e join e.student st join e.course co order by e.studentNumber", Object[].class )
.setResultTransformer( Transformers.aliasToBean( StudentDTO.class ) );
}
};
@ -2545,8 +2535,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select new org.hibernate.orm.test.querycache.StudentDTO(s.name) from Student s order by s.studentNumber" );
return s.createQuery("select new org.hibernate.orm.test.querycache.StudentDTO(s.name) from Student s order by s.studentNumber", StudentDTO.class );
}
};
ResultChecker checker = results -> {
@ -2596,8 +2585,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select new org.hibernate.orm.test.querycache.StudentDTO(s.name) from Student s order by s.studentNumber" );
return s.createQuery("select new org.hibernate.orm.test.querycache.StudentDTO(s.name) from Student s order by s.studentNumber", StudentDTO.class );
}
};
ResultChecker checker = results -> {
@ -2653,8 +2641,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select new Student(s.studentNumber, s.name) from Student s order by s.studentNumber" );
return s.createQuery("select new Student(s.studentNumber, s.name) from Student s order by s.studentNumber", Student.class );
}
};
ResultChecker checker = results -> {
@ -2710,7 +2697,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery( "select new Student(555L, s.name) from Student s order by s.studentNumber" );
return s.createQuery( "select new Student(555L, s.name) from Student s order by s.studentNumber", Student.class );
}
};
ResultChecker checker = results -> {
@ -2761,7 +2748,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery( "select new list(s.studentNumber, s.name) from Student s order by s.studentNumber" );
return s.createQuery( "select new list(s.studentNumber, s.name) from Student s order by s.studentNumber", List.class );
}
};
ResultChecker checker = results -> {
@ -2808,8 +2795,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select new map(s.studentNumber as sNumber, s.name as sName) from Student s order by s.studentNumber" );
return s.createQuery("select new map(s.studentNumber as sNumber, s.name as sName) from Student s order by s.studentNumber", Map.class );
}
};
ResultChecker checker = results -> {
@ -2858,8 +2844,7 @@ public abstract class AbstractQueryCacheResultTransformerTest {
HqlExecutor hqlSelectNewMapExecutor = new HqlExecutor() {
@Override
public Query getQuery(Session s) {
return s.createQuery(
"select new map(s as s, pc as pc) from Student s left join s.preferredCourse pc left join fetch s.enrolments order by s.studentNumber" );
return s.createQuery("select new map(s as s, pc as pc) from Student s left join s.preferredCourse pc left join fetch s.enrolments order by s.studentNumber", Map.class );
}
};
ResultChecker checker = results -> {

View File

@ -81,9 +81,9 @@ public class TernaryTest extends BaseCoreFunctionalTestCase {
s = openSession();
t = s.beginTransaction();
List l = s.createQuery("from Employee e join e.managerBySite m where m.name='Bob'").list();
List l = s.createQuery("from Employee e join e.managerBySite m where m.name='Bob'", Object[].class).list();
assertEquals( l.size(), 0 );
l = s.createQuery("from Employee e join e.managerBySite m where m.name='Tom'").list();
l = s.createQuery("from Employee e join e.managerBySite m where m.name='Tom'", Object[].class).list();
assertEquals( l.size(), 2 );
t.commit();
s.close();
@ -103,7 +103,7 @@ public class TernaryTest extends BaseCoreFunctionalTestCase {
}
assertTrue(total==3);
l = s.createQuery("from Employee e left join e.managerBySite m left join m.managerBySite m2").list();
l = s.createQuery("from Employee e left join e.managerBySite m left join m.managerBySite m2", Object[].class).list();
// clean up...
l = s.createQuery("from Employee e left join fetch e.managerBySite").list();
@ -124,7 +124,7 @@ public class TernaryTest extends BaseCoreFunctionalTestCase {
public void testIndexRelatedFunctions() {
Session session = openSession();
session.beginTransaction();
session.createQuery( "from Employee e join e.managerBySite as m where index(m) is not null" )
session.createQuery( "from Employee e join e.managerBySite as m where index(m) is not null", Object[].class )
.list();
session.createQuery( "from Employee e where minIndex(e.managerBySite) is not null" )
.list();