diff --git a/src/main/java/org/springframework/data/projection/SpelEvaluatingMethodInterceptor.java b/src/main/java/org/springframework/data/projection/SpelEvaluatingMethodInterceptor.java index fb2dd2407..4feddee13 100644 --- a/src/main/java/org/springframework/data/projection/SpelEvaluatingMethodInterceptor.java +++ b/src/main/java/org/springframework/data/projection/SpelEvaluatingMethodInterceptor.java @@ -52,6 +52,7 @@ class SpelEvaluatingMethodInterceptor implements MethodInterceptor { private final EvaluationContext evaluationContext; private final MethodInterceptor delegate; private final Map expressions; + private final Object target; /** * Creates a new {@link SpelEvaluatingMethodInterceptor} delegating to the given {@link MethodInterceptor} as fallback @@ -72,7 +73,7 @@ class SpelEvaluatingMethodInterceptor implements MethodInterceptor { Assert.notNull(parser, "SpelExpressionParser must not be null!"); Assert.notNull(targetInterface, "Target interface must not be null!"); - StandardEvaluationContext evaluationContext = new StandardEvaluationContext(new TargetWrapper(target)); + StandardEvaluationContext evaluationContext = new StandardEvaluationContext(); if (target instanceof Map) { evaluationContext.addPropertyAccessor(new MapAccessor()); @@ -86,6 +87,7 @@ class SpelEvaluatingMethodInterceptor implements MethodInterceptor { this.evaluationContext = evaluationContext; this.delegate = delegate; + this.target = target; } /** @@ -134,7 +136,7 @@ class SpelEvaluatingMethodInterceptor implements MethodInterceptor { return delegate.invoke(invocation); } - return expression.getValue(evaluationContext); + return expression.getValue(evaluationContext, TargetWrapper.of(target, invocation.getArguments())); } /** @@ -142,19 +144,10 @@ class SpelEvaluatingMethodInterceptor implements MethodInterceptor { * * @author Oliver Gierke */ + @lombok.Value(staticConstructor = "of") static class TargetWrapper { - private final Object target; - - public TargetWrapper(Object target) { - this.target = target; - } - - /** - * @return the target - */ - public Object getTarget() { - return target; - } + Object target; + Object[] args; } } diff --git a/src/test/java/org/springframework/data/projection/SpelEvaluatingMethodInterceptorUnitTests.java b/src/test/java/org/springframework/data/projection/SpelEvaluatingMethodInterceptorUnitTests.java index 3c4e8bc47..ad7504233 100755 --- a/src/test/java/org/springframework/data/projection/SpelEvaluatingMethodInterceptorUnitTests.java +++ b/src/test/java/org/springframework/data/projection/SpelEvaluatingMethodInterceptorUnitTests.java @@ -104,6 +104,21 @@ public class SpelEvaluatingMethodInterceptorUnitTests { assertThat(interceptor.invoke(invocation)).isEqualTo("Dave"); } + @Test // DATACMNS-1150 + public void forwardsParameterIntoSpElExpressionEvaluation() throws Throwable { + + DefaultListableBeanFactory factory = new DefaultListableBeanFactory(); + factory.registerSingleton("someBean", new SomeBean()); + + when(invocation.getMethod()).thenReturn(Projection.class.getMethod("invokeBeanWithParameter", Integer.class)); + when(invocation.getArguments()).thenReturn(new Object[] { 1 }); + + MethodInterceptor interceptor = new SpelEvaluatingMethodInterceptor(delegate, new Target(), factory, parser, + Projection.class); + + assertThat(interceptor.invoke(invocation)).isEqualTo("property1"); + } + interface Projection { @Value("#{target.name}") @@ -115,6 +130,9 @@ public class SpelEvaluatingMethodInterceptorUnitTests { String getName(); String getAddress(); + + @Value("#{@someBean.someMethod(target, args[0])}") + String invokeBeanWithParameter(Integer parameter); } interface InvalidProjection { @@ -135,5 +153,9 @@ public class SpelEvaluatingMethodInterceptorUnitTests { public String getValue() { return "value"; } + + public String someMethod(Target target, Integer parameter) { + return target.getName() + parameter.toString(); + } } }