INT-4537: Fix RSConsumer for MockIntegrationCtx

JIRA: https://jira.spring.io/browse/INT-4537

Fixes spring-projects/spring-integration#2582

* Rename `ReactiveStreamsConsumer.messageHandler` property to the
`handler` for consistency with other `IntegrationConsumer` s
* Do not wrap `Subscriber` into the `MessageHandler` if that one is
already a `MessageHandler`
* Fix `MockIntegrationContext` for the logic around `ReactiveStreamsConsumer`
where it is not enough just replace a `handler`, but we also need to do
that with the `subscriber`.
Luckily the `MockMessageHandler` is also a Reactive `Subscriber`
* Clean up `MockIntegrationContext.beans` in the end of `resetBeans()`
* Improve `testing.adoc`

**Cherry-pick to 5.0.x**
This commit is contained in:
Artem Bilan
2018-10-05 13:36:29 -04:00
committed by Gary Russell
parent 9e9fa2cf58
commit 2df71fba30
4 changed files with 64 additions and 16 deletions

View File

@@ -30,6 +30,7 @@ import org.springframework.context.Lifecycle;
import org.springframework.integration.core.MessageProducer;
import org.springframework.integration.core.MessageSource;
import org.springframework.integration.endpoint.IntegrationConsumer;
import org.springframework.integration.endpoint.ReactiveStreamsConsumer;
import org.springframework.integration.endpoint.SourcePollingChannelAdapter;
import org.springframework.integration.test.mock.MockMessageHandler;
import org.springframework.integration.test.util.TestUtils;
@@ -38,6 +39,9 @@ import org.springframework.messaging.MessageHandler;
import org.springframework.util.Assert;
import org.springframework.util.ObjectUtils;
import reactor.util.function.Tuple2;
import reactor.util.function.Tuples;
/**
* A {@link BeanFactoryAware} component with an API to customize real beans
* in the application context from test code.
@@ -91,10 +95,17 @@ public class MockIntegrationContext implements BeanFactoryAware {
if (endpoint instanceof SourcePollingChannelAdapter) {
directFieldAccessor.setPropertyValue("source", e.getValue());
}
else if (endpoint instanceof ReactiveStreamsConsumer) {
Tuple2<?, ?> value = (Tuple2<?, ?>) e.getValue();
directFieldAccessor.setPropertyValue("handler", value.getT1());
directFieldAccessor.setPropertyValue("subscriber", value.getT2());
}
else if (endpoint instanceof IntegrationConsumer) {
directFieldAccessor.setPropertyValue("handler", e.getValue());
}
});
this.beans.clear();
}
/**
@@ -137,7 +148,13 @@ public class MockIntegrationContext implements BeanFactoryAware {
}
DirectFieldAccessor directFieldAccessor = new DirectFieldAccessor(endpoint);
Object targetMessageHandler = directFieldAccessor.getPropertyValue("handler");
this.beans.put(consumerEndpointId, targetMessageHandler);
if (endpoint instanceof ReactiveStreamsConsumer) {
Object targetSubscriber = directFieldAccessor.getPropertyValue("subscriber");
this.beans.put(consumerEndpointId, Tuples.of(targetMessageHandler, targetSubscriber));
}
else {
this.beans.put(consumerEndpointId, targetMessageHandler);
}
if (mockMessageHandler instanceof MessageProducer) {
if (targetMessageHandler instanceof MessageProducer) {
@@ -160,6 +177,10 @@ public class MockIntegrationContext implements BeanFactoryAware {
directFieldAccessor.setPropertyValue("handler", mockMessageHandler);
if (endpoint instanceof ReactiveStreamsConsumer) {
directFieldAccessor.setPropertyValue("subscriber", mockMessageHandler);
}
if (autoStartup && endpoint instanceof Lifecycle) {
((Lifecycle) endpoint).start();
}

View File

@@ -20,6 +20,7 @@ import static org.hamcrest.Matchers.containsString;
import static org.hamcrest.Matchers.instanceOf;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNotSame;
import static org.junit.Assert.assertSame;
import static org.junit.Assert.assertThat;
import static org.junit.Assert.fail;
@@ -36,6 +37,7 @@ import org.junit.After;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.ArgumentCaptor;
import org.reactivestreams.Subscriber;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
@@ -46,7 +48,7 @@ import org.springframework.integration.annotation.ServiceActivator;
import org.springframework.integration.channel.DirectChannel;
import org.springframework.integration.channel.QueueChannel;
import org.springframework.integration.config.EnableIntegration;
import org.springframework.integration.endpoint.EventDrivenConsumer;
import org.springframework.integration.endpoint.ReactiveStreamsConsumer;
import org.springframework.integration.expression.ValueExpression;
import org.springframework.integration.handler.ExpressionEvaluatingMessageHandler;
import org.springframework.integration.support.MessageBuilder;
@@ -183,7 +185,8 @@ public class MockMessageHandlerTests {
ArgumentCaptor<Message<?>> messageArgumentCaptor = MockIntegration.messageArgumentCaptor();
MessageHandler mockMessageHandler =
spy(mockMessageHandler(messageArgumentCaptor))
.handleNext(m -> { });
.handleNext(m -> {
});
String endpointId = "rawHandlerConsumer";
this.mockIntegrationContext.substituteMessageHandlerFor(endpointId, mockMessageHandler);
@@ -214,6 +217,11 @@ public class MockMessageHandlerTests {
assertThat(e, instanceOf(IllegalStateException.class));
assertThat(e.getMessage(), containsString("with replies can't replace simple MessageHandler"));
}
this.mockIntegrationContext.resetBeans();
assertNotSame(mockMessageHandler, TestUtils.getPropertyValue(endpoint, "handler", MessageHandler.class));
assertNotSame(mockMessageHandler, TestUtils.getPropertyValue(endpoint, "subscriber", Subscriber.class));
}
/**
@@ -272,9 +280,9 @@ public class MockMessageHandlerTests {
}
@Bean
public EventDrivenConsumer rawHandlerConsumer() {
return new EventDrivenConsumer(rawChannel(),
new ExpressionEvaluatingMessageHandler(new ValueExpression<>("test")));
public ReactiveStreamsConsumer rawHandlerConsumer() {
return new ReactiveStreamsConsumer(rawChannel(),
(MessageHandler) new ExpressionEvaluatingMessageHandler(new ValueExpression<>("test")));
}
@ServiceActivator(inputChannel = "startChannel", outputChannel = "nextChannel")
@@ -291,7 +299,8 @@ public class MockMessageHandlerTests {
@ServiceActivator(inputChannel = "nextChannel")
public MessageHandler handleNextInput() {
return mockMessageHandler(argumentCaptorForOutputTest())
.handleNext(m -> { });
.handleNext(m -> {
});
}
}