HHH-17375 Support array on RHS of in predicate
This commit is contained in:
parent
5c6a2f4a7d
commit
dcedc5cf18
|
@ -1420,6 +1420,24 @@ include::{array-example-dir-hql}/ArrayContainsArrayTest.java[tags=hql-array-cont
|
||||||
----
|
----
|
||||||
====
|
====
|
||||||
|
|
||||||
|
In addition to that, it is also possible to use the `in` predicate with arrays.
|
||||||
|
|
||||||
|
[[hql-array-in-hql-example]]
|
||||||
|
====
|
||||||
|
[source, JAVA, indent=0]
|
||||||
|
----
|
||||||
|
include::{array-example-dir-hql}/ArrayContainsTest.java[tags=hql-array-in-hql-example]
|
||||||
|
----
|
||||||
|
====
|
||||||
|
|
||||||
|
[[hql-array-in-array-hql-example]]
|
||||||
|
====
|
||||||
|
[source, JAVA, indent=0]
|
||||||
|
----
|
||||||
|
include::{array-example-dir-hql}/ArrayContainsArrayTest.java[tags=hql-array-in-array-hql-example]
|
||||||
|
----
|
||||||
|
====
|
||||||
|
|
||||||
[[hql-array-overlaps-functions]]
|
[[hql-array-overlaps-functions]]
|
||||||
[[hql-array-intersects-functions]]
|
[[hql-array-intersects-functions]]
|
||||||
===== `array_intersects()` and `array_intersects_nullable()`
|
===== `array_intersects()` and `array_intersects_nullable()`
|
||||||
|
|
|
@ -706,6 +706,7 @@ inList
|
||||||
| LEFT_PAREN (expressionOrPredicate (COMMA expressionOrPredicate)*)? RIGHT_PAREN# ExplicitTupleInList
|
| LEFT_PAREN (expressionOrPredicate (COMMA expressionOrPredicate)*)? RIGHT_PAREN# ExplicitTupleInList
|
||||||
| LEFT_PAREN subquery RIGHT_PAREN # SubqueryInList
|
| LEFT_PAREN subquery RIGHT_PAREN # SubqueryInList
|
||||||
| parameter # ParamInList
|
| parameter # ParamInList
|
||||||
|
| expression # ArrayInList
|
||||||
;
|
;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -2846,6 +2846,28 @@ public class SemanticQueryBuilder<R> extends HqlParserBaseVisitor<Object> implem
|
||||||
creationContext.getNodeBuilder()
|
creationContext.getNodeBuilder()
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
else if ( inListContext instanceof HqlParser.ArrayInListContext ) {
|
||||||
|
if ( getCreationOptions().useStrictJpaCompliance() ) {
|
||||||
|
throw new StrictJpaComplianceViolation( StrictJpaComplianceViolation.Type.HQL_COLLECTION_FUNCTION );
|
||||||
|
}
|
||||||
|
final HqlParser.ArrayInListContext arrayInListContext =
|
||||||
|
(HqlParser.ArrayInListContext) inListContext;
|
||||||
|
|
||||||
|
final SqmExpression<?> arrayExpr = (SqmExpression<?>) arrayInListContext.expression().accept( this );
|
||||||
|
final SqmExpressible<?> arrayExpressible = arrayExpr.getExpressible();
|
||||||
|
if ( arrayExpressible != null && !( arrayExpressible.getSqmType() instanceof BasicPluralType<?, ?>) ) {
|
||||||
|
throw new SemanticException(
|
||||||
|
"Right operand for in-array predicate must be a basic plural type expression, but found: " + arrayExpressible.getSqmType(),
|
||||||
|
query
|
||||||
|
);
|
||||||
|
}
|
||||||
|
final SelfRenderingSqmFunction<Boolean> contains = getFunctionDescriptor( "array_contains" ).generateSqmExpression(
|
||||||
|
asList( arrayExpr, testExpression ),
|
||||||
|
null,
|
||||||
|
creationContext.getQueryEngine()
|
||||||
|
);
|
||||||
|
return new SqmBooleanExpressionPredicate( contains, negated, creationContext.getNodeBuilder() );
|
||||||
|
}
|
||||||
else {
|
else {
|
||||||
throw new ParsingException( "Unexpected IN predicate type [" + ctx.getClass().getSimpleName() + "] : " + ctx.getText() );
|
throw new ParsingException( "Unexpected IN predicate type [" + ctx.getClass().getSimpleName() + "] : " + ctx.getText() );
|
||||||
}
|
}
|
||||||
|
|
|
@ -211,4 +211,16 @@ public class ArrayContainsArrayTest {
|
||||||
} );
|
} );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testInArraySyntax(SessionFactoryScope scope) {
|
||||||
|
scope.inSession( em -> {
|
||||||
|
//tag::hql-array-in-array-hql-example[]
|
||||||
|
List<EntityWithArrays> results = em.createQuery( "from EntityWithArrays e where ['abc', 'def'] in e.theArray", EntityWithArrays.class )
|
||||||
|
.getResultList();
|
||||||
|
//end::hql-array-in-array-hql-example[]
|
||||||
|
assertEquals( 1, results.size() );
|
||||||
|
assertEquals( 2L, results.get( 0 ).getId() );
|
||||||
|
} );
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -145,4 +145,16 @@ public class ArrayContainsTest {
|
||||||
} );
|
} );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testInSyntax(SessionFactoryScope scope) {
|
||||||
|
scope.inSession( em -> {
|
||||||
|
//tag::hql-array-in-hql-example[]
|
||||||
|
List<EntityWithArrays> results = em.createQuery( "from EntityWithArrays e where 'abc' in e.theArray", EntityWithArrays.class )
|
||||||
|
.getResultList();
|
||||||
|
//end::hql-array-in-hql-example[]
|
||||||
|
assertEquals( 1, results.size() );
|
||||||
|
assertEquals( 2L, results.get( 0 ).getId() );
|
||||||
|
} );
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -128,7 +128,7 @@ Plenty of syntax sugar for array operations was added:
|
||||||
|Support casting array to string
|
|Support casting array to string
|
||||||
|
|
||||||
|`array_contains(array, element)`
|
|`array_contains(array, element)`
|
||||||
|`array contains element`
|
|`array contains element` or `element in array`
|
||||||
|Contains predicate for containment check
|
|Contains predicate for containment check
|
||||||
|
|
||||||
|`array_intersects(array, array(1, 2))`
|
|`array_intersects(array, array(1, 2))`
|
||||||
|
|
Loading…
Reference in New Issue