Sep 18th, 2012, 12:50 PM
Unit Testing recommendations?
We're just getting into SI and currently have a configuration that
1) starts with a variety of different file-inbound-channel-adapters (one for each regex pattern) and uses comparators
2) creates a Spring Batch "job request" (as describe in the spring-batch-integration checkout) using a service activator
3) Calls our batch jobs
4) continues with a file outbound gateway to move the file when down
5) ends with another service activator to call a database cleanup dao method.
For (junit) unit testing, our first instincts are to do both integration testing (start with file, trigger entire flow, then check output file and database), but also unit testing. What's your favorite way to accomplish unit testing with a multi-step flow?
One idea is to change our channel definitions isn test/resources so that every channel was a PollableChannel (with <queue />) instead of a DirectChannel. The initial assumption was that we could just call .receive(timeout) but an initial test led to unexpected results. Another idea was to mimic an approach in the SI samples where we configure bridge channels in test/resources and then check those for output, but I guess I have a broader question on if anyone has devised another method to make SI unit testing simpler, with a minimum of altered configuration. I'm curious what general approach other teams follow for unit-testing SI.
Oct 2nd, 2012, 07:28 AM
One approach we found works decently is to use Spring profiles. Unfortunately, you can only use Spring profiles with the latest milestone release of Spring Integration, which is 2.2.0-RC1. The technique we used was to determine which pieces of the integration we wanted to unit test, and then we disconnected the channels between those two units of work. For instance, the output channel of the first unit of work did not match the input channel of the second unit of work. In a default profile we added bridges between these two disjoint channels. So by default, the integration would run all the way through. In a "test" profile we added queues that hooked up to the end of each unit of work in the flow. In our unit tests, we pulled the messages from the queues. If you can't use profiles, you can implement the same technique by splitting up the configuration files (e.g. spring-integration-main.xml, spring-integration-default.xml, and spring-integration-test.xml). In your unit tests, you can just load the test xml. For an end to end test, you can load the default.xml.
Hope that gives you some ideas.