简体   繁体   中英

Camel and JAXB: Dynamic contextPath using simple()

I have a route where I have a list of XML files as input which I want to unmarshal and process through JAXB.

This is what I added to my route:

.unmarshal().jaxb("foo.bar.camel.xmlbeans.CLIENTID")

This is working as expected but I need the CLIENTID property to be dynamic. The information is contained inside the message header so I tried this:

.unmarshal().jaxb("foo.bar.camel.xmlbeans." + simple("${client.clientId}"))

This is not working as simple() returns a SimpleBuilder and I have no solution to get the actual value... I wanted to use .evaluate(exchange, type) but I can't find how to access the exchange from within the route.

How would I be able to achieve that?

You have to be careful what logic is applied when constructing the route and what logic is applied when an exchange is routed. The confusing thing is that there are two levels of abstraction, two languages - Java and Camel DSL on top of each other.

In your case, your java runtime is trying to evaluate String + SimpleBuilder when the construction java is run.

I don't think there is a construct in Camel providing dynamic JAXB contexts from an exchange parameter. That would be bad for performance to start with, and you have a limited set of classes loaded on your classpath anyway.

I can think of a couple of possible ways to handle this:

  1. Multiple package names in the context. Specify jaxb("org.package1:org.package2:foo.bar") - then jaxb hopefully finds the right class to unmarshal without further logic.

  2. If you by some reason want multiple (but limited amount of) contexts you can create multiple with DataFormat jaxb1 = new JaxbDataFormat("foo.bar:bar.foo"); and then use a choice in camel to use the right jaxb dataformat.

  3. If you really really want to create the context dynamically in runtime (might hurt your performance more than you want), you can easily do this in a simple java processor with a few lines of code.

    public class Proc implements Processor { public void process(Exchange exchange) throws Exception { String clientId = exchange.getIn().getHeader("clientid"); JAXBContext jaxb = JAXBContext.newInstance("foo.bar."+ clientId); Unmarshaller unmarshaller = jaxb.createUnmarshaller(); InputStream input = exchange.getIn(InputStream.class); exchange.getIn().setBody(unmarshaller.unmarshal(input)); } }

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM