DEV Community

André Moriya
André Moriya

Posted on

Apache camel: Xml file to JSON file.

Hi there,

I started learning Apache Camel a few days ago and was having difficulty with this simple case: Creating a JSON file from an XML file.

Problem 1: Old version

I picked up a project from a course I was taking. And the version used in this course was out of date. The course was using the dependency 'camel-xmljson,' which has since been removed in the new version.

Upgrading project

So I've decided to upgrade project to use Java 17 and apache camel version 3.18.0.

To do this, I've needed to import new dependencies on project:

<dependency>
    <groupId>org.apache.camel</groupId>
    <artifactId>camel-jaxb</artifactId>
    <version>${camel-version}</version>
</dependency>
<dependency>
    <groupId>org.apache.camel</groupId>
    <artifactId>camel-jackson</artifactId>
    <version>${camel-version}</version>
</dependency>
<dependency>
    <groupId>org.apache.camel</groupId>
    <artifactId>camel-jacksonxml</artifactId>
    <version>${camel-version}</version>
</dependency>
Enter fullscreen mode Exit fullscreen mode

Refactoring the code

After import the new dependencies, I needed to refactor my code.

Before refactoring

The code was as follows:

public static void main(String[] args) throws Exception {

        CamelContext context = new DefaultCamelContext();
        context.addRoutes(new RouteBuilder() {

            @Override
            public void configure() throws Exception {

                from("file:pedidos?delay=5s&noop=true").
                    split().
                        xpath("/pedido/itens/item").
                    filter().
                        xpath("/item/formato[text()='EBOOK']").
                    marshal().xmljson().
                    log("${id} - ${body}").
                    setHeader(Exchange.FILE_NAME, simple("${file:name.noext}-${header.CamelSplitIndex}.json")).
                to("file:saida");
            }

        });

        context.start();
        Thread.sleep(20000);
        context.stop();
    }
Enter fullscreen mode Exit fullscreen mode

After refactoring

And now I needed to do this:

public static void main(String[] args) throws Exception {

        try (CamelContext context = new DefaultCamelContext()) {
            JacksonDataFormat jacksonDataFormat = new JacksonDataFormat();
            jacksonDataFormat.setPrettyPrint(true);
            jacksonDataFormat.enableFeature(SerializationFeature.WRAP_ROOT_VALUE);

            context.addRoutes(new RouteBuilder() {

                @Override
                public void configure() throws Exception {

                    from("file:input?delay=5s&noop=true")
                        .filter()
                            .xpath("/pedido/itens/item/formato[text()='EBOOK']")
                        .unmarshal().jacksonXml(Pedido.class)
                        .marshal(jacksonDataFormat)
                        .setHeader(Exchange.FILE_NAME, simple("${file:name.noext}.json"))
                        .to("file:output");
                }

            });

            context.start();
            Thread.sleep(20000);
            context.stop();
        }
    }
Enter fullscreen mode Exit fullscreen mode

I needed to use some jackson annotations in "Pedido.java":

import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty;
import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlRootElement;

@JacksonXmlRootElement(localName = "pedido")
public class Pedido {

    @JacksonXmlProperty(localName = "id")
    private String id;
    @JacksonXmlProperty(localName = "dataCompra")
    private String dataCompra;
    @JacksonXmlProperty(localName = "itens")
    private Itens itens;
    @JacksonXmlProperty(localName = "pagamento")
    private Pagamento pagamento;

....
// getters and setters

Enter fullscreen mode Exit fullscreen mode

Note that 'Before refactoring,' I only needed to use'marshal().xmljson(),' and 'After refactoring,' I needed to do the following:

JacksonDataFormat jacksonDataFormat = new JacksonDataFormat();
jacksonDataFormat.setPrettyPrint(true);
jacksonDataFormat.enableFeature(SerializationFeature.WRAP_ROOT_VALUE);

.unmarshal().jacksonXml(Pedido.class)
.marshal(jacksonDataFormat)
Enter fullscreen mode Exit fullscreen mode

Conclusion

Well, this was the solution I discovered.

I know, there must be a better method, and if you know, left your comment and help me improve. :D

Thank you very much and see you!

Top comments (4)

Collapse
 
j_a_o_v_c_t_r profile image
João Victor Martins

Thank you for sharing your knowledge, Andre. I've never worked with camel, but I know that is an excellent resource.

Collapse
 
andremoriya profile image
André Moriya

Hi João, thanks man.

Me too. I've never worked too. I'm learning in my new challenge.

Collapse
 
dearrudam profile image
Maximillian Arruda • Edited

Great article, André 👏👏👏 Congratulations!!! I miss talking to you, my friend!!! It's been a long time since we chatted!!! I'll DM you soon!!! See ya!!!

Collapse
 
andremoriya profile image
André Moriya

Hi Max, thanks man.
I miss talking to you too, lets talk again :D.
I will send a message.
See ya