Moving the MethodPublishingInterceptor and @Publisher annotation support to the sandbox for now.

This commit is contained in:
Mark Fisher
2008-10-20 17:55:36 +00:00
parent 7ffab20b45
commit 6e4b501ec6
12 changed files with 0 additions and 850 deletions

View File

@@ -1,91 +0,0 @@
/*
* Copyright 2002-2008 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.integration.aop;
import java.lang.annotation.Annotation;
import java.lang.reflect.Method;
import org.aopalliance.intercept.MethodInvocation;
import org.springframework.aop.support.AopUtils;
import org.springframework.core.annotation.AnnotationUtils;
import org.springframework.integration.channel.ChannelResolver;
import org.springframework.integration.core.MessageChannel;
import org.springframework.util.Assert;
/**
* {@link MessagePublishingInterceptor} that resolves the channel from the
* publisher annotation of the invoked method.
*
* @author Mark Fisher
*/
public class AnnotationAwareMessagePublishingInterceptor extends MessagePublishingInterceptor {
private Class<? extends Annotation> publisherAnnotationType;
private String channelAttributeName;
private ChannelResolver channelResolver;
public AnnotationAwareMessagePublishingInterceptor(Class<? extends Annotation> publisherAnnotationType,
String channelAttributeName, ChannelResolver channelResolver) {
Assert.notNull(publisherAnnotationType, "'publisherAnnotationType' must not be null");
Assert.notNull(channelAttributeName, "'channelAttributeName' must not be null");
Assert.notNull(channelResolver, "'channelResolver' must not be null");
this.publisherAnnotationType = publisherAnnotationType;
this.channelAttributeName = channelAttributeName;
this.channelResolver = channelResolver;
}
@Override
protected MessageChannel resolveChannel(MethodInvocation invocation) {
String channelName = this.extractAnnotationValue(invocation, this.channelAttributeName, String.class);
if (channelName != null) {
MessageChannel channel = this.channelResolver.resolveChannelName(channelName);
if (channel != null) {
return channel;
}
}
return super.resolveChannel(invocation);
}
@Override
protected PayloadType determinePayloadType(MethodInvocation invocation) {
PayloadType payloadType = this.extractAnnotationValue(invocation, "payloadType", PayloadType.class);
if (payloadType != null) {
return payloadType;
}
return super.determinePayloadType(invocation);
}
@SuppressWarnings("unchecked")
private <T> T extractAnnotationValue(MethodInvocation invocation, String attributeName, Class<T> type) {
Class<?> targetClass = AopUtils.getTargetClass(invocation.getThis());
Method method = AopUtils.getMostSpecificMethod(invocation.getMethod(), targetClass);
Annotation annotation = AnnotationUtils.getAnnotation(method, this.publisherAnnotationType);
if (annotation != null) {
Object value = AnnotationUtils.getValue(annotation, attributeName);
if (value != null && type.isAssignableFrom(value.getClass())) {
return (T) value;
}
}
return null;
}
}

View File

@@ -1,106 +0,0 @@
/*
* Copyright 2002-2008 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.integration.aop;
import org.aopalliance.intercept.MethodInterceptor;
import org.aopalliance.intercept.MethodInvocation;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.integration.channel.MessageChannelTemplate;
import org.springframework.integration.core.Message;
import org.springframework.integration.core.MessageChannel;
import org.springframework.integration.message.MessageBuilder;
import org.springframework.util.Assert;
/**
* Interceptor that publishes a target method's return value to a channel.
*
* @author Mark Fisher
*/
public class MessagePublishingInterceptor implements MethodInterceptor {
public static enum PayloadType { RETURN_VALUE, ARGUMENTS, EXCEPTION };
protected final Log logger = LogFactory.getLog(getClass());
private volatile MessageChannel outputChannel;
private final MessageChannelTemplate channelTemplate = new MessageChannelTemplate();
private volatile PayloadType payloadType = PayloadType.RETURN_VALUE;
public void setOutputChannel(MessageChannel outputChannel) {
this.outputChannel = outputChannel;
}
public void setPayloadType(PayloadType payloadType) {
Assert.notNull(payloadType, "'payloadType' must not be null");
this.payloadType = payloadType;
}
/**
* Invoke the target method and publish its return value.
*/
public Object invoke(MethodInvocation invocation) throws Throwable {
PayloadType payloadType = this.determinePayloadType(invocation);
if (payloadType.equals(PayloadType.ARGUMENTS)) {
this.sendMessage(invocation.getArguments(), invocation);
}
Object retval = null;
Throwable throwable = null;
try {
retval = invocation.proceed();
return retval;
}
catch (Throwable t) {
throwable = t;
throw t;
}
finally {
if (payloadType.equals(PayloadType.RETURN_VALUE)) {
this.sendMessage(retval, invocation);
}
else if (payloadType.equals(PayloadType.EXCEPTION)) {
this.sendMessage(throwable, invocation);
}
}
}
private void sendMessage(Object payload, MethodInvocation invocation) {
if (payload != null) {
Message<?> message = (payload instanceof Message)
? (Message<?>) payload
: MessageBuilder.withPayload(payload).build();
this.channelTemplate.send(message, this.resolveChannel(invocation));
}
}
/**
* Subclasses may override this method to provide custom behavior.
*/
protected MessageChannel resolveChannel(MethodInvocation invocation) {
return this.outputChannel;
}
protected PayloadType determinePayloadType(MethodInvocation invocation) {
return this.payloadType;
}
}

View File

@@ -1,52 +0,0 @@
/*
* Copyright 2002-2008 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.integration.aop;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Inherited;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* Indicates that the method's return value, thrown exception, or
* invocation arguments should be published to the specified
* channel. The value will only be published if non-null.
* The default payload type is <em>return value</em>.
*
* @author Mark Fisher
*/
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Inherited
@Documented
public @interface Publisher {
/**
* name of the channel where Messages should be sent
*/
String channel();
/**
* type of payload to intercept and send
* @see MessagePublishingInterceptor.PayloadType
*/
MessagePublishingInterceptor.PayloadType payloadType()
default MessagePublishingInterceptor.PayloadType.RETURN_VALUE;
}

View File

@@ -1,68 +0,0 @@
/*
* Copyright 2002-2008 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.integration.aop;
import java.lang.annotation.Annotation;
import org.aopalliance.aop.Advice;
import org.springframework.aop.Pointcut;
import org.springframework.aop.support.AbstractPointcutAdvisor;
import org.springframework.aop.support.annotation.AnnotationMatchingPointcut;
import org.springframework.integration.channel.ChannelResolver;
import org.springframework.util.Assert;
/**
* Advisor whose pointcut matches a method annotation and whose advice will
* publish a message to the channel provided by that annotation.
*
* @author Mark Fisher
* @see Publisher
* @see AnnotationAwareMessagePublishingInterceptor
*/
@SuppressWarnings("serial")
public class PublisherAnnotationAdvisor extends AbstractPointcutAdvisor {
private AnnotationAwareMessagePublishingInterceptor advice;
private AnnotationMatchingPointcut pointcut;
public PublisherAnnotationAdvisor(ChannelResolver channelResolver) {
this(Publisher.class, "channel", channelResolver);
}
public PublisherAnnotationAdvisor(Class<? extends Annotation> publisherAnnotationType,
String channelNameAttribute, ChannelResolver channelResolver) {
Assert.notNull(publisherAnnotationType, "'publisherAnnotationType' must not be null");
Assert.notNull(channelNameAttribute, "'channelNameAttribute' must not be null");
Assert.notNull(channelResolver, "'channelResolver' must not be null");
this.pointcut = AnnotationMatchingPointcut.forMethodAnnotation(publisherAnnotationType);
this.advice = new AnnotationAwareMessagePublishingInterceptor(
publisherAnnotationType, channelNameAttribute, channelResolver);
}
public Pointcut getPointcut() {
return this.pointcut;
}
public Advice getAdvice() {
return this.advice;
}
}

View File

@@ -1,137 +0,0 @@
/*
* Copyright 2002-2008 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.integration.config.annotation;
import java.lang.annotation.Annotation;
import java.lang.reflect.Method;
import java.util.concurrent.atomic.AtomicBoolean;
import org.springframework.aop.Advisor;
import org.springframework.aop.framework.Advised;
import org.springframework.aop.framework.ProxyFactory;
import org.springframework.aop.support.AopUtils;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.BeanClassLoaderAware;
import org.springframework.beans.factory.BeanFactory;
import org.springframework.beans.factory.BeanFactoryAware;
import org.springframework.beans.factory.config.BeanPostProcessor;
import org.springframework.core.annotation.AnnotationUtils;
import org.springframework.integration.aop.Publisher;
import org.springframework.integration.aop.PublisherAnnotationAdvisor;
import org.springframework.integration.channel.BeanFactoryChannelResolver;
import org.springframework.util.Assert;
import org.springframework.util.ReflectionUtils;
/**
* A {@link BeanPostProcessor} that adds a message publishing interceptor when
* it discovers annotated methods.
*
* @author Mark Fisher
*/
public class PublisherAnnotationPostProcessor implements BeanPostProcessor, BeanFactoryAware, BeanClassLoaderAware {
private volatile Class<? extends Annotation> publisherAnnotationType = Publisher.class;
private volatile String channelNameAttribute = "channel";
private volatile Advisor advisor;
private volatile BeanFactory beanFactory;
private volatile ClassLoader beanClassLoader;
public void setBeanFactory(BeanFactory beanFactory) {
this.beanFactory = beanFactory;
}
public void setBeanClassLoader(ClassLoader beanClassLoader) {
Assert.notNull(beanClassLoader, "'beanClassLoader' must not be null");
this.beanClassLoader = beanClassLoader;
}
public void setPublisherAnnotationType(Class<? extends Annotation> publisherAnnotationType) {
Assert.notNull(publisherAnnotationType, "'publisherAnnotationType' must not be null");
this.publisherAnnotationType = publisherAnnotationType;
}
public void setChannelNameAttribute(String channelNameAttribute) {
Assert.notNull(channelNameAttribute, "'channelNameAttribute' must not be null");
this.channelNameAttribute = channelNameAttribute;
}
private void createAdvisor() {
Assert.state(this.beanFactory != null, "BeanFactory is required");
this.advisor = new PublisherAnnotationAdvisor(this.publisherAnnotationType, this.channelNameAttribute,
new BeanFactoryChannelResolver(this.beanFactory));
}
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
return bean;
}
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
Class<?> targetClass = AopUtils.getTargetClass(bean);
if (targetClass == null) {
return bean;
}
if (this.advisor == null) {
this.createAdvisor();
}
if (AopUtils.canApply(this.advisor, targetClass)) {
if (bean instanceof Advised) {
((Advised) bean).addAdvisor(this.advisor);
return bean;
}
else {
ProxyFactory pf = new ProxyFactory(bean);
pf.setProxyTargetClass(this.requiresClassProxying(targetClass));
pf.addAdvisor(this.advisor);
return pf.getProxy(this.beanClassLoader);
}
}
else {
return bean;
}
}
private boolean requiresClassProxying(Class<?> targetClass) {
final AtomicBoolean result = new AtomicBoolean(false);
final Class<?>[] interfaces = targetClass.getInterfaces();
ReflectionUtils.doWithMethods(targetClass, new ReflectionUtils.MethodCallback() {
public void doWith(Method method) throws IllegalArgumentException, IllegalAccessException {
Annotation annotation = AnnotationUtils.findAnnotation(method, publisherAnnotationType);
if (annotation != null) {
boolean foundMethodOnInterface = false;
for (Class<?> iface : interfaces) {
Method ifaceMethod = ReflectionUtils.findMethod(
iface, method.getName(), method.getParameterTypes());
if (ifaceMethod != null) {
foundMethodOnInterface = true;
break;
}
}
if (!foundMethodOnInterface) {
result.set(true);
}
}
}
});
return result.get();
}
}

View File

@@ -40,7 +40,6 @@ import org.springframework.integration.bus.MessageBusAwareBeanPostProcessor;
import org.springframework.integration.channel.MessagePublishingErrorHandler;
import org.springframework.integration.channel.QueueChannel;
import org.springframework.integration.config.annotation.MessagingAnnotationPostProcessor;
import org.springframework.integration.config.annotation.PublisherAnnotationPostProcessor;
import org.springframework.integration.scheduling.SimpleTaskScheduler;
import org.springframework.scheduling.concurrent.CustomizableThreadFactory;
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
@@ -60,9 +59,6 @@ public class MessageBusParser extends AbstractSimpleBeanDefinitionParser {
public static final String MESSAGE_BUS_AWARE_POST_PROCESSOR_BEAN_NAME =
"internal.MessageBusAwareBeanPostProcessor";
private static final String PUBLISHER_ANNOTATION_POST_PROCESSOR_BEAN_NAME =
"internal.PublisherAnnotationPostProcessor";
private static final String MESSAGING_ANNOTATION_POST_PROCESSOR_BEAN_NAME =
"internal.MessagingAnnotationPostProcessor";
@@ -154,7 +150,6 @@ public class MessageBusParser extends AbstractSimpleBeanDefinitionParser {
private void addPostProcessors(Element element, ParserContext parserContext) {
this.registerMessageBusAwarePostProcessor(parserContext);
if ("true".equals(element.getAttribute("enable-annotations").toLowerCase())) {
this.registerPublisherPostProcessor(parserContext);
this.registerMessagingAnnotationPostProcessor(parserContext);
}
}
@@ -166,12 +161,6 @@ public class MessageBusParser extends AbstractSimpleBeanDefinitionParser {
parserContext.getRegistry().registerBeanDefinition(MESSAGE_BUS_AWARE_POST_PROCESSOR_BEAN_NAME, builder.getBeanDefinition());
}
private void registerPublisherPostProcessor(ParserContext parserContext) {
BeanDefinition bd = new RootBeanDefinition(PublisherAnnotationPostProcessor.class);
BeanComponentDefinition bcd = new BeanComponentDefinition(bd, PUBLISHER_ANNOTATION_POST_PROCESSOR_BEAN_NAME);
parserContext.registerBeanComponent(bcd);
}
private void registerMessagingAnnotationPostProcessor(ParserContext parserContext) {
BeanDefinition bd = new RootBeanDefinition(MessagingAnnotationPostProcessor.class);
BeanComponentDefinition bcd = new BeanComponentDefinition(

View File

@@ -1,26 +0,0 @@
/*
* Copyright 2002-2008 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.integration.aop;
/**
* @author Mark Fisher
*/
public interface ITestBean {
String test();
}

View File

@@ -1,98 +0,0 @@
/*
* Copyright 2002-2008 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.integration.aop;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import org.junit.Test;
import org.springframework.aop.framework.ProxyFactory;
import org.springframework.integration.channel.QueueChannel;
import org.springframework.integration.core.Message;
/**
* @author Mark Fisher
*/
public class MessagePublishingInterceptorTests {
@Test
public void testNonNullReturnValuePublishedWithDefaultChannel() {
QueueChannel channel = new QueueChannel();
MessagePublishingInterceptor interceptor = new MessagePublishingInterceptor();
interceptor.setOutputChannel(channel);
TestService proxy = (TestService) this.createProxy(new TestServiceImpl("hello world"), interceptor);
proxy.messageTest();
Message<?> message = channel.receive(0);
assertNotNull(message);
assertEquals("hello world", message.getPayload());
}
@Test
public void testNullReturnValueNotPublished() {
QueueChannel channel = new QueueChannel();
MessagePublishingInterceptor interceptor = new MessagePublishingInterceptor();
interceptor.setOutputChannel(channel);
TestService proxy = (TestService) this.createProxy(new TestServiceImpl(null), interceptor);
proxy.messageTest();
assertNull(channel.receive(0));
}
@Test
public void testVoidReturnValueNotPublished() {
QueueChannel channel = new QueueChannel();
MessagePublishingInterceptor interceptor = new MessagePublishingInterceptor();
interceptor.setOutputChannel(channel);
TestService proxy = (TestService) this.createProxy(new TestServiceImpl(null), interceptor);
proxy.voidTest();
assertNull(channel.receive(0));
}
private Object createProxy(Object target, MessagePublishingInterceptor interceptor) {
ProxyFactory factory = new ProxyFactory(target);
factory.addAdvice(interceptor);
return factory.getProxy();
}
private static interface TestService {
String messageTest();
void voidTest();
}
private static class TestServiceImpl implements TestService {
private String message;
public TestServiceImpl(String message) {
this.message = message;
}
public String messageTest() {
return this.message;
}
public void voidTest() {
return;
}
}
}

View File

@@ -1,173 +0,0 @@
/*
* Copyright 2002-2008 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.integration.aop;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertTrue;
import org.junit.Test;
import org.springframework.aop.framework.ProxyFactory;
import org.springframework.integration.channel.QueueChannel;
import org.springframework.integration.channel.TestChannelResolver;
import org.springframework.integration.core.Message;
/**
* @author Mark Fisher
*/
public class PublisherAnnotationAdvisorTests {
@Test
public void testPublisherAnnotation() {
final QueueChannel channel = new QueueChannel();
channel.setBeanName("testChannel");
TestChannelResolver channelResolver = new TestChannelResolver();
channelResolver.addChannel(channel);
PublisherAnnotationAdvisor advisor = new PublisherAnnotationAdvisor(channelResolver);
TestService proxy = (TestService) this.createProxy(new TestServiceImpl("hello world"), advisor);
proxy.publisherTest();
Message<?> message = channel.receive(0);
assertNotNull(message);
assertEquals("hello world", message.getPayload());
}
@Test
public void testNoPublisherAnnotation() {
final QueueChannel channel = new QueueChannel();
channel.setBeanName("testChannel");
TestChannelResolver channelResolver = new TestChannelResolver();
channelResolver.addChannel(channel);
PublisherAnnotationAdvisor advisor = new PublisherAnnotationAdvisor(channelResolver);
TestService proxy = (TestService) this.createProxy(new TestServiceImpl("hello world"), advisor);
proxy.noPublisherTest();
Message<?> message = channel.receive(0);
assertNull(message);
}
@Test
public void testPublishArguments() {
final QueueChannel channel = new QueueChannel();
channel.setBeanName("testChannel");
TestChannelResolver channelResolver = new TestChannelResolver();
channelResolver.addChannel(channel);
PublisherAnnotationAdvisor advisor = new PublisherAnnotationAdvisor(channelResolver);
TestService proxy = (TestService) this.createProxy(new TestServiceImpl("hello world"), advisor);
proxy.publishArguments("foo", 99);
Message<?> message = channel.receive(0);
assertNotNull(message);
assertTrue(message.getPayload() instanceof Object[]);
Object[] args = (Object[]) message.getPayload();
assertEquals(2, args.length);
assertEquals("foo", args[0]);
assertEquals(99, args[1]);
}
@Test
public void testPublishException() {
final QueueChannel channel = new QueueChannel();
channel.setBeanName("testChannel");
TestChannelResolver channelResolver = new TestChannelResolver();
channelResolver.addChannel(channel);
PublisherAnnotationAdvisor advisor = new PublisherAnnotationAdvisor(channelResolver);
TestService proxy = (TestService) this.createProxy(new TestServiceImpl("hello world"), advisor);
RuntimeException caughtException = null;
try {
proxy.publishException();
}
catch (RuntimeException e) {
caughtException = e;
}
assertNotNull(caughtException);
Message<?> message = channel.receive(0);
assertNotNull(message);
assertTrue(message.getPayload() instanceof RuntimeException);
RuntimeException publishedException = (RuntimeException) message.getPayload();
assertEquals(caughtException, publishedException);
}
@Test
public void testPublishReturnValue() {
final QueueChannel channel = new QueueChannel();
channel.setBeanName("testChannel");
TestChannelResolver channelResolver = new TestChannelResolver();
channelResolver.addChannel(channel);
PublisherAnnotationAdvisor advisor = new PublisherAnnotationAdvisor(channelResolver);
TestService proxy = (TestService) this.createProxy(new TestServiceImpl("hello world"), advisor);
Integer actualReturnValue = proxy.publishReturnValue();
Message<?> message = channel.receive(0);
assertNotNull(message);
assertEquals(actualReturnValue, message.getPayload());
}
private Object createProxy(Object target, PublisherAnnotationAdvisor advisor) {
ProxyFactory factory = new ProxyFactory(target);
factory.addAdvisor(advisor);
return factory.getProxy();
}
private static interface TestService {
String publisherTest();
String noPublisherTest();
void publishArguments(String s, Integer n);
Integer publishReturnValue();
void publishException();
}
private static class TestServiceImpl implements TestService {
private String message;
public TestServiceImpl(String message) {
this.message = message;
}
@Publisher(channel="testChannel")
public String publisherTest() {
return this.message;
}
public String noPublisherTest() {
return this.message;
}
@Publisher(channel="testChannel", payloadType=MessagePublishingInterceptor.PayloadType.ARGUMENTS)
public void publishArguments(String s, Integer n) {
}
@Publisher(channel="testChannel", payloadType=MessagePublishingInterceptor.PayloadType.EXCEPTION)
public void publishException() {
throw new RuntimeException("test failure");
}
@Publisher(channel="testChannel", payloadType=MessagePublishingInterceptor.PayloadType.RETURN_VALUE)
public Integer publishReturnValue() {
return 123;
}
}
}

View File

@@ -1,44 +0,0 @@
/*
* Copyright 2002-2008 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.integration.aop;
import static org.junit.Assert.assertEquals;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import org.springframework.integration.channel.PollableChannel;
import org.springframework.integration.core.Message;
/**
* @author Mark Fisher
*/
public class PublisherAnnotationPostProcessorTests {
@Test
public void testPublisherAnnotation() {
ApplicationContext context = new ClassPathXmlApplicationContext(
"publisherAnnotationPostProcessorTests.xml", this.getClass());
ITestBean testBean = (ITestBean) context.getBean("testBean");
testBean.test();
PollableChannel channel = (PollableChannel) context.getBean("testChannel");
Message<?> result = channel.receive();
assertEquals("test", result.getPayload());
}
}

View File

@@ -1,31 +0,0 @@
/*
* Copyright 2002-2008 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.integration.aop;
/**
* @author Mark Fisher
*/
public class PublisherAnnotationTestBean implements ITestBean {
@Publisher(channel="testChannel")
public String test() {
return "test";
}
}

View File

@@ -1,13 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd">
<bean id="testChannel" class="org.springframework.integration.channel.QueueChannel"/>
<bean id="testBean" class="org.springframework.integration.aop.PublisherAnnotationTestBean"/>
<bean class="org.springframework.integration.config.annotation.PublisherAnnotationPostProcessor"/>
</beans>