Chapter 6. Adding another route to the routing context

This tutorial shows you how to add a second route to the camel context in the ZooOrderApp project’s blueprint.xml file. The second route:

  • Takes messages (valid orders) directly from the terminal end of the first route’s otherwise branch
  • Sorts the messages according to the customer’s country
  • Sends each message to the corresponding country folder in the ZooOrderApp/target/messages folder.

Goals

In this tutorial you complete the following tasks:

  • Reconfigure the existing route for direct connection to a second route
  • Add a second route to your <camelContext>
  • Configure the new route to take messages directly from the otherwise branch of the first route
  • Add a content-based router to the new route
  • Add and configure a message header, logging, and target destination to each output branch of the new route’s content-based router

Prerequisites

To start this tutorial, you need the ZooOrderApp project resulting from one of the following:

Reconfiguring the existing route’s endpoint

The existing route sends all valid orders to the target/messages/validOrders folder.

In this section, you reconfigure the endpoint of the existing route’s Otherwise _elseValid branch to instead connect to a new route (which you create in the next section).

To configure the existing route for direct connection with the new route:

  1. Open your ZooOrderApp/src/main/resources/OSGI-INF/blueprint/blueprint.xml in the route editor.
  2. On the canvas, select the Route_route1 container to open its properties in the Properties view.
  3. Scroll down to the Shutdown Route property and then select Default.
  4. On the canvas, select the terminal file node To_Valid to display its properties in the Properties view.
  5. In the Uri field, delete the existing text, and then enter direct:OrderFulfillment.
  6. In the Id field, enter _Fulfill.
Note

Instead of repurposing the existing To_Valid terminal file node, you could have replaced it with a ComponentsDirect component, configuring it with the same property values as the repurposed To_Valid node.

To learn more about the Direct component see the Apache Camel Component Reference.

Adding the second route

To add another route to the routing context:

  1. In the Palette, open the Routing drawer and select the Route ( Route icon ) pattern.
  2. Drag the Route pattern to the canvas and drop it next to the Route_route1 container:

    tutRte2DropOnCanvas

    The Route pattern becomes the Route_route2 container node on the canvas.

  3. Click the Route_route2 container node to display its properties in the Properties view. Leave the properties as they are.
  4. Save the file.
Note

As your multi-route routing context grows in complexity, you might want to focus the route editor on an individual route while you work on it. To do so, in Project Explorer, double-click the route that you want the route editor to display on the canvas; for example Route_route2:

tutProjExSwitchRtesOnCanvas

To display all routes in the routing context on the canvas, double-click the project’s .xml context file entry (src/main/resources/OSGI-INF/…​) at the top of the Camel Contexts folder.

Configuring a Choice branch to process USA orders

In this section, you add a Choice branch to the route and configure the route to send USA orders to a new target/messages/validOrders/USA folder.

You also set a message header and a log file component.

  1. In the Palette, open the Components drawer and drag a Direct component ( Direct icon ) to the canvas and drop it in the Route_route2 container:

    tutCBRrte2From2Add

    The Route_route2 container expands to accommodate the From_from2 node.

  2. On the canvas, select the From_from2 node to open its properties in the Properties view.
  3. In the Uri field, replace name (following direct:) with OrderFulfillment, and in the Id field, enter _direct:OrderFulfillment.

    tutCBRrte2From2Props
  4. In the Palette, open the Routing drawer and drag a Choice ( Choice icon ) pattern to the canvas and drop it in the Route_route2 container.

    The Route_route2 container expands to accommodate the Choice_choice2 node.

  5. In the Route_route2 container, select the From _direct:OrderFulfillment node and drag its connector arrow over the Choice_choice2 node, then release it:

    tutCBRrte2Choice2Added

    In the Properties view, leave the Choice_choice2 node’s properties they are.

  6. In the Palette, open the Routing drawer and drag a When ( When icon ) pattern to the canvas and drop it in the Choice_choice2 container:

    tutCBRrte2When2Added

    The Choice_choice2 container expands to accommodate the When_when2 node.

  7. On the canvas, select the When_when2 node to open its properties in the Properties view.
  8. Set the node’s properties as follows:

    • Select xpath from the Language drop-down menu.
    • Enter /order/customer/country = 'USA' in the Expression field.
    • Leave Trim enabled.
    • Enter _when/usa in the Id field.

      tutCBRrte2WhenUSAprops
      Note

      Once you select the expression Language, the Properties view displays its properties in an indented list directly below the Language field. The Id property in this list sets the ID of the expression. The Id property following the Description field sets the ID of the When node.

  9. In the Palette, open the Components drawer and drag a File component ( File icon ) to the canvas and drop it in the When_when/usa container.

    The When_when/usa container expands to accommodate the To_to1 node.

  10. In the Properties view:

    tutRte2EndptUSA
    • Replace directoryName with target/messages/validOrders/USA in the Uri field.
    • Enter _US in the Id field.
  11. Save the file.

To set a message header and add a log component:

  1. In the Palette, open the Transformation drawer and drag the Set Header pattern to the canvas and drop on the When_when/usa node:

    tutCBRrte2SetHeadUSAadd

    The When_when/usa container expands to accommodate the SetHeader_setHeader3 node.

  2. On the canvas, select the SetHeader_setHeader3 node to open its properties in the Properties view.
  3. Set the node’s properties as follows:

    • From the Language drop-down menu, select constant.
    • In the Expression field, type: USA
    • Leave Trim enabled.
    • In the Header Name field, type: Destination
    • In the Id field, type: _setHead_usa

      tutCRErte2SetHeadusaProps
  4. In the Palette, open the Components drawer and drag a Log component ( Log icon ) to the canvas and drop it in the When_when/usa container.

    The When_when/usa container expands to accommodate the Log_log3 node.

  5. On the canvas, select the SetHeader_setHead_usa node and drag its connector arrow over the Log_log3 node, then release it:

    tutCBRrte2Log3Added
  6. On the canvas, select the Log_log3 node to open its properties in the Properties view:

    tutCBRrteLog3Props
  7. In the Properties view:

    tutCBRrte2Log3usaAdded
    • Enter Valid order - ship animals to USA customer in the Message field.
    • Enter _usa in the Id field.
    • Leave Logging Level as is.
  8. On the canvas, select the Log_usa node and drag its connector arrow over the To_to1 node, then release it:

    tutCBRrte2USAtermFile
  9. Save the file.

    The USA branch of Route_route2 should look like this:

    tutUSAbranchRte2

Building and configuring the Germany branch of the second route

With Route_route2 displayed on the canvas:

  1. In the Palette, open the Routing drawer and drag an Otherwise pattern ( Otherwise icon ) to the canvas and drop it in the Choice_choice2 container:

    tutCBRrte2WhenGERAdd

    The Choice_choice2 container expands to accommodate the Otherwise_otherwise1 node.

  2. On the canvas, select the Otherwise_otherwise1 node to open its properties in the Properties view.
  3. In the Properties view, enter _else/ger in the Id field.
  4. In the Palette, open the Transformation drawer and drag a Set Header pattern ( Set Header icon ) to the canvas and drop it on the Otherwise_else/ger node:

    tutCBRrte2SetHeadGERAdd

    The Otherwise_else/ger container expands to accommodate the SetHeader_setHeader3 node.

  5. On the canvas, select the SetHeader_setHeader3 node to open its properties in the Properties view.
  6. In the Properties view:

    • Select constant from the Language drop-down menu.
    • Enter Germany in the Expression field.
    • Leave Trim as is.
    • Enter Destination in the Header Name field.
    • Enter_setHead_ger in the Id field.
  7. In the Palette, open the Components drawer and drag a Log pattern ( Log icon ) to the canvas and drop it in the Otherwise_else/ger container.

    The Otherwise_else/ger container expands to accommodate the Log_log3 node.

  8. On the canvas, select the SetHeader_setHead_ger node and drag its connector arrow over the Log_log3 node, and then release it:

    tutCBRrte2LogGERAdd
  9. On the canvas, select the Log_log3 node to open its properties in the Properties view.
  10. In the Properties view:

    • Enter Valid order - ship animals to Germany customer in the Message field.
    • Enter _ger in the Id field.
    • Leave the Logging Level as is.
  11. From the Components drawer, drag a File pattern ( File icon ) to the canvas and drop it in the Otherwise_else/ger container.

    The Otherwise_else/ger container expands to accommodate the To_to1 node.

  12. On the canvas, select the Log_ger node and drag its connector arrow over the To_to1 node, and then release it:

    tutCBRrte2GERtermFile
  13. On the canvas, select the To_to1 node to open its properties in the Properties view.
  14. In the Properties view:

    • Replace directoryName with target/messages/validOrders/Germany in the Uri field.
    • Enter _GER in the Id field.
  15. Save the file.

The Germany branch of Route_route2 should look like this:

tutGERbranchRte2

Verifying the new route

The routes on the canvas should look like this:

Completed route1

Completed first route in the ZooOrderApp routing context

Completed route2

Completed second route in the ZooOrderApp routing context

In the Source tab at the bottom of the canvas, the XML for the camelContext element should look like that shown in Example 6.1, “XML for dual-route content-based router”:

Example 6.1. XML for dual-route content-based router

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

<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://www.osgi.org/xmlns/blueprint/v1.0.0
    https://www.osgi.org/xmlns/blueprint/v1.0.0/blueprint.xsd
    http://camel.apache.org/schema/blueprint
    http://camel.apache.org/schema/blueprint/camel-blueprint.xsd">

  <camelContext id="_context1" xmlns="http://camel.apache.org/schema/blueprint">
        <route id="_route1" shutdownRoute="Default">
            <from id="_from1" uri="file:src/data?noop=true"/>
            <choice id="_choice1">
                <when id="_when1">
                    <xpath>/order/orderline/quantity/text() &gt; 10</xpath>
                    <log id="_log1" message="quantity requested exceeds maximum allowed - contact customer"/>
                    <setHeader headerName="Destination" id="_setHeader1">
                        <constant>InvalidOrders</constant>
                    </setHeader>
                    <to id="_Invalid" uri="file:target/messages/invalidOrders"/>
                </when>
                <otherwise id="_else2">
                    <log id="_log2" message="valid order - process"/>
                    <setHeader headerName="Destination" id="_setHeader2">
                        <constant>ValidOrders</constant>
                    </setHeader>
                    <to id="_Fulfill" uri="direct:OrderFulfillment"/>
                </otherwise>
            </choice>
        </route>
        <route id="_route2">
            <from id="_direct:OrderFulfillment" uri="direct:OrderFulfillment"/>
            <choice id="_choice2">
                <when id="_when/usa">
                    <xpath>/order/customer/country = 'USA'</xpath>
                    <setHeader headerName="Destination" id="_setHead_usa">
                        <constant>USA</constant>
                    </setHeader>
                    <log id="_usa" message="Valid order - ship animals to USA customer"/>
                    <to id="_US" uri="file:target/messages/validOrders/USA"/>
                </when>
                <otherwise id="_else/ger">
                    <setHeader headerName="Destination" id="_setHead_ger">
                        <constant>Germany</constant>
                    </setHeader>
                    <log id="_ger" message="Valid order - ship animals to Germany customer"/>
                    <to id="_GER" uri="file:target/messages/validOrders/Germany"/>
                </otherwise>
            </choice>
        </route>
    </camelContext>
</blueprint>
Important

If the tooling added the attribute shutdownRoute=" " to the second route element (<route id="route2">), delete that attribute. Otherwise, the ZooOrderApp project might fail to run.

To make sure that your updated project works as expected, follow these steps:

  1. In Project Explorer, right-click ZooOrderApp/Camel Contexts/blueprint.xml.
  2. From the popup menu, select Run AsLocal Camel Context (without tests).
  3. Check the end of the Console’s output. You should see these lines:
tutCBRrte2Console

Check the target destination folders to verify that the routes executed properly:

  1. In Project Explorer, right-click ZooOrderApp and then select Refresh.
  2. Expand the target/messages/ folder.

    The message*.xml files should be dispersed in your the destinations as shown:

    Figure 6.1. Target message destinations in Project Explorer

    message destinations

Next steps

In the next tutorial, Chapter 7, Debugging a routing context, you learn how to use the Fuse Tooling debugger.