DATAMONGO-1854 - Polishing.

Use ParameterBindingDocumentCodec to parse collation expressions.

Original pull request: #644.
This commit is contained in:
Mark Paluch
2019-02-20 14:27:10 +01:00
parent b8368a677d
commit 8b7071e6ae
17 changed files with 117 additions and 33 deletions

View File

@@ -119,7 +119,7 @@ public class Collation {
}
/**
* Parse the given collation string into a {@link Collation}.
* Parse the given {@code collation} string into a {@link Collation}.
*
* @param collation the collation to parse. Can be a simple string like {@code en_US} or a
* {@link Document#parse(String) parsable} document like <code>&#123; 'locale' : '?0' &#125;</code> .

View File

@@ -97,11 +97,9 @@ public @interface Query {
String sort() default "";
/**
* Defines the collation to apply when executing the query. <br />
*
* <pre>
* <code>
* Defines the collation to apply when executing the query.
*
* <pre class="code">
* // Fixed value
* &#64;Query(collation = "en_US")
* List<Entry> findAllByFixedCollation();
@@ -121,7 +119,6 @@ public @interface Query {
* // SpEL expression
* &#64;Query(collation = "?#{[0]}")
* List<Entry> findAllByDynamicSpElCollation(String collation);
* </code>
* </pre>
*
* @since 2.2

View File

@@ -16,6 +16,7 @@
package org.springframework.data.mongodb.repository.query;
import org.bson.Document;
import org.springframework.data.mongodb.core.ExecutableFindOperation.ExecutableFind;
import org.springframework.data.mongodb.core.ExecutableFindOperation.FindWithQuery;
import org.springframework.data.mongodb.core.ExecutableFindOperation.TerminatingFind;
@@ -27,8 +28,10 @@ import org.springframework.data.mongodb.repository.query.MongoQueryExecution.Pag
import org.springframework.data.mongodb.repository.query.MongoQueryExecution.PagingGeoNearExecution;
import org.springframework.data.mongodb.repository.query.MongoQueryExecution.SlicedExecution;
import org.springframework.data.repository.query.ParameterAccessor;
import org.springframework.data.repository.query.QueryMethodEvaluationContextProvider;
import org.springframework.data.repository.query.RepositoryQuery;
import org.springframework.data.repository.query.ResultProcessor;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.util.Assert;
/**
@@ -44,17 +47,24 @@ public abstract class AbstractMongoQuery implements RepositoryQuery {
private final MongoQueryMethod method;
private final MongoOperations operations;
private final ExecutableFind<?> executableFind;
private final SpelExpressionParser expressionParser;
private final QueryMethodEvaluationContextProvider evaluationContextProvider;
/**
* Creates a new {@link AbstractMongoQuery} from the given {@link MongoQueryMethod} and {@link MongoOperations}.
*
* @param method must not be {@literal null}.
* @param operations must not be {@literal null}.
* @param expressionParser must not be {@literal null}.
* @param evaluationContextProvider must not be {@literal null}.
*/
public AbstractMongoQuery(MongoQueryMethod method, MongoOperations operations) {
public AbstractMongoQuery(MongoQueryMethod method, MongoOperations operations, SpelExpressionParser expressionParser,
QueryMethodEvaluationContextProvider evaluationContextProvider) {
Assert.notNull(operations, "MongoOperations must not be null!");
Assert.notNull(method, "MongoQueryMethod must not be null!");
Assert.notNull(expressionParser, "SpelExpressionParser must not be null!");
Assert.notNull(evaluationContextProvider, "QueryMethodEvaluationContextProvider must not be null!");
this.method = method;
this.operations = operations;
@@ -63,6 +73,8 @@ public abstract class AbstractMongoQuery implements RepositoryQuery {
Class<?> type = metadata.getCollectionEntity().getType();
this.executableFind = operations.query(type);
this.expressionParser = expressionParser;
this.evaluationContextProvider = evaluationContextProvider;
}
/*
@@ -167,7 +179,7 @@ public abstract class AbstractMongoQuery implements RepositoryQuery {
Query applyAnnotatedCollationIfPresent(Query query, ConvertingParameterAccessor accessor) {
return QueryUtils.applyCollation(query, method.hasAnnotatedCollation() ? method.getAnnotatedCollation() : null,
accessor);
accessor, getQueryMethod().getParameters(), expressionParser, evaluationContextProvider);
}
/**

View File

@@ -20,6 +20,7 @@ import reactor.core.publisher.Mono;
import org.bson.Document;
import org.reactivestreams.Publisher;
import org.springframework.core.convert.converter.Converter;
import org.springframework.data.convert.EntityInstantiators;
import org.springframework.data.mongodb.core.MongoOperations;
@@ -33,8 +34,10 @@ import org.springframework.data.mongodb.repository.query.ReactiveMongoQueryExecu
import org.springframework.data.mongodb.repository.query.ReactiveMongoQueryExecution.ResultProcessingConverter;
import org.springframework.data.mongodb.repository.query.ReactiveMongoQueryExecution.ResultProcessingExecution;
import org.springframework.data.repository.query.ParameterAccessor;
import org.springframework.data.repository.query.QueryMethodEvaluationContextProvider;
import org.springframework.data.repository.query.RepositoryQuery;
import org.springframework.data.repository.query.ResultProcessor;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.util.Assert;
/**
@@ -50,6 +53,8 @@ public abstract class AbstractReactiveMongoQuery implements RepositoryQuery {
private final ReactiveMongoOperations operations;
private final EntityInstantiators instantiators;
private final FindWithProjection<?> findOperationWithProjection;
private final SpelExpressionParser expressionParser;
private final QueryMethodEvaluationContextProvider evaluationContextProvider;
/**
* Creates a new {@link AbstractReactiveMongoQuery} from the given {@link MongoQueryMethod} and
@@ -57,15 +62,22 @@ public abstract class AbstractReactiveMongoQuery implements RepositoryQuery {
*
* @param method must not be {@literal null}.
* @param operations must not be {@literal null}.
* @param expressionParser must not be {@literal null}.
* @param evaluationContextProvider must not be {@literal null}.
*/
public AbstractReactiveMongoQuery(ReactiveMongoQueryMethod method, ReactiveMongoOperations operations) {
public AbstractReactiveMongoQuery(ReactiveMongoQueryMethod method, ReactiveMongoOperations operations,
SpelExpressionParser expressionParser, QueryMethodEvaluationContextProvider evaluationContextProvider) {
Assert.notNull(method, "MongoQueryMethod must not be null!");
Assert.notNull(operations, "ReactiveMongoOperations must not be null!");
Assert.notNull(expressionParser, "SpelExpressionParser must not be null!");
Assert.notNull(evaluationContextProvider, "QueryMethodEvaluationContextProvider must not be null!");
this.method = method;
this.operations = operations;
this.instantiators = new EntityInstantiators();
this.expressionParser = expressionParser;
this.evaluationContextProvider = evaluationContextProvider;
MongoEntityMetadata<?> metadata = method.getEntityInformation();
Class<?> type = metadata.getCollectionEntity().getType();
@@ -105,7 +117,8 @@ public abstract class AbstractReactiveMongoQuery implements RepositoryQuery {
private Object execute(MongoParameterAccessor parameterAccessor) {
ConvertingParameterAccessor convertingParamterAccessor = new ConvertingParameterAccessor(operations.getConverter(), parameterAccessor);
ConvertingParameterAccessor convertingParamterAccessor = new ConvertingParameterAccessor(operations.getConverter(),
parameterAccessor);
Query query = createQuery(convertingParamterAccessor);
applyQueryMetaAttributesWhenPresent(query);
@@ -209,7 +222,7 @@ public abstract class AbstractReactiveMongoQuery implements RepositoryQuery {
Query applyAnnotatedCollationIfPresent(Query query, ConvertingParameterAccessor accessor) {
return QueryUtils.applyCollation(query, method.hasAnnotatedCollation() ? method.getAnnotatedCollation() : null,
accessor);
accessor, getQueryMethod().getParameters(), expressionParser, evaluationContextProvider);
}
/**

View File

@@ -335,7 +335,7 @@ public class MongoQueryMethod extends QueryMethod {
/**
* Get the collation value extracted from the {@link Query} annotation.
*
* @return the {@link Query#sort()} value.
* @return the {@link Query#collation()} value.
* @throws IllegalStateException if method not annotated with {@link Query}. Make sure to check
* {@link #hasAnnotatedQuery()} first.
* @since 2.2

View File

@@ -17,6 +17,7 @@ package org.springframework.data.mongodb.repository.query;
import org.bson.Document;
import org.bson.json.JsonParseException;
import org.springframework.data.mapping.context.MappingContext;
import org.springframework.data.mongodb.core.MongoOperations;
import org.springframework.data.mongodb.core.MongoTemplate;
@@ -26,10 +27,12 @@ import org.springframework.data.mongodb.core.query.Field;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.core.query.TextCriteria;
import org.springframework.data.repository.query.QueryMethod;
import org.springframework.data.repository.query.QueryMethodEvaluationContextProvider;
import org.springframework.data.repository.query.RepositoryQuery;
import org.springframework.data.repository.query.ResultProcessor;
import org.springframework.data.repository.query.ReturnedType;
import org.springframework.data.repository.query.parser.PartTree;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.util.StringUtils;
/**
@@ -52,10 +55,13 @@ public class PartTreeMongoQuery extends AbstractMongoQuery {
*
* @param method must not be {@literal null}.
* @param mongoOperations must not be {@literal null}.
* @param expressionParser must not be {@literal null}.
* @param evaluationContextProvider must not be {@literal null}.
*/
public PartTreeMongoQuery(MongoQueryMethod method, MongoOperations mongoOperations) {
public PartTreeMongoQuery(MongoQueryMethod method, MongoOperations mongoOperations,
SpelExpressionParser expressionParser, QueryMethodEvaluationContextProvider evaluationContextProvider) {
super(method, mongoOperations);
super(method, mongoOperations, expressionParser, evaluationContextProvider);
this.processor = method.getResultProcessor();
this.tree = new PartTree(method.getName(), processor.getReturnedType().getDomainType());

View File

@@ -21,23 +21,32 @@ import java.util.regex.Pattern;
import org.aopalliance.intercept.MethodInterceptor;
import org.bson.Document;
import org.springframework.aop.framework.ProxyFactory;
import org.springframework.data.mongodb.core.query.Collation;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.util.json.ParameterBindingContext;
import org.springframework.data.mongodb.util.json.ParameterBindingDocumentCodec;
import org.springframework.data.repository.query.QueryMethodEvaluationContextProvider;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.lang.Nullable;
import org.springframework.util.NumberUtils;
import org.springframework.util.ObjectUtils;
import org.springframework.util.StringUtils;
/**
* Internal utility class to help avoid duplicate code required in both the reactive and the sync {@link Query} support
* offered by repositories.
*
* @author Christoph Strobl
* @author Mark Paluch
* @since 2.1
* @currentRead Assassin's Apprentice - Robin Hobb
*/
class QueryUtils {
private static final ParameterBindingDocumentCodec CODEC = new ParameterBindingDocumentCodec();
private static final Pattern PARAMETER_BINDING_PATTERN = Pattern.compile("\\?(\\d+)");
/**
@@ -80,7 +89,9 @@ class QueryUtils {
* @see Query#collation(Collation)
* @since 2.2
*/
static Query applyCollation(Query query, @Nullable String collationExpression, ConvertingParameterAccessor accessor) {
static Query applyCollation(Query query, @Nullable String collationExpression, ConvertingParameterAccessor accessor,
MongoParameters parameters, SpelExpressionParser expressionParser,
QueryMethodEvaluationContextProvider evaluationContextProvider) {
if (accessor.getCollation() != null) {
return query.collation(accessor.getCollation());
@@ -90,10 +101,15 @@ class QueryUtils {
return query;
}
if (StringUtils.trimLeadingWhitespace(collationExpression).startsWith("{")) {
ParameterBindingContext bindingContext = new ParameterBindingContext((accessor::getBindableValue),
expressionParser, evaluationContextProvider.getEvaluationContext(parameters, accessor.getValues()));
return query.collation(Collation.from(CODEC.decode(collationExpression, bindingContext)));
}
Matcher matcher = PARAMETER_BINDING_PATTERN.matcher(collationExpression);
// TODO: use parameter binding Parser instead of Document.parse once DATAMONGO-2199 is merged.
if (!matcher.find()) {
return query.collation(Collation.parse(collationExpression));
}

View File

@@ -17,6 +17,7 @@ package org.springframework.data.mongodb.repository.query;
import org.bson.Document;
import org.bson.json.JsonParseException;
import org.springframework.data.mapping.context.MappingContext;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.ReactiveMongoOperations;
@@ -25,10 +26,12 @@ import org.springframework.data.mongodb.core.query.BasicQuery;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.core.query.TextCriteria;
import org.springframework.data.repository.query.QueryMethod;
import org.springframework.data.repository.query.QueryMethodEvaluationContextProvider;
import org.springframework.data.repository.query.RepositoryQuery;
import org.springframework.data.repository.query.ResultProcessor;
import org.springframework.data.repository.query.ReturnedType;
import org.springframework.data.repository.query.parser.PartTree;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.util.StringUtils;
/**
@@ -50,10 +53,13 @@ public class ReactivePartTreeMongoQuery extends AbstractReactiveMongoQuery {
*
* @param method must not be {@literal null}.
* @param mongoOperations must not be {@literal null}.
* @param expressionParser must not be {@literal null}.
* @param evaluationContextProvider must not be {@literal null}.
*/
public ReactivePartTreeMongoQuery(ReactiveMongoQueryMethod method, ReactiveMongoOperations mongoOperations) {
public ReactivePartTreeMongoQuery(ReactiveMongoQueryMethod method, ReactiveMongoOperations mongoOperations,
SpelExpressionParser expressionParser, QueryMethodEvaluationContextProvider evaluationContextProvider) {
super(method, mongoOperations);
super(method, mongoOperations, expressionParser, evaluationContextProvider);
this.processor = method.getResultProcessor();
this.tree = new PartTree(method.getName(), processor.getReturnedType().getDomainType());

View File

@@ -18,6 +18,7 @@ package org.springframework.data.mongodb.repository.query;
import org.bson.Document;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.data.mongodb.core.MongoOperations;
import org.springframework.data.mongodb.core.ReactiveMongoOperations;
import org.springframework.data.mongodb.core.query.BasicQuery;
@@ -78,7 +79,7 @@ public class ReactiveStringBasedMongoQuery extends AbstractReactiveMongoQuery {
ReactiveMongoOperations mongoOperations, SpelExpressionParser expressionParser,
QueryMethodEvaluationContextProvider evaluationContextProvider) {
super(method, mongoOperations);
super(method, mongoOperations, expressionParser, evaluationContextProvider);
Assert.notNull(query, "Query must not be null!");
Assert.notNull(expressionParser, "SpelExpressionParser must not be null!");

View File

@@ -18,6 +18,7 @@ package org.springframework.data.mongodb.repository.query;
import org.bson.Document;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.data.mongodb.core.MongoOperations;
import org.springframework.data.mongodb.core.query.BasicQuery;
import org.springframework.data.mongodb.core.query.Query;
@@ -77,7 +78,7 @@ public class StringBasedMongoQuery extends AbstractMongoQuery {
public StringBasedMongoQuery(String query, MongoQueryMethod method, MongoOperations mongoOperations,
SpelExpressionParser expressionParser, QueryMethodEvaluationContextProvider evaluationContextProvider) {
super(method, mongoOperations);
super(method, mongoOperations, expressionParser, evaluationContextProvider);
Assert.notNull(query, "Query must not be null!");
Assert.notNull(expressionParser, "SpelExpressionParser must not be null!");

View File

@@ -21,6 +21,7 @@ import java.util.Set;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.data.domain.Sort;
import org.springframework.data.domain.Sort.Direction;
import org.springframework.data.domain.Sort.Order;

View File

@@ -190,7 +190,7 @@ public class MongoRepositoryFactory extends RepositoryFactorySupport {
} else if (queryMethod.hasAnnotatedQuery()) {
return new StringBasedMongoQuery(queryMethod, operations, EXPRESSION_PARSER, evaluationContextProvider);
} else {
return new PartTreeMongoQuery(queryMethod, operations);
return new PartTreeMongoQuery(queryMethod, operations, EXPRESSION_PARSER, evaluationContextProvider);
}
}
}

View File

@@ -180,7 +180,7 @@ public class ReactiveMongoRepositoryFactory extends ReactiveRepositoryFactorySup
} else if (queryMethod.hasAnnotatedQuery()) {
return new ReactiveStringBasedMongoQuery(queryMethod, operations, EXPRESSION_PARSER, evaluationContextProvider);
} else {
return new ReactivePartTreeMongoQuery(queryMethod, operations);
return new ReactivePartTreeMongoQuery(queryMethod, operations, EXPRESSION_PARSER, evaluationContextProvider);
}
}
}

View File

@@ -16,9 +16,7 @@
package org.springframework.data.mongodb.repository.query;
import static org.assertj.core.api.Assertions.*;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.ArgumentMatchers.*;
import static org.mockito.Mockito.*;
import java.lang.reflect.Method;
@@ -35,6 +33,7 @@ import org.mockito.ArgumentCaptor;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.mockito.junit.MockitoJUnitRunner;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
@@ -60,6 +59,8 @@ import org.springframework.data.projection.ProjectionFactory;
import org.springframework.data.projection.SpelAwareProxyProjectionFactory;
import org.springframework.data.repository.Repository;
import org.springframework.data.repository.core.support.DefaultRepositoryMetadata;
import org.springframework.data.repository.query.QueryMethodEvaluationContextProvider;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import com.mongodb.client.result.DeleteResult;
@@ -455,7 +456,7 @@ public class AbstractMongoQueryUnitTests {
private boolean isLimitingQuery;
public MongoQueryFake(MongoQueryMethod method, MongoOperations operations) {
super(method, operations);
super(method, operations, new SpelExpressionParser(), QueryMethodEvaluationContextProvider.DEFAULT);
}
@Override

View File

@@ -30,6 +30,7 @@ import org.mockito.ArgumentCaptor;
import org.mockito.Mock;
import org.mockito.Mockito;
import org.mockito.junit.MockitoJUnitRunner;
import org.springframework.data.mongodb.core.Person;
import org.springframework.data.mongodb.core.ReactiveFindOperation.FindWithQuery;
import org.springframework.data.mongodb.core.ReactiveFindOperation.ReactiveFind;
@@ -45,6 +46,8 @@ import org.springframework.data.mongodb.repository.ReactiveMongoRepository;
import org.springframework.data.projection.ProjectionFactory;
import org.springframework.data.projection.SpelAwareProxyProjectionFactory;
import org.springframework.data.repository.core.support.DefaultRepositoryMetadata;
import org.springframework.data.repository.query.QueryMethodEvaluationContextProvider;
import org.springframework.expression.spel.standard.SpelExpressionParser;
/**
* @author Christoph Strobl
@@ -162,6 +165,19 @@ public class AbstractReactiveMongoQueryUnitTests {
.contains(Collation.of("en_US").toDocument());
}
@Test // DATAMONGO-1854
public void shouldApplyDynamicAnnotatedCollationWithMultiplePlaceholders() {
createQueryForMethod("findWithCollationUsingPlaceholdersInDocumentByFirstName", String.class, String.class,
int.class) //
.execute(new Object[] { "dalinar", "en_US", 2 });
ArgumentCaptor<Query> captor = ArgumentCaptor.forClass(Query.class);
verify(withQueryMock).matching(captor.capture());
assertThat(captor.getValue().getCollation().map(Collation::toDocument))
.contains(Collation.of("en_US").strength(2).toDocument());
}
@Test // DATAMONGO-1854
public void shouldApplyCollationParameter() {
@@ -223,7 +239,7 @@ public class AbstractReactiveMongoQueryUnitTests {
private boolean isLimitingQuery;
public ReactiveMongoQueryFake(ReactiveMongoQueryMethod method, ReactiveMongoOperations operations) {
super(method, operations);
super(method, operations, new SpelExpressionParser(), QueryMethodEvaluationContextProvider.DEFAULT);
}
@Override
@@ -277,6 +293,10 @@ public class AbstractReactiveMongoQueryUnitTests {
@org.springframework.data.mongodb.repository.Query(collation = "{ 'locale' : '?1' }")
List<Person> findWithCollationUsingPlaceholderInDocumentByFirstName(String firstname, String collation);
@org.springframework.data.mongodb.repository.Query(collation = "{ 'locale' : '?1', 'strength' : ?#{[2]}}")
List<Person> findWithCollationUsingPlaceholdersInDocumentByFirstName(String firstname, String collation,
int strength);
List<Person> findWithCollationParameterByFirstName(String firstname, Collation collation);
@org.springframework.data.mongodb.repository.Query(collation = "{ 'locale' : 'en_US' }")

View File

@@ -15,7 +15,7 @@
*/
package org.springframework.data.mongodb.repository.query;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.*;
import static org.mockito.Mockito.*;
import java.lang.reflect.Method;
@@ -27,6 +27,7 @@ import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.junit.MockitoJUnitRunner;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.geo.Distance;
@@ -53,6 +54,8 @@ import org.springframework.data.projection.SpelAwareProxyProjectionFactory;
import org.springframework.data.repository.Repository;
import org.springframework.data.repository.core.RepositoryMetadata;
import org.springframework.data.repository.core.support.DefaultRepositoryMetadata;
import org.springframework.data.repository.query.QueryMethodEvaluationContextProvider;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.util.ReflectionUtils;
/**
@@ -72,6 +75,7 @@ public class MongoQueryExecutionUnitTests {
@Mock TerminatingFindNear<Object> terminatingGeoMock;
@Mock DbRefResolver dbRefResolver;
SpelExpressionParser EXPRESSION_PARSER = new SpelExpressionParser();
Point POINT = new Point(10, 20);
Distance DISTANCE = new Distance(2.5, Metrics.KILOMETERS);
RepositoryMetadata metadata = new DefaultRepositoryMetadata(PersonRepository.class);
@@ -140,7 +144,8 @@ public class MongoQueryExecutionUnitTests {
ConvertingParameterAccessor accessor = new ConvertingParameterAccessor(converter,
new MongoParametersParameterAccessor(queryMethod, new Object[] { POINT, DISTANCE, PageRequest.of(0, 10) }));
PartTreeMongoQuery query = new PartTreeMongoQuery(queryMethod, mongoOperationsMock);
PartTreeMongoQuery query = new PartTreeMongoQuery(queryMethod, mongoOperationsMock, EXPRESSION_PARSER,
QueryMethodEvaluationContextProvider.DEFAULT);
PagingGeoNearExecution execution = new PagingGeoNearExecution(findOperationMock, queryMethod, accessor, query);
execution.execute(new Query());
@@ -158,7 +163,8 @@ public class MongoQueryExecutionUnitTests {
ConvertingParameterAccessor accessor = new ConvertingParameterAccessor(converter,
new MongoParametersParameterAccessor(queryMethod, new Object[] { POINT, DISTANCE, PageRequest.of(2, 10) }));
PartTreeMongoQuery query = new PartTreeMongoQuery(queryMethod, mongoOperationsMock);
PartTreeMongoQuery query = new PartTreeMongoQuery(queryMethod, mongoOperationsMock, EXPRESSION_PARSER,
QueryMethodEvaluationContextProvider.DEFAULT);
PagingGeoNearExecution execution = new PagingGeoNearExecution(findOperationMock, queryMethod, accessor, query);
execution.execute(new Query());

View File

@@ -33,6 +33,7 @@ import org.junit.rules.ExpectedException;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.junit.MockitoJUnitRunner;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.mongodb.MongoDbFactory;
import org.springframework.data.mongodb.core.ExecutableFindOperation.ExecutableFind;
@@ -51,6 +52,8 @@ import org.springframework.data.mongodb.repository.Query;
import org.springframework.data.projection.ProjectionFactory;
import org.springframework.data.projection.SpelAwareProxyProjectionFactory;
import org.springframework.data.repository.core.support.DefaultRepositoryMetadata;
import org.springframework.data.repository.query.QueryMethodEvaluationContextProvider;
import org.springframework.expression.spel.standard.SpelExpressionParser;
/**
* Unit tests for {@link PartTreeMongoQuery}.
@@ -217,7 +220,8 @@ public class PartTreeMongoQueryUnitTests {
MongoQueryMethod queryMethod = new MongoQueryMethod(method, new DefaultRepositoryMetadata(Repo.class), factory,
mappingContext);
return new PartTreeMongoQuery(queryMethod, mongoOperationsMock);
return new PartTreeMongoQuery(queryMethod, mongoOperationsMock, new SpelExpressionParser(),
QueryMethodEvaluationContextProvider.DEFAULT);
} catch (Exception e) {
throw new IllegalArgumentException(e.getMessage(), e);
}