Skip to content

Commit 021fab0

Browse files
committed
HHH-18497 Make reserved word identification for JPA compliance more robust
1 parent 2203e12 commit 021fab0

File tree

1 file changed

+103
-4
lines changed

1 file changed

+103
-4
lines changed

hibernate-core/src/main/java/org/hibernate/query/hql/internal/SqmTreeCreationHelper.java

Lines changed: 103 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
package org.hibernate.query.hql.internal;
66

77
import java.util.Locale;
8+
import java.util.Set;
89

910
import org.hibernate.grammars.hql.HqlParser;
1011
import org.hibernate.jpa.spi.JpaCompliance;
@@ -19,15 +20,113 @@
1920
import org.antlr.v4.runtime.Token;
2021
import org.antlr.v4.runtime.tree.ParseTree;
2122

22-
import static org.hibernate.grammars.hql.HqlParser.IDENTIFIER;
23-
2423
/**
2524
* Helper for dealing with SQM tree creation
2625
*
2726
* @author Steve Ebersole
2827
*/
2928
public class SqmTreeCreationHelper {
3029

30+
// The list is from the spec section 4.4.1
31+
private static final Set<String> RESERVED_WORDS = Set.of(
32+
"abs",
33+
"all",
34+
"and",
35+
"any",
36+
"as",
37+
"asc",
38+
"avg",
39+
"between",
40+
"bit_length",
41+
"both",
42+
"by",
43+
"case",
44+
"ceiling",
45+
"char_length",
46+
"character_length",
47+
"class",
48+
"coalesce",
49+
"concat",
50+
"count",
51+
"current_date",
52+
"current_time",
53+
"current_timestamp",
54+
"delete",
55+
"desc",
56+
"distinct",
57+
"else",
58+
"empty",
59+
"end",
60+
"entry",
61+
"escape",
62+
"exists",
63+
"exp",
64+
"extract",
65+
"false",
66+
"fetch",
67+
"first",
68+
"floor",
69+
"from",
70+
"function",
71+
"group",
72+
"having",
73+
"in",
74+
"index",
75+
"inner",
76+
"is",
77+
"join",
78+
"key",
79+
"leading",
80+
"last",
81+
"left",
82+
"length",
83+
"like",
84+
"local",
85+
"ln",
86+
"locate",
87+
"lower",
88+
"max",
89+
"member",
90+
"min",
91+
"mod",
92+
"new",
93+
"not",
94+
"null",
95+
"nulls",
96+
"nullif",
97+
"object",
98+
"of",
99+
"on",
100+
"or",
101+
"order",
102+
"outer",
103+
"position",
104+
"power",
105+
"replace",
106+
"right",
107+
"round",
108+
"select",
109+
"set",
110+
"sign",
111+
"size",
112+
"some",
113+
"sqrt",
114+
"substring",
115+
"sum",
116+
"then",
117+
"trailing",
118+
"treat",
119+
"trim",
120+
"true",
121+
"type",
122+
"unknown",
123+
"update",
124+
"upper",
125+
"value",
126+
"when",
127+
"where"
128+
);
129+
31130
/**
32131
* Handle secondary query roots using cross-join semantics.
33132
*
@@ -108,7 +207,7 @@ public static String extractVariable(HqlParser.VariableContext ctx, SemanticQuer
108207
// which JPA disallows...
109208
if ( sqmBuilder.getCreationOptions().useStrictJpaCompliance() ) {
110209
final Token identificationVariableToken = identifierContext.getStart();
111-
if ( identificationVariableToken.getType() != IDENTIFIER ) {
210+
if ( RESERVED_WORDS.contains( identificationVariableToken.getText().toLowerCase( Locale.ENGLISH ) ) ) {
112211
throw new StrictJpaComplianceViolation(
113212
String.format(
114213
Locale.ROOT,
@@ -128,7 +227,7 @@ public static String extractVariable(HqlParser.VariableContext ctx, SemanticQuer
128227
// which JPA disallows...
129228
if ( sqmBuilder.getCreationOptions().useStrictJpaCompliance() ) {
130229
final Token identificationVariableToken = identifierContext.getStart();
131-
if ( identificationVariableToken.getType() != IDENTIFIER ) {
230+
if ( RESERVED_WORDS.contains( identificationVariableToken.getText().toLowerCase( Locale.ENGLISH ) ) ) {
132231
throw new StrictJpaComplianceViolation(
133232
String.format(
134233
Locale.ROOT,

0 commit comments

Comments
 (0)