Skip to content

Commit 052c057

Browse files
DATAMONGO-1603 - Fix Placeholder not replaced correctly in @query.
Additional tests and fixes for complex quoted replacements eg. in regex query.
1 parent 807ec47 commit 052c057

File tree

2 files changed

+22
-6
lines changed

2 files changed

+22
-6
lines changed

spring-data-mongodb/src/main/java/org/springframework/data/mongodb/repository/query/ExpressionEvaluatingParameterBinder.java

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -247,7 +247,8 @@ private Pattern createReplacementPattern(List<ParameterBinding> bindings) {
247247

248248
regex.append("|");
249249
regex.append("(" + Pattern.quote(binding.getParameter()) + ")");
250-
regex.append("(\\W?['\"]|\\w*')?");
250+
regex.append("([\\w.]*");
251+
regex.append("(\\W?['\"]|\\w*')?)");
251252
}
252253

253254
return Pattern.compile(regex.substring(1));
@@ -265,18 +266,18 @@ private Placeholder extractPlaceholder(int parameterIndex, Matcher matcher) {
265266

266267
if (matcher.groupCount() > 1) {
267268

268-
String rawPlaceholder = matcher.group(parameterIndex * 2 + 1);
269-
String suffix = matcher.group(parameterIndex * 2 + 2);
269+
String rawPlaceholder = matcher.group(parameterIndex * 3 + 1);
270+
String suffix = matcher.group(parameterIndex * 3 + 2);
270271

271272
if (!StringUtils.hasText(rawPlaceholder)) {
272273

273274
rawPlaceholder = matcher.group();
274275
if(rawPlaceholder.matches(".*\\d$")) {
275276
suffix = "";
276277
} else {
277-
int index = rawPlaceholder.replaceAll("[^\\?a-zA-Z0-9]*$", "").length() - 1;
278-
if(index > 1) {
279-
suffix = rawPlaceholder.substring(index);
278+
int index = rawPlaceholder.replaceAll("[^\\?0-9]*$", "").length() - 1;
279+
if (index > 0 && rawPlaceholder.length() > index) {
280+
suffix = rawPlaceholder.substring(index+1);
280281
}
281282
}
282283
if (QuotedString.endsWithQuote(rawPlaceholder)) {

spring-data-mongodb/src/test/java/org/springframework/data/mongodb/repository/query/StringBasedMongoQueryUnitTests.java

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -485,6 +485,18 @@ public void shouldAllowQuotedParameterWithSuffixAppended() throws Exception {
485485
is((DBObject) new BasicDBObject().append("arg0", "calamity").append("arg1", "regalias")));
486486
}
487487

488+
@Test // DATAMONGO-1603
489+
public void shouldCaptureReplacementWithComplexSuffixCorrectly() throws Exception {
490+
491+
StringBasedMongoQuery mongoQuery = createQueryForMethod("findByMultiRegex", String.class);
492+
ConvertingParameterAccessor accessor = StubParameterAccessor.getAccessor(converter, "calamity");
493+
494+
org.springframework.data.mongodb.core.query.Query query = mongoQuery.createQuery(accessor);
495+
496+
assertThat(query.getQueryObject(), is((DBObject) JSON.parse(
497+
"{ \"$or\" : [ { \"firstname\" : { \"$regex\" : \".*calamity.*\" , \"$options\" : \"i\"}} , { \"lastname\" : { \"$regex\" : \".*calamityxyz.*\" , \"$options\" : \"i\"}}]}")));
498+
}
499+
488500
private StringBasedMongoQuery createQueryForMethod(String name, Class<?>... parameters) throws Exception {
489501

490502
Method method = SampleRepository.class.getMethod(name, parameters);
@@ -508,6 +520,9 @@ private interface SampleRepository extends Repository<Person, Long> {
508520
@Query("{ 'lastname' : { '$regex' : '^(?0)'} }")
509521
Person findByLastnameRegex(String lastname);
510522

523+
@Query("{'$or' : [{'firstname': {'$regex': '.*?0.*', '$options': 'i'}}, {'lastname' : {'$regex': '.*?0xyz.*', '$options': 'i'}} ]}")
524+
Person findByMultiRegex(String arg0);
525+
511526
@Query("{ 'address' : ?0 }")
512527
Person findByAddress(Address address);
513528

0 commit comments

Comments
 (0)