Skip to content

Commit 4f55b7a

Browse files
committed
Fix entity name expansion templated native queries.
ExpressionBasedStringQuery now correctly expands the entityName placeholder again. Closes #3979
1 parent f487d0e commit 4f55b7a

File tree

4 files changed

+20
-24
lines changed

4 files changed

+20
-24
lines changed

spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/query/AbstractStringBasedJpaQuery.java

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -80,15 +80,12 @@ public AbstractStringBasedJpaQuery(JpaQueryMethod method, EntityManager em, Stri
8080

8181
this.valueExpressionDelegate = valueExpressionDelegate;
8282
this.valueExpressionContextProvider = valueExpressionDelegate.createValueContextProvider(method.getParameters());
83-
this.query = new ExpressionBasedStringQuery(queryString, method.getEntityInformation(), valueExpressionDelegate,
84-
method.isNativeQuery());
83+
this.query = new ExpressionBasedStringQuery(queryString, method, valueExpressionDelegate);
8584

8685
this.countQuery = Lazy.of(() -> {
8786

8887
if (StringUtils.hasText(countQueryString)) {
89-
90-
return new ExpressionBasedStringQuery(countQueryString, method.getEntityInformation(), valueExpressionDelegate,
91-
method.isNativeQuery());
88+
return new ExpressionBasedStringQuery(countQueryString, method, valueExpressionDelegate);
9289
}
9390

9491
return query.deriveCountQuery(method.getCountQueryProjection());

spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/query/ExpressionBasedStringQuery.java

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,17 @@ class ExpressionBasedStringQuery extends StringQuery {
5252
private static final String ENTITY_NAME_VARIABLE = "#" + ENTITY_NAME;
5353
private static final String ENTITY_NAME_VARIABLE_EXPRESSION = "#{" + ENTITY_NAME_VARIABLE;
5454

55+
/**
56+
* Creates a new {@link ExpressionBasedStringQuery} for the given query and {@link JpaQueryMethod}.
57+
*
58+
* @param query must not be {@literal null} or empty.
59+
* @param queryMethod must not be {@literal null} or empty.
60+
* @param parser must not be {@literal null}.
61+
*/
62+
public ExpressionBasedStringQuery(String query, JpaQueryMethod queryMethod, ValueExpressionParser parser) {
63+
this(query, queryMethod.getEntityInformation(), parser, queryMethod.isNativeQuery());
64+
}
65+
5566
/**
5667
* Creates a new {@link ExpressionBasedStringQuery} for the given query and {@link EntityMetadata}.
5768
*
@@ -62,7 +73,7 @@ class ExpressionBasedStringQuery extends StringQuery {
6273
*/
6374
public ExpressionBasedStringQuery(String query, JpaEntityMetadata<?> metadata, ValueExpressionParser parser,
6475
boolean nativeQuery) {
65-
super(renderQueryIfExpressionOrReturnQuery(query, metadata, parser), nativeQuery && !containsExpression(query));
76+
super(renderQueryIfExpressionOrReturnQuery(query, metadata, parser), nativeQuery);
6677
}
6778

6879
/**

spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/query/ExpressionBasedStringQueryUnitTests.java

Lines changed: 5 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -97,25 +97,13 @@ void shouldDetectBindParameterCountCorrectlyWithJDBCStyleParameters() {
9797
assertThat(query.getParameterBindings()).hasSize(8);
9898
}
9999

100-
@Test
101-
void shouldDetectComplexNativeQueriesWithSpelAsNonNative() {
102-
103-
StringQuery query = new ExpressionBasedStringQuery(
104-
"select n from #{#entityName} n where (LOWER(n.name) LIKE LOWER(NULLIF(text(concat('%',?#{#networkRequest.name},'%')), '')) OR ?#{#networkRequest.name} IS NULL )"
105-
+ "AND (LOWER(n.server) LIKE LOWER(NULLIF(text(concat('%',?#{#networkRequest.server},'%')), '')) OR ?#{#networkRequest.server} IS NULL)"
106-
+ "AND (n.createdAt >= ?#{#networkRequest.createdTime.startDateTime}) AND (n.createdAt <=?#{#networkRequest.createdTime.endDateTime})"
107-
+ "AND (n.updatedAt >= ?#{#networkRequest.updatedTime.startDateTime}) AND (n.updatedAt <=?#{#networkRequest.updatedTime.endDateTime})",
108-
metadata, PARSER, true);
109-
110-
assertThat(query.isNativeQuery()).isFalse();
111-
}
100+
@Test // GH-3979
101+
void shouldExpandExpressionUsingNativeQueries() {
112102

113-
@Test
114-
void shouldDetectSimpleNativeQueriesWithSpelAsNonNative() {
115-
116-
StringQuery query = new ExpressionBasedStringQuery("select n from #{#entityName} n", metadata, PARSER, true);
103+
StringQuery query = new ExpressionBasedStringQuery("select n.* from #{#entityName} n", metadata, PARSER, true);
117104

118-
assertThat(query.isNativeQuery()).isFalse();
105+
assertThat(query.isNativeQuery()).isTrue();
106+
assertThat(query.getQueryString()).isEqualTo("select n.* from User n");
119107
}
120108

121109
@Test

spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/sample/UserRepository.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -607,7 +607,7 @@ Page<User> findAllOrderedBySpecialNameMultipleParams(@Param("name") String name,
607607
Map<String, Object> findMapWithNullValues();
608608

609609
// DATAJPA-1307
610-
@Query(value = "select * from SD_User u where u.emailAddress = ?", nativeQuery = true)
610+
@Query(value = "select * from SD_#{#entityName} u where u.emailAddress = ?", nativeQuery = true)
611611
User findByEmailNativeAddressJdbcStyleParameter(String emailAddress);
612612

613613
// DATAJPA-1334

0 commit comments

Comments
 (0)