Skip to content

Commit

Permalink
Add factory method overload to ValueExpressionQueryRewriter to return…
Browse files Browse the repository at this point in the history
… a EvaluatingValueExpressionQueryRewriter directly.
  • Loading branch information
mp911de committed Oct 8, 2024
1 parent 5c290bb commit 09faabc
Show file tree
Hide file tree
Showing 3 changed files with 41 additions and 17 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,14 @@ public static ValueExpressionDelegate create() {
ValueExpressionParser.create());
}

public ValueExpressionParser getValueExpressionParser() {
return valueExpressionParser;
}

public QueryMethodValueEvaluationContextAccessor getEvaluationContextAccessor() {
return contextAccessor;
}

/**
* Creates a {@link ValueEvaluationContextProvider} for query method {@link Parameters} for later creation of a
* {@link ValueEvaluationContext} based on the actual method parameter values. The resulting
Expand All @@ -76,10 +84,6 @@ public ValueEvaluationContextProvider createValueContextProvider(Parameters<?, ?
return contextAccessor.create(parameters);
}

public ValueExpressionParser getValueExpressionParser() {
return valueExpressionParser;
}

@Override
public ValueExpression parse(String expressionString) throws ParseException {
return valueExpressionParser.parse(expressionString);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -98,21 +98,39 @@ private ValueExpressionQueryRewriter(ValueExpressionParser expressionParser,
}

/**
* Creates a new {@link ValueExpressionQueryRewriter} using the given {@link ValueExpressionParser} and rewrite
* functions.
* Creates a new {ValueExpressionQueryRewriter using the given {@link ValueExpressionParser} and rewrite functions.
*
* @param expressionParser the expression parser to use.
* @param parameterNameSource function to generate parameter names. Typically, a function of the form
* {@code (index, expression) -> "__some_placeholder_" + index}.
* @param replacementSource function to generate replacements. Typically, a concatenation of the prefix and the
* parameter name such as {@code String::concat}.
* @return
* @return a ValueExpressionQueryRewriter instance to rewrite queries and extract parsed {@link ValueExpression}s.
*/
public static ValueExpressionQueryRewriter of(ValueExpressionParser expressionParser,
BiFunction<Integer, String, String> parameterNameSource, BiFunction<String, String, String> replacementSource) {
return new ValueExpressionQueryRewriter(expressionParser, parameterNameSource, replacementSource);
}

/**
* Creates a new {@link ValueExpressionQueryRewriter} using the given {@link ValueExpressionParser} and rewrite
* functions.
*
* @param delegate the ValueExpressionDelegate to use for parsing and to obtain EvaluationContextAccessor from.
* @param parameterNameSource function to generate parameter names. Typically, a function of the form
* {@code (index, expression) -> "__some_placeholder_" + index}.
* @param replacementSource function to generate replacements. Typically, a concatenation of the prefix and the
* parameter name such as {@code String::concat}.
* @return a EvaluatingValueExpressionQueryRewriter instance to rewrite queries and extract parsed
* {@link ValueExpression}s.
* @since 3.4
*/
public static EvaluatingValueExpressionQueryRewriter of(ValueExpressionDelegate delegate,
BiFunction<Integer, String, String> parameterNameSource, BiFunction<String, String, String> replacementSource) {
return of((ValueExpressionParser) delegate, parameterNameSource, replacementSource)
.withEvaluationContextAccessor(delegate.getEvaluationContextAccessor());
}

/**
* Parses the query for {@link org.springframework.data.expression.ValueExpression value expressions} using the
* pattern:
Expand All @@ -137,15 +155,15 @@ public ParsedQuery parse(String query) {
* Creates a {@link EvaluatingValueExpressionQueryRewriter} from the current one and the given
* {@link QueryMethodValueEvaluationContextAccessor}.
*
* @param factory must not be {@literal null}.
* @return
* @param accessor must not be {@literal null}.
* @return EvaluatingValueExpressionQueryRewriter instance to rewrite and evaluate Value Expressions.
*/
public EvaluatingValueExpressionQueryRewriter withEvaluationContextAccessor(
QueryMethodValueEvaluationContextAccessor factory) {
QueryMethodValueEvaluationContextAccessor accessor) {

Assert.notNull(factory, "QueryMethodValueEvaluationContextAccessor must not be null");
Assert.notNull(accessor, "QueryMethodValueEvaluationContextAccessor must not be null");

return new EvaluatingValueExpressionQueryRewriter(expressionParser, factory, parameterNameSource,
return new EvaluatingValueExpressionQueryRewriter(expressionParser, accessor, parameterNameSource,
replacementSource);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -74,7 +74,6 @@ void findsAndReplacesExpressions() {
Tuple.tuple("EPP2", "${three}"), //
Tuple.tuple("EPP3", "${four}") //
);

}

@Test // GH-3049
Expand Down Expand Up @@ -113,17 +112,20 @@ private void checkNoExpressionIsFound(String query) {
@Test // GH-3049
void shouldEvaluateExpression() throws Exception {

ValueExpressionQueryRewriter rewriter = ValueExpressionQueryRewriter.of(PARSER, PARAMETER_NAME_SOURCE,
REPLACEMENT_SOURCE);
StandardEnvironment environment = new StandardEnvironment();
environment.getPropertySources().addFirst(new MapPropertySource("synthetic", Map.of("foo", "world")));

QueryMethodValueEvaluationContextAccessor factory = new QueryMethodValueEvaluationContextAccessor(environment,
QueryMethodValueEvaluationContextAccessor contextAccessor = new QueryMethodValueEvaluationContextAccessor(
environment,
EvaluationContextProvider.DEFAULT);

ValueExpressionDelegate delegate = new ValueExpressionDelegate(contextAccessor, PARSER);
ValueExpressionQueryRewriter.EvaluatingValueExpressionQueryRewriter rewriter = ValueExpressionQueryRewriter
.of(delegate, PARAMETER_NAME_SOURCE, REPLACEMENT_SOURCE);

Method method = ValueExpressionQueryRewriterUnitTests.MyRepository.class.getDeclaredMethod("simpleExpression",
String.class);
var extractor = rewriter.withEvaluationContextAccessor(factory).parse("SELECT :#{#value}, :${foo}",
var extractor = rewriter.parse("SELECT :#{#value}, :${foo}",
new DefaultParameters(ParametersSource.of(method)));

assertThat(extractor.getQueryString()).isEqualTo("SELECT :EPP0, :EPP1");
Expand Down

0 comments on commit 09faabc

Please sign in to comment.