我正在为一个隐藏最终用户的骆驼业务的库编写测试用例。 该库公开了诸如sendMessages()等方法,并在内部使用ProducerTemplate将消息发送到camel路由,在这些路由中它们被聚合并最终发送到目的地。
我希望能够编写调用库方法的测试并模拟camel路由端点以便稍后对其进行断言。
如果我使用CamelSpringTestSupport,它基本上会创建一个新的ClassPathXmlApplicationContext,使用它我可以测试路由。
但是我想测试在库的camel context中创建的端点,以及我测试覆盖库代码。
可以这样做吗?
答案 0 :(得分:3)
使用Camel的AdviceWith动态更改路由行为(拦截交换并发送到模拟端点进行验证等)......它非常灵活,可以利用熟悉的MockEndpoints等...
例如......拦截发送到direct:start
路径的消息
context.getRouteDefinition("myRouteId").adviceWith(context, new AdviceWithRouteBuilder() {
@Override
public void configure() throws Exception {
interceptSendToEndpoint("direct:start")
.skipSendToOriginalEndpoint()
.to("mock:start");
}
});
getMockEndpoint("mock:start").expectedBodiesReceived("Hello World");
答案 1 :(得分:0)
我的最终测试用例如下所示,其中现有的上下文路由被模拟。
import org.apache.camel.Exchange;
import org.apache.camel.builder.AdviceWithRouteBuilder;
import org.apache.camel.component.mock.MockEndpoint;
import org.apache.camel.test.spring.CamelSpringTestSupport;
import org.junit.Assert;
import org.junit.BeforeClass;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.context.support.AbstractApplicationContext;
import org.springframework.test.annotation.DirtiesContext;
import java.net.URL;
import java.nio.file.Paths;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class MyAppTest extends CamelSpringTestSupport {
private static MyApp myapp;
protected final Logger log = LoggerFactory.getLogger(MyAppTest.class);
@Override
protected AbstractApplicationContext createApplicationContext() {
return (AbstractApplicationContext) myApp.getContext();
}
@Override
public boolean isUseAdviceWith() {
// tell we are using advice with, which allows us to advice the route
// before Camel is being started, and thus can replace myApp Endpoint with something else.
return true;
}
@BeforeClass
public static void oneTimeSetUp() throws Exception {
myApp = new myApp();
}
@Test
@DirtiesContext
public void test01() throws Exception {
log.info("TEST: Going to apply advideWith clause to existing route");
context.getRouteDefinition("bulkIndexRoute").adviceWith(context, new AdviceWithRouteBuilder() {
@Override
public void configure() throws Exception {
weaveByToString(".*myAppEndpoint.*")
.replace()
.aggregate(header("ABC"), new ArrayListAggregationStrategy())
.completionSize(100)
.completionInterval(1000)
.to("mock:foo");
}
});
log.info("TEST: Done applying adviceWith Clause");
MockEndpoint mockedES = getMockEndpoint("mock:foo");
mockedES.expectedMessageCount(2);
mockedES.setAssertPeriod(10000);
// Create 150 test documents and index them
for(int i = 0; i < 150; i++) {
Map<String, String> d = new HashMap<String, String>();
d.put("key1", "value" + i);
d.put("key2", "value" + i);
myApp.send("param1", "param2", d);
}
mockedES.assertIsSatisfied();
int count = 0;
for(Exchange ex : mockedES.getExchanges()){
List<Map<String, Object>> documentList = ex.getIn().getBody(List.class);
count += documentList.size();
}
Assert.assertEquals("Received back 150 message", 150, count);
}
}
MyApp类将上下文返回给测试,以便可以模拟运行上下文中的路由。