By kswaughs | Tuesday, September 13, 2016

Camel SQL Stored Example

Camel SQL Stored Component is used to call stored procedures.

As a developer, You have to write only a mapper class to transform input/output parameters to your pojo class.

In this example, we will see how to use this component to call stored procedures using an embedded derby database.

Step 1: DataSource Setup

db-schema.sql
CREATE TABLE books (
  BookId VARCHAR(10) NOT NULL,
  BookName VARCHAR(100) NOT NULL,
  author VARCHAR(50) NOT NULL,
  price VARCHAR(20),
  CreateDate VARCHAR(50) NOT NULL
);

// Inserting two books data
INSERT INTO books(BookId, BookName, Author, Price, CreateDate) VALUES 
('FICT3', 'The Ruins', 'Scott Smith', '$9', 'July 18, 2006');
INSERT INTO books(BookId, BookName, Author, Price, CreateDate) VALUES 
('FICT4', 'Velocity', 'Dean Koontz', '$11', 'July 20, 2006');

// Stored procedure to fetch all books
CREATE PROCEDURE GET_ALL_BOOKS() PARAMETER STYLE JAVA LANGUAGE JAVA MODIFIES SQL DATA DYNAMIC RESULT SETS 1 EXTERNAL NAME 'com.kswaughs.db.util.BookStoredProcedure.findAllBooks';

// Stored procedure to fetch requested book
CREATE PROCEDURE GET_BOOK(IN book_name VARCHAR(100)) PARAMETER STYLE JAVA LANGUAGE JAVA MODIFIES SQL DATA DYNAMIC RESULT SETS 1 EXTERNAL NAME 'com.kswaughs.db.util.BookStoredProcedure.findBook';

Stored procedure implementation class is BookStoredProcedure. This is Apache Derby's way of implementation, purely written in Java. This has nothing to do with camel.

BookStoredProcedure.java
package com.kswaughs.db.util;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;

import org.springframework.jdbc.support.JdbcUtils;

public class BookStoredProcedure {

    /**
     * Derby Stored Procedure implementation to read all books 
     * @param bookResults
     * @throws SQLException
     */
    public static void findAllBooks(ResultSet[] bookResults)
            throws SQLException {

        Connection connection = null;
        PreparedStatement statement = null;

        try {
            connection = DriverManager.getConnection("jdbc:default:connection");
            String sql = "select * from books";
            statement = connection.prepareStatement(sql);
            bookResults[0] = statement.executeQuery();
        } finally {
            
            JdbcUtils.closeConnection(connection);
        }

    }
    
    /**
     * Derby Stored Procedure implementation to read requested book
     * @param bookResults
     * @throws SQLException
     */
    public static void findBook(String book_name, ResultSet[] bookResults)
            throws SQLException {

        Connection connection = null;
        PreparedStatement statement = null;

        try {
            connection = DriverManager.getConnection("jdbc:default:connection");
            
            String query = "select * from books where BookName = ?";
                
            statement = connection.prepareStatement(query);
            statement.setString(1, book_name);
            
            bookResults[0] = statement.executeQuery();
        } finally {
            
            JdbcUtils.closeConnection(connection);
        }
    }
}

Step 2: Application Context Configuration

database-context.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:jdbc="http://www.springframework.org/schema/jdbc" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:cxf="http://camel.apache.org/schema/cxf" 
    xmlns:jaxrs="http://cxf.apache.org/jaxrs"
    xmlns:context="http://www.springframework.org/schema/context"
    xsi:schemaLocation="
       http://www.springframework.org/schema/beans
       http://www.springframework.org/schema/beans/spring-beans.xsd
       http://camel.apache.org/schema/cxf
       http://camel.apache.org/schema/cxf/camel-cxf.xsd 
       http://cxf.apache.org/jaxrs
       http://cxf.apache.org/schemas/jaxrs.xsd
       http://www.springframework.org/schema/jdbc 
       http://www.springframework.org/schema/jdbc/spring-jdbc-3.0.xsd
       http://camel.apache.org/schema/spring
       http://camel.apache.org/schema/spring/camel-spring.xsd
       http://www.springframework.org/schema/context 
       http://www.springframework.org/schema/context/spring-context.xsd ">

    <!-- this is the JDBC data source which uses an in-memory only Apache Derby database -->
    <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"
        destroy-method="close">
        <property name="driverClassName" value="org.apache.derby.jdbc.EmbeddedDriver" />
        <property name="url" value="jdbc:derby:memory:orders;create=true" />
        <property name="username" value="" />
        <property name="password" value="" />
    </bean>

    <jdbc:initialize-database data-source="dataSource" enabled="true">
        <jdbc:script location="classpath:db-schema.sql" />
    </jdbc:initialize-database>

    <!-- configure the Camel SQL Stored component to use the JDBC data source -->
     <bean id="sqlStored" class="org.apache.camel.component.sql.stored.SqlStoredComponent">
        <property name="dataSource" ref="dataSource" />
    </bean>

    <bean id="bookMapper" class="com.kswaughs.db.util.BookMapper" />

    <bean id="bookRouter" class="com.kswaughs.router.BookRouter" />
    
    <camelContext id="bookCtx" xmlns="http://camel.apache.org/schema/spring">
    
        <routeBuilder ref="bookRouter" />

    </camelContext>

</beans>

Step 3: Define Routers for calling two stored procedures using Java DSL

BookRouter.java
package com.kswaughs.router;

import org.apache.camel.builder.RouteBuilder;

public class BookRouter extends RouteBuilder {

    @Override
    public void configure() throws Exception {
        
         from("direct:sp")
            .to("sqlStored:GET_ALL_BOOKS()")
            .bean("bookMapper", "readAllBooks")
            .log("${body}");
        
        from("direct:sp-getbook")
            .bean("bookMapper", "buildReqMap")
            .to("sqlStored:GET_BOOK(VARCHAR :#BookName)")
            .bean("bookMapper", "readAllBooks")
            .log("${body}");
    }

}

Step 4: Create POJO class & Row mapper class

Book.java
package com.kswaughs.beans;

public class Book {
    
    private String bookId;
    private String bookName;
    private String author;
    private String price;
    private String createDate;
    
    public String getBookId() {
        return bookId;
    }
    
    public void setBookId(String bookId) {
        this.bookId = bookId;
    }
    
    public String getBookName() {
        return bookName;
    }
    
    public void setBookName(String bookName) {
        this.bookName = bookName;
    }
    
    public String getAuthor() {
        return author;
    }
    
    public void setAuthor(String author) {
        this.author = author;
    }
    
    public String getPrice() {
        return price;
    }
    public void setPrice(String price) {
        this.price = price;
    }
    
    public String getCreateDate() {
        return createDate;
    }
    
    public void setCreateDate(String createDate) {
        this.createDate = createDate;
    }

    @Override
    public String toString() {
        StringBuilder builder = new StringBuilder();
        builder.append("Book [bookId=");
        builder.append(bookId);
        builder.append(", bookName=");
        builder.append(bookName);
        builder.append(", author=");
        builder.append(author);
        builder.append(", price=");
        builder.append(price);
        builder.append(", createDate=");
        builder.append(createDate);
        builder.append("]");
        return builder.toString();
    }
}

BookMapper.java
package com.kswaughs.db.util;

import com.kswaughs.beans.Book;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class BookMapper {
    
    /**
     * Transforms input request to request map
     * @param bookName
     * @return
     */
    public Map<String, Object> buildReqMap(String bookName) {
        Map<String, Object> answer = new HashMap<String, Object>();
        answer.put("BookName", bookName);
        return answer;
    }

        /**
     * Transforms Resultsets into List of Books objects
     * @param resultSets
     * @return
     * @throws Exception
     */
    public List<Book> readAllBooks(Map<String, List<Map<String, String>>> resultSets) 
        throws Exception {
          
        List<Book> books = new ArrayList<Book>();
      
        System.out.println("resultSets:"+resultSets);
        
        Set<String>  keys = resultSets.keySet();
        
        for (String key : keys) {
           
           List<Map<String, String>> rsts = resultSets.get(key);
           
           for (Map<String, String>  rst: rsts) {
            
                Book book = new Book();
                
                book.setBookId(rst.get("BookId"));
                book.setBookName(rst.get("BookName"));
                book.setAuthor(rst.get("Author"));
                book.setPrice(rst.get("Price"));
                book.setCreateDate(rst.get("CreateDate"));
                
                books.add(book);
            }
         }
        
      return books;
    }
}

Step 5: Test the application

CamelBookApp.java
package com.kswaughs.app;

import com.kswaughs.beans.Book;

import java.util.Date;
import java.util.List;

import org.apache.camel.CamelContext;
import org.apache.camel.ProducerTemplate;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

import com.kswaughs.db.util.Book;

public class CamelBookApp {

    public static void main(String[] args) {

        try {
            ApplicationContext springCtx = new ClassPathXmlApplicationContext(
                    "database-context.xml");

            CamelContext context = springCtx.getBean("bookCtx", CamelContext.class);
            
            context.start();
        
            ProducerTemplate producerTemplate = context.createProducerTemplate();
            
             // Fetch all books
            List<Book> resp = producerTemplate.requestBody("direct:sp",  null, List.class);
            System.out.println("SP resp:"+resp);
            
            // Fetch book by name
            List<Book> resp1 = producerTemplate
                 .requestBody("direct:sp-getbook",  "Velocity", List.class);
            System.out.println("SP resp1:"+resp1);
       
        } catch (Exception e) {
          
            e.printStackTrace();
        } 
    }
 
}

Console Logs

 
resultSets:{#result-set-1=[{BOOKID=FICT3, BOOKNAME=The Ruins, AUTHOR=Scott Smith, PRICE=$9, CREATEDATE=July 18, 2006}, {BOOKID=FICT4, BOOKNAME=Velocity, AUTHOR=Dean Koontz, PRICE=$11, CREATEDATE=July 20, 2006}]}
INFO|09/13/2016 11:39:18 980|[Book [bookId=FICT3, bookName=The Ruins, author=Scott Smith, price=$9, createDate=July 18, 2006], Book [bookId=FICT4, bookName=Velocity, author=Dean Koontz, price=$11, createDate=July 20, 2006]]
SP resp:[Book [bookId=FICT3, bookName=The Ruins, author=Scott Smith, price=$9, createDate=July 18, 2006], Book [bookId=FICT4, bookName=Velocity, author=Dean Koontz, price=$11, createDate=July 20, 2006]]
resultSets:{#result-set-1=[{BOOKID=FICT4, BOOKNAME=Velocity, AUTHOR=Dean Koontz, PRICE=$11, CREATEDATE=July 20, 2006}]}
INFO|09/13/2016 11:39:19 000|[Book [bookId=FICT4, bookName=Velocity, author=Dean Koontz, price=$11, createDate=July 20, 2006]]
SP resp1:[Book [bookId=FICT4, bookName=Velocity, author=Dean Koontz, price=$11, createDate=July 20, 2006]]

Maven dependencies

pom.xml
<properties>
    <spring.version>4.1.6.RELEASE</spring.version>
    <camelspring.version>2.16.0</camelspring.version>  
</properties>
    
<dependencies>
    <!-- Camel Dependencies -->
    <dependency>
        <groupId>org.apache.camel</groupId>
        <artifactId>camel-core</artifactId>
        <version>${camelspring.version}</version>
    </dependency>
     <dependency>
        <groupId>org.apache.camel</groupId>
        <artifactId>camel-cxf</artifactId>
        <version>${camelspring.version}</version>
    </dependency> 
    <dependency>
        <groupId>org.apache.camel</groupId>
        <artifactId>camel-spring</artifactId>
        <version>${camelspring.version}</version>
    </dependency>
    <dependency>
        <groupId>org.apache.camel</groupId>
        <artifactId>camel-sql</artifactId>
        <version>2.17.1</version>
    </dependency>
    <!-- End of Camel Dependencies -->

    <dependency>
        <groupId>commons-dbcp</groupId>
        <artifactId>commons-dbcp</artifactId>
        <version>1.2.2</version>
    </dependency>

    <dependency>
        <groupId>commons-pool</groupId>
        <artifactId>commons-pool</artifactId>
        <version>1.6</version>
    </dependency>
    <dependency>
        <groupId>org.apache.derby</groupId>
        <artifactId>derby</artifactId>
        <version>10.11.1.1</version>
    </dependency>
    
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-core</artifactId>
        <version>${spring.version}</version>
    </dependency>    
</dependencies>

Recommend this on


By kswaughs | Tuesday, August 30, 2016

Camel SQL Component Example

Camel SQL Component is used to perform database operations using JDBC queries.

As a developer, You have to write only a mapper class to transform input/output parameters to your pojo class.

In this example, we will see how to use this component for insert and read books from an embedded derby database.

Step 1: DataSource Setup

db-schema.sql
CREATE TABLE books (
  BookId VARCHAR(10) NOT NULL,
  BookName VARCHAR(100) NOT NULL,
  author VARCHAR(50) NOT NULL,
  price VARCHAR(20),
  CreateDate VARCHAR(50) NOT NULL
);

Step 2: Externalize the sql queries in a file

sql.properties

sql.insertBook=INSERT INTO books(BookId, BookName, Author, Price, CreateDate) VALUES (:#BookId, :#BookName, :#Author, :#Price, :#CreateDate)

sql.getAllBooks=select * from books

Step 3: Application Context Configuration

database-context.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:jdbc="http://www.springframework.org/schema/jdbc" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:cxf="http://camel.apache.org/schema/cxf" 
    xmlns:jaxrs="http://cxf.apache.org/jaxrs"
    xmlns:context="http://www.springframework.org/schema/context"
    xsi:schemaLocation="
       http://www.springframework.org/schema/beans
       http://www.springframework.org/schema/beans/spring-beans.xsd
       http://camel.apache.org/schema/cxf
       http://camel.apache.org/schema/cxf/camel-cxf.xsd 
       http://cxf.apache.org/jaxrs
       http://cxf.apache.org/schemas/jaxrs.xsd
       http://www.springframework.org/schema/jdbc 
       http://www.springframework.org/schema/jdbc/spring-jdbc-3.0.xsd
       http://camel.apache.org/schema/spring
       http://camel.apache.org/schema/spring/camel-spring.xsd
       http://www.springframework.org/schema/context 
       http://www.springframework.org/schema/context/spring-context.xsd ">

    <!-- this is the JDBC data source which uses an in-memory only Apache Derby database -->
    <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"
        destroy-method="close">
        <property name="driverClassName" value="org.apache.derby.jdbc.EmbeddedDriver" />
        <property name="url" value="jdbc:derby:memory:orders;create=true" />
        <property name="username" value="" />
        <property name="password" value="" />
    </bean>

    <jdbc:initialize-database data-source="dataSource" enabled="true">
        <jdbc:script location="classpath:db-schema.sql" />
    </jdbc:initialize-database>

    <!-- configure the Camel SQL component to use the JDBC data source -->
    <bean id="sqlComponent" class="org.apache.camel.component.sql.SqlComponent">
        <property name="dataSource" ref="dataSource" />
    </bean>

    <bean id="bookMapper" class="com.kswaughs.db.util.BookMapper" />

    <bean id="bookRouter" class="com.kswaughs.router.BookRouter" />
    
    <camelContext id="bookCtx" xmlns="http://camel.apache.org/schema/spring">
    
        <!-- use Camel property placeholder loaded from the given file -->
        <propertyPlaceholder id="placeholder" location="classpath:sql.properties" />

        <routeBuilder ref="bookRouter" />

    </camelContext>

</beans>

Step 4: Define Routers for Insert & Read using Java DSL

BookRouter.java
package com.kswaughs.router;

import org.apache.camel.builder.RouteBuilder;

public class BookRouter extends RouteBuilder {

    @Override
    public void configure() throws Exception {
        
        from("direct:insert")
            .log("Inserted new Book")
            .bean("bookMapper", "getMap")
            .to("sqlComponent:{{sql.insertBook}}");
    
        from("direct:select")
            .to("sqlComponent:{{sql.getAllBooks}}")
            .bean("bookMapper", "readBooks")
            .log("${body}");
    }

}

If you want to configure routes using spring DSL, replace camelContext section from database-context.xml with below configuration.

<camelContext id="bookCtx" xmlns="http://camel.apache.org/schema/spring">

        <!-- use Camel property placeholder loaded from the given file -->
        <propertyPlaceholder id="placeholder" location="classpath:sql.properties" />

        <!-- route that generate new orders and insert them in the database -->
        <route id="insertBook-route">
            <from uri="direct:insert" />
            <log message="Inserted new Book" />
            <transform>
                <method ref="bookMapper" method="getMap" />
            </transform>
            <to uri="sqlComponent:{{sql.insertBook}}" />
        </route>

        <route id="getAllBooks-route">
            <from uri="direct:select" />
            <to uri="sqlComponent:{{sql.getAllBooks}}" />
            <to uri="bean:bookMapper?method=readBooks" />
            <log message="${body}" />
        </route>

</camelContext>

Step 5: Create POJO class & Row mapper class

Book.java
package com.kswaughs.beans;

public class Book {
    
    private String bookId;
    private String bookName;
    private String author;
    private String price;
    private String createDate;
    
    public String getBookId() {
        return bookId;
    }
    
    public void setBookId(String bookId) {
        this.bookId = bookId;
    }
    
    public String getBookName() {
        return bookName;
    }
    
    public void setBookName(String bookName) {
        this.bookName = bookName;
    }
    
    public String getAuthor() {
        return author;
    }
    
    public void setAuthor(String author) {
        this.author = author;
    }
    
    public String getPrice() {
        return price;
    }
    public void setPrice(String price) {
        this.price = price;
    }
    
    public String getCreateDate() {
        return createDate;
    }
    
    public void setCreateDate(String createDate) {
        this.createDate = createDate;
    }

    @Override
    public String toString() {
        StringBuilder builder = new StringBuilder();
        builder.append("Book [bookId=");
        builder.append(bookId);
        builder.append(", bookName=");
        builder.append(bookName);
        builder.append(", author=");
        builder.append(author);
        builder.append(", price=");
        builder.append(price);
        builder.append(", createDate=");
        builder.append(createDate);
        builder.append("]");
        return builder.toString();
    }
}

BookMapper.java
package com.kswaughs.db.util;

import com.kswaughs.beans.Book;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class BookMapper {
    
    public Map<String, Object> getMap(Book book) {
        Map<String, Object> answer = new HashMap<String, Object>();
        answer.put("BookId", book.getBookId());
        answer.put("BookName", book.getBookName());
        answer.put("Author", book.getAuthor() );
        answer.put("Price", book.getPrice());
        answer.put("CreateDate", book.getCreateDate());
        return answer;
    }

   public List<Book> readBooks( List<Map<String, String>>  dataList) {
        
        System.out.println("data:"+dataList);
        
        List<Book> books = new ArrayList<Book>();
        
        for (Map<String, String> data : dataList) {
              
            Book book = new Book();
            
            book.setBookId(data.get("BookId"));
            book.setBookName(data.get("BookName"));
            book.setAuthor(data.get("Author"));
            book.setPrice(data.get("Price"));
            book.setCreateDate(data.get("CreateDate"));
            
            books.add(book);
        }
        
       return books;
    }
}

Step 6: Test the application

CamelBookApp.java
package com.kswaughs.app;

import com.kswaughs.beans.Book;

import java.util.Date;
import java.util.List;

import org.apache.camel.CamelContext;
import org.apache.camel.ProducerTemplate;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

import com.kswaughs.db.util.Book;

public class CamelBookApp {

    public static void main(String[] args) {

        try {
            ApplicationContext springCtx = new ClassPathXmlApplicationContext(
                    "database-context.xml");

            CamelContext context = springCtx.getBean("bookCtx", CamelContext.class);
            
            context.start();
        
            ProducerTemplate producerTemplate = context.createProducerTemplate();
            
            // Insert book 1
            Book book1 = buildBook1();
            String resp = producerTemplate.requestBody("direct:insert",  book1, String.class);
            System.out.println("resp:"+resp);
            
            // Insert book 2
            Book book2 = buildBook2();
            resp = producerTemplate.requestBody("direct:insert",  book2, String.class);
            System.out.println("resp:"+resp);
            
            // Read all books
            List<Book> resp1 = producerTemplate
                     .requestBody("direct:select",  null, List.class);
            System.out.println("resp1:"+resp1);
        
        } catch (Exception e) {
            
            e.printStackTrace();
        
        } 
    }
    
    private static Book buildBook1() {
        
        Book book = new Book();
        
        book.setBookId("FICT1");
        book.setBookName("Rogue Lawyer");
        book.setAuthor("John Grisham");
        book.setPrice("$10");
        book.setCreateDate(new Date().toString());
        return book;
        
    }

    private static Book buildBook2() {
        
        Book book = new Book();
        
        book.setBookId("FICT2");
        book.setBookName("Doctor Sleep");
        book.setAuthor("Stephen King");
        book.setPrice("$9");
        book.setCreateDate(new Date().toString());
        return book;
        
    }
}

Console Logs

 
INFO|08/30/2016 11:05:26 918|Refreshing org.springframework.context.support.ClassPathXmlApplicationContext@67fc85d: startup date [Tue Aug 30 11:05:26 IST 2016]; root of context hierarchy
INFO|08/30/2016 11:05:26 966|Loading XML bean definitions from class path resource [database-context.xml]
INFO|08/30/2016 11:05:29 385|Executing SQL script from class path resource [db-schema.sql]
INFO|08/30/2016 11:05:29 529|Executed SQL script from class path resource [db-schema.sql] in 144 ms.
INFO|08/30/2016 11:05:29 806|Apache Camel 2.16.0 (CamelContext: bookCtx) is starting
INFO|08/30/2016 11:05:29 807|JMX is enabled
INFO|08/30/2016 11:05:29 961|Loaded 198 type converters
INFO|08/30/2016 11:05:30 005|Runtime endpoint registry is in extended mode gathering usage statistics of all incoming and outgoing endpoints (cache limit: 1000)
INFO|08/30/2016 11:05:30 127|AllowUseOriginalMessage is enabled. If access to the original message is not needed, then its recommended to turn this option off as it may improve performance.
INFO|08/30/2016 11:05:30 127|StreamCaching is not in use. If using streams then its recommended to enable stream caching. See more details at http://camel.apache.org/stream-caching.html
INFO|08/30/2016 11:05:30 211|Route: route1 started and consuming from: Endpoint[direct://insert]
INFO|08/30/2016 11:05:30 213|Route: route2 started and consuming from: Endpoint[direct://select]
INFO|08/30/2016 11:05:30 213|Total 2 routes, of which 2 is started.
INFO|08/30/2016 11:05:30 214|Apache Camel 2.16.0 (CamelContext: bookCtx) started in 0.408 seconds
INFO|08/30/2016 11:05:30 217|Apache Camel 2.16.0 (CamelContext: bookCtx) is starting
INFO|08/30/2016 11:05:30 217|Total 2 routes, of which 2 is started.
INFO|08/30/2016 11:05:30 217|Apache Camel 2.16.0 (CamelContext: bookCtx) started in 0.000 seconds
INFO|08/30/2016 11:05:30 228|Inserted new Book
resp:{BookName=Rogue Lawyer, Price=$10, Author=John Grisham, BookId=FICT1, CreateDate=Tue Aug 30 11:05:30 IST 2016}
INFO|08/30/2016 11:05:30 297|Inserted new Book
resp:{BookName=Doctor Sleep, Price=$9, Author=Stephen King, BookId=FICT2, CreateDate=Tue Aug 30 11:05:30 IST 2016}
data:[{BOOKID=FICT1, BOOKNAME=Rogue Lawyer, AUTHOR=John Grisham, PRICE=$10, CREATEDATE=Tue Aug 30 11:05:30 IST 2016}, {BOOKID=FICT2, BOOKNAME=Doctor Sleep, AUTHOR=Stephen King, PRICE=$9, CREATEDATE=Tue Aug 30 11:05:30 IST 2016}]
INFO|08/30/2016 11:05:30 328|[Book [bookId=FICT1, bookName=Rogue Lawyer, author=John Grisham, price=$10, createDate=Tue Aug 30 11:05:30 IST 2016], Book [bookId=FICT2, bookName=Doctor Sleep, author=Stephen King, price=$9, createDate=Tue Aug 30 11:05:30 IST 2016]]
resp1:[Book [bookId=FICT1, bookName=Rogue Lawyer, author=John Grisham, price=$10, createDate=Tue Aug 30 11:05:30 IST 2016], Book [bookId=FICT2, bookName=Doctor Sleep, author=Stephen King, price=$9, createDate=Tue Aug 30 11:05:30 IST 2016]]

Maven dependencies

pom.xml
<properties>
    <spring.version>4.1.6.RELEASE</spring.version>
    <camelspring.version>2.16.0</camelspring.version>  
</properties>
    
<dependencies>
    <!-- Camel Dependencies -->
    <dependency>
        <groupId>org.apache.camel</groupId>
        <artifactId>camel-core</artifactId>
        <version>${camelspring.version}</version>
    </dependency>
     <dependency>
        <groupId>org.apache.camel</groupId>
        <artifactId>camel-cxf</artifactId>
        <version>${camelspring.version}</version>
    </dependency> 
    <dependency>
        <groupId>org.apache.camel</groupId>
        <artifactId>camel-spring</artifactId>
        <version>${camelspring.version}</version>
    </dependency>
    <dependency>
        <groupId>org.apache.camel</groupId>
        <artifactId>camel-sql</artifactId>
        <version>2.17.1</version>
    </dependency>
    <!-- End of Camel Dependencies -->

    <dependency>
        <groupId>commons-dbcp</groupId>
        <artifactId>commons-dbcp</artifactId>
        <version>1.2.2</version>
    </dependency>

    <dependency>
        <groupId>commons-pool</groupId>
        <artifactId>commons-pool</artifactId>
        <version>1.6</version>
    </dependency>
    <dependency>
        <groupId>org.apache.derby</groupId>
        <artifactId>derby</artifactId>
        <version>10.11.1.1</version>
    </dependency>
    
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-core</artifactId>
        <version>${spring.version}</version>
    </dependency>    
</dependencies>

Recommend this on


By kswaughs | Friday, May 13, 2016

Camel Splitter Aggregator Example

What is a Splitter Aggregator Pattern ?

A Message is divided into small independent pieces and processed individually and then grouped all pieces and processed together.

In this example, We will create an order with two different types of items and will see how these items are processed individually to get price of each item and calculating the total price of all items of this order using aggregation strategy. We will see how the following business components involved in developing this application.

1. Item Processor component

2. Order Items Aggregator

3. Java DSL Router

4. Camel context Configuration

5. Data models

6. Test the Application 

Step 1 : Item Processor component

ItemSvc.java
package com.kswaughs.split;

import com.kswaughs.split.beans.Item;

public class ItemSvc {
    
    public Item processBook(Item item) throws InterruptedException {
        
        System.out.println("handle book Item:" +item);
        item.setPrice(30);
        
        System.out.println("book Item processed");
        
        return item;
    }

    public Item processPhone(Item item) throws InterruptedException {
        
        System.out.println("handle phone Item:" +item);
        item.setPrice(500);
        
        System.out.println("phone Item processed");
        
        return item;
    }
}

Step 2 : Order Items Aggregator

OrderItemStrategy.java
package com.kswaughs.split;

import java.util.ArrayList;
import java.util.List;

import org.apache.camel.Exchange;
import org.apache.camel.processor.aggregate.AggregationStrategy;

import com.kswaughs.split.beans.Item;
import com.kswaughs.split.beans.Order;

public class OrderItemStrategy implements AggregationStrategy {
    
    @Override
    public Exchange aggregate(Exchange oldExchange, Exchange newExchange) {
        
           if (oldExchange == null) {
               
               Item newItem= newExchange.getIn().getBody(Item.class);
               System.out.println("Aggregate first item: " + newItem);
               
               Order currentOrder = new Order();
               currentOrder.setId("ORD"+System.currentTimeMillis());
               List<Item> currentItems = new ArrayList<Item>();
   
               currentItems.add(newItem);
               currentOrder.setItems(currentItems);
               currentOrder.setTotalPrice(newItem.getPrice());
               
               newExchange.getIn().setBody(currentOrder);
               
                // the first time we aggregate we only have the new exchange,
                // so we just return it
                return newExchange;
            }
           
            Order order = oldExchange.getIn().getBody(Order.class);
            Item newItem= newExchange.getIn().getBody(Item.class);
     
            System.out.println("Aggregate old items: " + order);
            System.out.println("Aggregate new item: " + newItem);
            
            order.getItems().add(newItem);
           
            double totalPrice = order.getTotalPrice() + newItem.getPrice();
            order.setTotalPrice(totalPrice);

            // return old as this is the one that has all the orders gathered until now
            return oldExchange;
    }

}

Step 3 : Java DSL Router

OrderRouter.java
package com.kswaughs.split;

import org.apache.camel.builder.RouteBuilder;

public class OrderRouter extends RouteBuilder {

    @Override
    public void configure() throws Exception {
        
        from("direct:processOrder")
            .split(body().method("getItems"), new OrderItemStrategy())
            // each splitted message is send to this bean to process it
            .to("direct:processItem")
         .end();
    
        
        from("direct:processItem")
            .choice()
                .when(body().method("getType").isEqualTo("Book"))
                    .to("bean:itemService?method=processBook").
                otherwise()
                    .to("bean:itemService?method=processPhone");
    }

}

Step 4 : Camel context Configuration

camel-context.xml
<?xml version="1.0" encoding="UTF-8"?>

<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xmlns:cxf="http://camel.apache.org/schema/cxf"
    xmlns:jaxrs="http://cxf.apache.org/jaxrs" 
    xmlns:context="http://www.springframework.org/schema/context"
    xsi:schemaLocation="
        http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd
        http://camel.apache.org/schema/cxf
        http://camel.apache.org/schema/cxf/camel-cxf.xsd
        http://cxf.apache.org/jaxrs
        http://cxf.apache.org/schemas/jaxrs.xsd
        http://camel.apache.org/schema/spring
        http://camel.apache.org/schema/spring/camel-spring.xsd
        http://www.springframework.org/schema/context 
        http://www.springframework.org/schema/context/spring-context.xsd">


    <bean id="orderRouter" class="com.kswaughs.split.OrderRouter" />
    <bean id="itemService" class="com.kswaughs.split.ItemSvc" />
    <camelContext id="orderCtx" xmlns="http://camel.apache.org/schema/spring">
        <routeBuilder ref="orderRouter" />
    </camelContext>
    
</beans>

Step 5 : Data models

Data model of Item

Item.java
package com.kswaughs.split.beans;

public class Item {

    public Item(String id, String name, String type) {
        this.id = id;
        this.name = name;
        this.type = type;
    }

    private String id;

    private String name;
    
    private String type;

    private double price;

    public String getId() {
        return id;
    }

    public String getName() {
        return name;
    }

    public double getPrice() {
        return price;
    }

    public void setPrice(double price) {
        this.price = price;
    }
    
    public String getType() {
        return type;
    }

    @Override
    public String toString() {
        StringBuilder builder = new StringBuilder();
        builder.append("Item [id=");
        builder.append(id);
        builder.append(", name=");
        builder.append(name);
        builder.append(", type=");
        builder.append(type);
        builder.append(", price=");
        builder.append(price);
        builder.append("]");
        return builder.toString();
    }
    
}

Data model of Order

Order.java
package com.kswaughs.split.beans;

import java.util.List;

public class Order {
    
    private String id;
    
    private List items;
    
    private double totalPrice;
        
    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }

    public List getItems() {
        return items;
    }

    public void setItems(List items) {
        this.items = items;
    }    

    public double getTotalPrice() {
        return totalPrice;
    }

    public void setTotalPrice(double totalPrice) {
        this.totalPrice = totalPrice;
    }

    @Override
    public String toString() {
        StringBuilder builder = new StringBuilder();
        builder.append("Order [id=");
        builder.append(id);
        builder.append(", items=");
        builder.append(items);
        builder.append(", totalPrice=");
        builder.append(totalPrice);
        builder.append("]");
        return builder.toString();
    }

}

Step 6 : Start the camel context and test your application

OrderApp.java
package com.kswaughs.split;

import java.util.ArrayList;
import java.util.List;

import org.apache.camel.CamelContext;
import org.apache.camel.ProducerTemplate;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

import com.kswaughs.split.beans.Item;
import com.kswaughs.split.beans.Order;

public class OrderApp {
    
    public static void main(String[] args) {
        
    
        try {
            ApplicationContext springCtx = new ClassPathXmlApplicationContext(
                    "camel-context.xml");

            CamelContext context = springCtx.getBean("orderCtx",
                    CamelContext.class);
            
            context.start();
                
            ProducerTemplate producerTemplate = context.createProducerTemplate();
            
            List<Item> items = new ArrayList<Item>();
            items.add(new Item("1", "Camel in Action book", "Book"));
            items.add(new Item("2", "Apple IPhone8", "Phone"));
            
            Order myOrder = new Order();
            myOrder.setItems(items);
                        
            Order respOrder = producerTemplate.requestBody(
                    "direct:processOrder", myOrder, Order.class);
            
            System.out.println("resp order:"+respOrder);

            context.stop();
            
        } catch (Exception e) {
            
            e.printStackTrace();
        
        } 

    }

}

Console Output

 
handle book Item:Item [id=1, name=Camel in Action book, type=Book, price=0.0]
book Item processed
Aggregate first item: Item [id=1, name=Camel in Action book, type=Book, price=30.0]
handle phone Item:Item [id=2, name=Apple IPhone8, type=Phone, price=0.0]
phone Item processed
Aggregate old items: Order [id=ORD1463125872691, items=[Item [id=1, name=Camel in Action book, type=Book, price=30.0]], totalPrice=30.0]
Aggregate new item: Item [id=2, name=Apple IPhone8, type=Phone, price=500.0]

resp order:Order [id=ORD1463125872691, items=[Item [id=1, name=Camel in Action book, type=Book, price=30.0], Item [id=2, name=Apple IPhone8, type=Phone, price=500.0]], totalPrice=530.0]

Maven dependencies

pom.xml
<properties>
    <camelspring.version>2.16.0</camelspring.version>  
    <spring.version>4.1.6.RELEASE</spring.version>
</properties>

<dependency>
    <groupId>org.apache.camel</groupId>
    <artifactId>camel-core</artifactId>
    <version>${camelspring.version}</version>
</dependency>
<dependency>
    <groupId>org.apache.camel</groupId>
    <artifactId>camel-cxf</artifactId>
    <version>${camelspring.version}</version>
</dependency>
<dependency>
    <groupId>org.apache.camel</groupId>
    <artifactId>camel-spring</artifactId>
    <version>${camelspring.version}</version>
</dependency>
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-core</artifactId>
    <version>${spring.version}</version>
</dependency>

Recommend this on


By kswaughs | Tuesday, March 8, 2016

Camel soap web service client

To consume a soap web service, first generate the stubs and data types from existing wsdl document using wsdl2java command. I have a HelloWorld service running on my machine and after running wsdl2java command, below web service client components are generated in the following packages.

com/kswaughs/poc/acct/
    HelloWorldImplService.class [ Web service client class]
    HelloWorld.class [ web service interface ]
    AcctRequest.class [ request data type ]
    AcctResponse.class [ response data type ]
 
wsdl/
    HelloWorld.wsdl [ wsdl document ]

In this below example, I will explain how to configure camel cxf endpoint using above classes and make a web service call using java DSL routing for building a web service request AcctRequest.java, parsing the web service response AcctResponse.java.

Step 1 : Write a service client class to build the web service request and parse web service response.

SoapSvcClient.java
package com.kswaughs.outbound;

import com.kswaughs.poc.acct.AcctRequest;
import com.kswaughs.poc.acct.AcctResponse;
import com.kswaughs.beans.UserResp;

public class SoapSvcClient {
 
    // Build web service request
    public AcctRequest buildSoapReq(String reqId) {
  
        AcctRequest acctReq = new AcctRequest();
  
        acctReq.setCustNumber(reqId);
  
        System.out.println("Soap Request built successfully");
  
        return acctReq;
    }

    // Read web service response and build a pojo response
    public UserResp parseSoapResp(AcctResponse soapResp) {
  
        UserResp resp = new UserResp();
        resp.setId(soapResp.getCustNumber());
        resp.setName(soapResp.getCustName());
        resp.setBalance(String.valueOf(soapResp.getBalance()));
  
        System.out.println("Soap Response parsed successfully");
  
        return resp;
    }
}

Step 2 : Define all your beans and endpoint in camel context.

camel-context.xml
<?xml version="1.0" encoding="UTF-8"?>

<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xmlns:cxf="http://camel.apache.org/schema/cxf"
    xmlns:jaxrs="http://cxf.apache.org/jaxrs" 
    xmlns:context="http://www.springframework.org/schema/context"
    xsi:schemaLocation="
        http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd
        http://camel.apache.org/schema/cxf
        http://camel.apache.org/schema/cxf/camel-cxf.xsd
        http://cxf.apache.org/jaxrs
        http://cxf.apache.org/schemas/jaxrs.xsd
        http://camel.apache.org/schema/spring
        http://camel.apache.org/schema/spring/camel-spring.xsd
        http://www.springframework.org/schema/context 
        http://www.springframework.org/schema/context/spring-context.xsd">


    <bean id="myRouter" class="com.kswaughs.router.MyRouter" />
    <bean id="userSvcClient" class="com.kswaughs.outbound.SoapSvcClient" />

    <!-- Using Java DSL Router -->
    <camelContext id="firstCtx" xmlns="http://camel.apache.org/schema/spring">
    <routeBuilder ref="myRouter" />
    </camelContext>
 
    <cxf:cxfEndpoint id="accountEndpoint" address="http://localhost:3333/wspoc/user"
        wsdlURL="/wsdl/HelloWorld.wsdl"
        serviceClass="com.kswaughs.poc.acct.HelloWorld"
        endpointName="ws:HelloWorldImplPort"
        serviceName="ws:HelloWorldImplService" 
        xmlns:ws="http://acct.poc.kswaughs.com/" 
        loggingFeatureEnabled="true">
        <cxf:properties>
            <entry key="dataFormat" value="POJO"/>
        </cxf:properties>
    </cxf:cxfEndpoint>
</beans>

Step 3 : Define the Router using Java DSL

MyRouter.java
package com.kswaughs.router;

import org.apache.camel.builder.RouteBuilder;
import org.apache.camel.component.cxf.common.message.CxfConstants;
import org.springframework.stereotype.Component;

    @Component
    public class MyRouter extends RouteBuilder {

    @Override
    public void configure() throws Exception {
  
        from("direct:getUserDetails")
            .bean("userSvcClient", "buildSoapReq")
            .setHeader(CxfConstants.OPERATION_NAME, constant("getAccountInfo"))
            .to("cxf:bean:accountEndpoint")
            .bean("userSvcClient", "parseSoapResp");
   
    }
}

Step 4 : Start the camel context and test your application.

CamelApp.java
package com.kswaughs.app;

import org.apache.camel.CamelContext;
import org.apache.camel.ProducerTemplate;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

import com.kswaughs.beans.UserResp;

public class CamelApp {

    public static void main(String[] args) {

        try {
            ApplicationContext springCtx = new 
                ClassPathXmlApplicationContext("camel-context.xml");

            CamelContext context = springCtx
                .getBean("firstCtx", CamelContext.class);
   
            context.start();
    
            ProducerTemplate producerTemplate = context.createProducerTemplate();
   
            UserResp resp = producerTemplate
                .requestBody("direct:getUserDetails", "12345", UserResp.class);
   
            System.out.println("resp:"+resp);

            context.stop();
  
        } catch (Exception e) {     
            e.printStackTrace();    
        } 
        finally {  }
 
    }

}

Console Output

 
Soap Request built successfully
INFO|03/02/2016 15:26:49 990|Outbound Message
---------------------------
ID: 1
Address: http://localhost:3333/wspoc/user
Encoding: UTF-8
Http-Method: POST
Content-Type: text/xml
Headers: {Accept=[*/*], breadcrumbId=[ID-PC223152-53569-1456912608587-0-1], SOAPAction=[""]}
Payload: <soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"><soap:Body><ns1:getAccountInfo xmlns:ns1="http://acct.poc.kswaughs.com/"><arg0><custNumber>12345</custNumber></arg0></ns1:getAccountInfo></soap:Body></soap:Envelope>
--------------------------------------
INFO|03/02/2016 15:26:50 011|Inbound Message
----------------------------
ID: 1
Response-Code: 200
Encoding: UTF-8
Content-Type: text/xml;charset="utf-8"
Headers: {Content-type=[text/xml;charset="utf-8"], Transfer-encoding=[chunked]}
Payload: <?xml version="1.0" encoding="UTF-8"?><S:Envelope xmlns:S="http://schemas.xmlsoap.org/soap/envelope/"><S:Body><ns2:getAccountInfoResponse xmlns:ns2="http://acct.poc.kswaughs.com/"><return><balance>200</balance><custName>kswaughs</custName><custNumber>12345</custNumber></return></ns2:getAccountInfoResponse></S:Body></S:Envelope>
--------------------------------------
Soap Response parsed successfully
resp:UserResp [id=12345, name=kswaughs, balance=200]

Maven dependencies

pom.xml
<properties>
    <camelspring.version>2.16.0</camelspring.version>  
    <spring.version>4.1.6.RELEASE</spring.version>
</properties>

<dependency>
    <groupId>org.apache.camel</groupId>
    <artifactId>camel-core</artifactId>
    <version>${camelspring.version}</version>
</dependency>
<dependency>
    <groupId>org.apache.camel</groupId>
    <artifactId>camel-cxf</artifactId>
    <version>${camelspring.version}</version>
</dependency>
<dependency>
    <groupId>org.apache.camel</groupId>
    <artifactId>camel-spring</artifactId>
    <version>${camelspring.version}</version>
</dependency>
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-core</artifactId>
    <version>${spring.version}</version>
</dependency>

Recommend this on


By kswaughs | Thursday, November 19, 2015

Create REST service using Apache Camel

This post has the working example of creating a REST service using Apache camel.

1) Add below maven dependencies in your pom.xml

pom.xml
<properties>
  <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
  <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
  <camelspring.version>2.16.0</camelspring.version>
  <spring.version>3.2.10.RELEASE</spring.version>
 </properties>

 <dependencies>
  <!-- Camel Dependencies -->
  <dependency>
   <groupId>org.apache.camel</groupId>
   <artifactId>camel-core</artifactId>
   <version>${camelspring.version}</version>
  </dependency>
  <dependency>
   <groupId>org.apache.camel</groupId>
   <artifactId>camel-cxf</artifactId>
   <version>${camelspring.version}</version>
  </dependency>
  <dependency>
   <groupId>org.apache.camel</groupId>
   <artifactId>camel-servlet</artifactId>
   <version>${camelspring.version}</version>
  </dependency>
  <!-- End of Camel Dependencies -->

  <!-- Spring Dependencies -->
  <dependency>
   <groupId>org.springframework</groupId>
   <artifactId>spring-core</artifactId>
   <version>${spring.version}</version>
  </dependency>
  <dependency>
   <groupId>org.springframework</groupId>
   <artifactId>spring-context</artifactId>
   <version>${spring.version}</version>
  </dependency>
  <dependency>
   <groupId>org.springframework</groupId>
   <artifactId>spring-context-support</artifactId>
   <version>${spring.version}</version>
  </dependency>
  <dependency>
   <groupId>org.springframework</groupId>
   <artifactId>spring-web</artifactId>
   <version>${spring.version}</version>
  </dependency>
  <dependency>
   <groupId>org.springframework</groupId>
   <artifactId>spring-beans</artifactId>
   <version>${spring.version}</version>
  </dependency>
  <!-- End of Spring dependencies -->

  <!-- Jackson dependencies -->
  <dependency>
   <groupId>org.codehaus.jackson</groupId>
   <artifactId>jackson-jaxrs</artifactId>
   <version>1.9.13</version>
  </dependency>
  <dependency>
   <groupId>org.codehaus.jackson</groupId>
   <artifactId>jackson-core-asl</artifactId>
   <version>1.9.13</version>
  </dependency>
 <dependencies/> 

2) Define CXFServlet and camel-context xml in your web.xml

web.xml
<?xml version="1.0" encoding="ISO-8859-1"?>
<web-app version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee"
 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">

 <display-name>Apache Camel CXF Rest Web Application</display-name>
 <context-param>
  <param-name>contextConfigLocation</param-name>
  <param-value>classpath:camel-cxfrs-config.xml</param-value>
 </context-param>
  <servlet>
  <servlet-name>CXF Servlet</servlet-name>
  <servlet-class>org.apache.cxf.transport.servlet.CXFServlet</servlet-class>
 </servlet>
 <servlet-mapping>
  <servlet-name>CXF Servlet</servlet-name>
  <url-pattern>/*</url-pattern>
 </servlet-mapping>
 <listener>
  <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
 </listener>
</web-app> 

3) Define your camel-context xml

camel-cxfrs-config.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:cxf="http://camel.apache.org/schema/cxf"
       xmlns:jaxrs="http://cxf.apache.org/jaxrs"
       xsi:schemaLocation="
       http://www.springframework.org/schema/beans
       http://www.springframework.org/schema/beans/spring-beans.xsd
       http://camel.apache.org/schema/cxf
       http://camel.apache.org/schema/cxf/camel-cxf.xsd
       http://cxf.apache.org/jaxrs
       http://cxf.apache.org/schemas/jaxrs.xsd
       http://camel.apache.org/schema/spring
       http://camel.apache.org/schema/spring/camel-spring.xsd
    ">

 <import resource="classpath:META-INF/cxf/cxf.xml" />
 <import resource="classpath:META-INF/cxf/cxf-servlet.xml" />

 <bean id="userServiceBean" class="com.poc.rest.UserServiceImpl" />

 <cxf:rsServer id="userSvcServer" address="/"
  loggingFeatureEnabled="true">
  <cxf:serviceBeans>
   <ref bean="userServiceBean" />
  </cxf:serviceBeans>
  <cxf:providers>
   <bean class="org.codehaus.jackson.jaxrs.JacksonJsonProvider" />
  </cxf:providers>
 </cxf:rsServer>

 <camelContext id="context" xmlns="http://camel.apache.org/schema/spring">
  <route>
   <from uri="cxfrs:bean:userSvcServer" />
   <log message="Processing CXF route....http method ${header.CamelHttpMethod}" />
   <log message="Processing CXF route....path is ${header.CamelHttpPath}" />
   <log message="Processing CXF route....body is ${body}" />
   <choice>
    <when>
     <simple>${header.operationName} == 'details'</simple>
     <to uri="direct:invokeDetails" />
    </when>
    <when>
     <simple>${header.operationName} == 'add'</simple>
     <to uri="direct:invokeAdd" />
    </when>
   </choice>
  </route>

  <route id="invokeDetails">
   <from uri="direct:invokeDetails" />
   <log message="Processing invokeDetails....Start ${body}" />
   <bean ref="userServiceBean" method="details" />
   <log message="Processing invokeDetails....End is ${body}" />
  </route>
  <route id="invokeAdd">
   <from uri="direct:invokeAdd" />
   <log message="Processing invokeAdd....Start is ${body}" />
   <bean ref="userServiceBean" method="add" />
   <log message="Processing invokeAdd....End is ${body}" />
  </route>
 </camelContext>
</beans>

4) Define your REST interface

Rest Interface using Jax-RS
package com.poc.rest;

import javax.ws.rs.GET;
import javax.ws.rs.POST;
import javax.ws.rs.Path;
import javax.ws.rs.PathParam;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;

import com.poc.rest.beans.AddReq;

@Path("/user")
public interface UserService {

 @GET
 @Path("/details/{id}")
 @Produces(MediaType.APPLICATION_JSON)
 public Response details(@PathParam("id") String id);

 @POST
 @Path("/add")
 @Produces(MediaType.APPLICATION_JSON)
 public Response add(AddReq input);

}

5) Implementation code

UserServiceImpl.java
package com.poc.rest;

import javax.ws.rs.core.Response;
import javax.ws.rs.core.Response.Status;

import com.poc.rest.beans.AddReq;
import com.poc.rest.beans.AddResp;
import com.poc.rest.beans.DetailsResp;

public class UserServiceImpl implements UserService {

 public Response details(String id) {
  
     System.out.println("UserServiceImpl Java details start");
  
     DetailsResp resp = new DetailsResp();
     resp.setId(id);
     resp.setName("kswaughs");
     resp.setStatus("Success");
  
     return Response.status(Status.OK).
                entity(resp).build();

 }

 public Response add(AddReq req) {
  
     System.out.println("UserServiceImpl Java add start");
  
     AddResp resp = new AddResp();
     resp.setId(req.getId());
     resp.setStatus("Success");
  
     return Response.status(Status.OK).
                entity(resp).build();
 }

}

6) Testing the service. Run the maven build and generated the war with name 'camel-rest' and deployed in Jboss 7 server.

  
 Test 1 : 
 operation : details
 method : GET
 URL : http://127.0.0.1:8080/camel-rest-0.0.1-SNAPSHOT/user/details/123
 Response :
 
  {
   "status": "Success",
   "id": "12345",
   "name": "kswaughs"
  }
Test 2 :
operation : add
method : POST
URL : http://127.0.0.1:8080/camel-rest-0.0.1-SNAPSHOT/user/add
Request
{ "id" : "12345" , "name":"kswaughs" }

Response
{
   "id": "12345",
   "status": "Success"
}

Recommend this on