Author: ruwan
Date: Tue May 13 09:48:41 2008
New Revision: 16952

Log:
Adding the Router Mediator core to the ESB

Added:
   trunk/esb/java/modules/mediators/
   trunk/esb/java/modules/mediators/pom.xml
      - copied, changed from r16889, /trunk/esb/java/modules/core/pom.xml
   trunk/esb/java/modules/mediators/router/
   trunk/esb/java/modules/mediators/router/pom.xml
      - copied, changed from r16889, /trunk/esb/java/modules/core/pom.xml
   trunk/esb/java/modules/mediators/router/src/
   trunk/esb/java/modules/mediators/router/src/main/
   trunk/esb/java/modules/mediators/router/src/main/java/
   trunk/esb/java/modules/mediators/router/src/main/java/org/
   trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/
   trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/
   trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/config/
   
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/config/mediator/
   
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/config/mediator/xml/
   
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/config/mediator/xml/RouterMediatorFactory.java
   (contents, props changed)
   
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/config/mediator/xml/RouterMediatorSerializer.java
   (contents, props changed)
   trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/mediators/
   
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/mediators/eip/
   
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/mediators/eip/Route.java
   (contents, props changed)
   
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/mediators/eip/RouterMediator.java
   (contents, props changed)
   trunk/esb/java/modules/mediators/router/src/main/resources/
   trunk/esb/java/modules/mediators/router/src/main/resources/META-INF/
   trunk/esb/java/modules/mediators/router/src/main/resources/META-INF/services/
   
trunk/esb/java/modules/mediators/router/src/main/resources/META-INF/services/org.apache.synapse.config.xml.MediatorFactory
   (contents, props changed)
   
trunk/esb/java/modules/mediators/router/src/main/resources/META-INF/services/org.apache.synapse.config.xml.MediatorSerializer
   (contents, props changed)
Modified:
   trunk/esb/java/pom.xml

Copied: trunk/esb/java/modules/mediators/pom.xml (from r16889, 
/trunk/esb/java/modules/core/pom.xml)
==============================================================================
--- /trunk/esb/java/modules/core/pom.xml        (original)
+++ trunk/esb/java/modules/mediators/pom.xml    Tue May 13 09:48:41 2008
@@ -1,19 +1,3 @@
-<!--
-  ~ Copyright (c) 2006, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
-  ~
-  ~ Licensed under the Apache License, Version 2.0 (the "License");
-  ~ you may not use this file except in compliance with the License.
-  ~ You may obtain a copy of the License at
-  ~
-  ~      http://www.apache.org/licenses/LICENSE-2.0
-  ~
-  ~ Unless required by applicable law or agreed to in writing, software
-  ~ distributed under the License is distributed on an "AS IS" BASIS,
-  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-  ~ See the License for the specific language governing permissions and
-  ~ limitations under the License.
-  -->
-
 <project
         xmlns="http://maven.apache.org/POM/4.0.0";
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance";
@@ -26,62 +10,14 @@
     </parent>
 
     <groupId>org.wso2.esb</groupId>
-    <artifactId>wso2-esb-core</artifactId>
-
-    <name>WSO2 ESB - Core</name>
-    <description>WSO2 Enterprise Service Bus (ESB) - Core</description>
-    <packaging>jar</packaging>
-
-    <build>
-        <plugins>
-
-            <plugin>
-                <groupId>org.apache.maven.plugins</groupId>
-                <artifactId>maven-antrun-plugin</artifactId>
-                <version>1.1</version>
-                <executions>
-                    <execution>
-                        <id>authentication_mar</id>
-                        <phase>package</phase>
-                        <configuration>
-                            <tasks>
-                                <echo message="*** Creating the authentication 
mar ***"/>
-                                <mkdir 
dir="target/modules/authentication/META-INF"/>
-                                <copy 
file="src/main/java/org/wso2/esb/modules/authentication/META-INF/module.xml"
-                                      
tofile="target/modules/authentication/META-INF/module.xml"/>
-                                <jar 
jarfile="target/modules/authentication.mar">
-                                    <fileset 
dir="target/modules/authentication">
-                                        <include name="**"/>
-                                    </fileset>
-                                </jar>
-                                <echo message="*** Creating the admin services 
aar ***"/>
-                                <mkdir dir="target/services/admin/META-INF"/>
-                                <copy 
file="src/main/java/org/wso2/esb/services/META-INF/services.xml"
-                                      
tofile="target/services/admin/META-INF/services.xml"/>
-                                <jar jarfile="target/services/ESBAdmin.aar">
-                                    <fileset dir="target/services/admin">
-                                        <include name="**"/>
-                                    </fileset>
-                                    <fileset dir="target/classes">
-                                        <include 
name="org/wso2/esb/services/**.class"/>
-                                    </fileset>
-                                </jar>
-                            </tasks>
-                        </configuration>
-                        <goals>
-                            <goal>run</goal>
-                        </goals>
-                    </execution>
-                </executions>
-            </plugin>
-        </plugins>
-    </build>
+    <artifactId>wso2-esb-mediators</artifactId>
 
-    <dependencies>
-        <dependency>
-            <groupId>org.wso2.esb</groupId>
-            <artifactId>wso2-esb-startup</artifactId>
-            <version>SNAPSHOT</version>
-        </dependency>
-    </dependencies>
+    <name>WSO2 ESB - Mediators</name>
+    <description>WSO2 Enterprise Service Bus (ESB) - Mediators [this is the 
parent pom for all the mediator modules in ESB]</description>
+    <packaging>pom</packaging>
+
+    <modules>
+        <module>router</module>
+        <module>smooks</module>
+    </modules>
 </project>

Copied: trunk/esb/java/modules/mediators/router/pom.xml (from r16889, 
/trunk/esb/java/modules/core/pom.xml)
==============================================================================
--- /trunk/esb/java/modules/core/pom.xml        (original)
+++ trunk/esb/java/modules/mediators/router/pom.xml     Tue May 13 09:48:41 2008
@@ -1,19 +1,3 @@
-<!--
-  ~ Copyright (c) 2006, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
-  ~
-  ~ Licensed under the Apache License, Version 2.0 (the "License");
-  ~ you may not use this file except in compliance with the License.
-  ~ You may obtain a copy of the License at
-  ~
-  ~      http://www.apache.org/licenses/LICENSE-2.0
-  ~
-  ~ Unless required by applicable law or agreed to in writing, software
-  ~ distributed under the License is distributed on an "AS IS" BASIS,
-  ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-  ~ See the License for the specific language governing permissions and
-  ~ limitations under the License.
-  -->
-
 <project
         xmlns="http://maven.apache.org/POM/4.0.0";
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance";
@@ -21,67 +5,15 @@
     <modelVersion>4.0.0</modelVersion>
     <parent>
         <groupId>org.wso2.esb</groupId>
-        <artifactId>wso2-esb</artifactId>
+        <artifactId>wso2-esb-mediators</artifactId>
         <version>1.7-SNAPSHOT</version>
     </parent>
 
-    <groupId>org.wso2.esb</groupId>
-    <artifactId>wso2-esb-core</artifactId>
+    <groupId>org.wso2.esb.mediators</groupId>
+    <artifactId>router-mediator</artifactId>
 
-    <name>WSO2 ESB - Core</name>
-    <description>WSO2 Enterprise Service Bus (ESB) - Core</description>
+    <name>WSO2 ESB - Router Mediator</name>
+    <description>WSO2 Enterprise Service Bus (ESB) - Router 
Mediator</description>
     <packaging>jar</packaging>
 
-    <build>
-        <plugins>
-
-            <plugin>
-                <groupId>org.apache.maven.plugins</groupId>
-                <artifactId>maven-antrun-plugin</artifactId>
-                <version>1.1</version>
-                <executions>
-                    <execution>
-                        <id>authentication_mar</id>
-                        <phase>package</phase>
-                        <configuration>
-                            <tasks>
-                                <echo message="*** Creating the authentication 
mar ***"/>
-                                <mkdir 
dir="target/modules/authentication/META-INF"/>
-                                <copy 
file="src/main/java/org/wso2/esb/modules/authentication/META-INF/module.xml"
-                                      
tofile="target/modules/authentication/META-INF/module.xml"/>
-                                <jar 
jarfile="target/modules/authentication.mar">
-                                    <fileset 
dir="target/modules/authentication">
-                                        <include name="**"/>
-                                    </fileset>
-                                </jar>
-                                <echo message="*** Creating the admin services 
aar ***"/>
-                                <mkdir dir="target/services/admin/META-INF"/>
-                                <copy 
file="src/main/java/org/wso2/esb/services/META-INF/services.xml"
-                                      
tofile="target/services/admin/META-INF/services.xml"/>
-                                <jar jarfile="target/services/ESBAdmin.aar">
-                                    <fileset dir="target/services/admin">
-                                        <include name="**"/>
-                                    </fileset>
-                                    <fileset dir="target/classes">
-                                        <include 
name="org/wso2/esb/services/**.class"/>
-                                    </fileset>
-                                </jar>
-                            </tasks>
-                        </configuration>
-                        <goals>
-                            <goal>run</goal>
-                        </goals>
-                    </execution>
-                </executions>
-            </plugin>
-        </plugins>
-    </build>
-
-    <dependencies>
-        <dependency>
-            <groupId>org.wso2.esb</groupId>
-            <artifactId>wso2-esb-startup</artifactId>
-            <version>SNAPSHOT</version>
-        </dependency>
-    </dependencies>
 </project>

Added: 
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/config/mediator/xml/RouterMediatorFactory.java
==============================================================================
--- (empty file)
+++ 
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/config/mediator/xml/RouterMediatorFactory.java
   Tue May 13 09:48:41 2008
@@ -0,0 +1,124 @@
+/*
+ * Copyright (c) 2006, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.wso2.esb.config.mediator.xml;
+
+import org.apache.axiom.om.OMAttribute;
+import org.apache.axiom.om.OMElement;
+import org.apache.synapse.Mediator;
+import org.apache.synapse.config.xml.AbstractMediatorFactory;
+import org.apache.synapse.config.xml.SynapseXPathFactory;
+import org.apache.synapse.config.xml.TargetFactory;
+import org.apache.synapse.config.xml.XMLConfigConstants;
+import org.jaxen.JaxenException;
+import org.wso2.esb.mediators.eip.Route;
+import org.wso2.esb.mediators.eip.RouterMediator;
+
+import javax.xml.namespace.QName;
+import java.util.Iterator;
+import java.util.regex.Pattern;
+
+/**
+ * <p>Builds the <code>RouterMediator</code> using the following 
configuration</p>
+ *
+ * <pre>
+ * &lt;router [continueAfter=(true | false)]&gt;
+ *   &lt;route expression="xpath" [match="regEx"] [breakRouter=(true | 
false)]&gt;
+ *     &lt;target [sequence="string"] [endpoint="string"]&gt;
+ *       &lt;sequence ....../&gt;?
+ *       &lt;endpoint ....../&gt;?
+ *     &lt;/target&gt;
+ *   &lt;/route&gt;+
+ * &lt;/router&gt;
+ * </pre>
+ */
+public class RouterMediatorFactory extends AbstractMediatorFactory {
+
+    private static final QName ROUTER_Q = new 
QName(XMLConfigConstants.SYNAPSE_NAMESPACE, "router");
+    private static final QName ROUTE_Q = new 
QName(XMLConfigConstants.SYNAPSE_NAMESPACE, "route");
+    private static final QName TARGET_Q = new 
QName(XMLConfigConstants.SYNAPSE_NAMESPACE, "target");
+
+    private static final QName ATT_CONTINUE_AFTER = new QName("continueAfter");
+    private static final QName ATT_MATCH = new QName("match");
+    private static final QName ATT_BREAK_ROUTER = new QName("breakRouter");
+
+    public Mediator createMediator(OMElement elem) {
+
+        if (!ROUTER_Q.equals(elem.getQName())) {
+            handleException("Unable to create the Router mediator. " +
+                "Unexpected element as the Router mediator configuration");
+        }
+
+        RouterMediator m = new RouterMediator();
+
+        OMAttribute continueAfterAttr = elem.getAttribute(ATT_CONTINUE_AFTER);
+        if (continueAfterAttr != null && continueAfterAttr.getAttributeValue() 
!= null) {
+            
m.setContinueAfter(Boolean.parseBoolean(continueAfterAttr.getAttributeValue()));
+        }
+
+        for (Iterator itr = elem.getChildrenWithName(ROUTE_Q); itr.hasNext();) 
{
+
+            OMElement routeElement = (OMElement) itr.next();
+
+            OMAttribute expressionAttr = routeElement.getAttribute(ATT_EXPRN);
+            OMAttribute matchAttr = routeElement.getAttribute(ATT_MATCH);
+            OMAttribute breakRouterAttr = 
routeElement.getAttribute(ATT_BREAK_ROUTER);
+            OMElement targetElem = 
routeElement.getFirstChildWithName(TARGET_Q);
+
+            Route route = new Route();
+
+            if (expressionAttr != null && expressionAttr.getAttributeValue() 
!= null) {
+
+                try {
+                    route.setExpression(
+                        SynapseXPathFactory.getSynapseXPath(routeElement, 
ATT_EXPRN));
+                } catch (JaxenException e) {
+                    handleException("Couldn't build the xpath from the 
expression : "
+                        + expressionAttr.getAttributeValue(), e);
+                }
+            } else {
+
+                handleException("Route without an expression attribute has 
been found, " +
+                    "but it is required to have an expression for all routes");
+            }
+
+            if (matchAttr != null && matchAttr.getAttributeValue() != null) {
+                route.setMatch(Pattern.compile(matchAttr.getAttributeValue()));
+            }
+
+            if (breakRouterAttr != null && breakRouterAttr.getAttributeValue() 
!= null) {
+                
route.setBreakRouter(Boolean.parseBoolean(breakRouterAttr.getAttributeValue()));
+            }
+
+            if (targetElem != null) {
+
+                route.setTarget(TargetFactory.createTarget(targetElem));
+
+            } else {
+                handleException("Route has to have a target for it, " +
+                    "missing the taregt of the route");
+            }
+
+            m.addRoute(route);
+        }
+
+        return m;
+    }
+
+    public QName getTagQName() {
+        return ROUTER_Q;
+    }
+}

Added: 
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/config/mediator/xml/RouterMediatorSerializer.java
==============================================================================
--- (empty file)
+++ 
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/config/mediator/xml/RouterMediatorSerializer.java
        Tue May 13 09:48:41 2008
@@ -0,0 +1,100 @@
+/*
+ * Copyright (c) 2006, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.wso2.esb.config.mediator.xml;
+
+import org.apache.axiom.om.OMElement;
+import org.apache.synapse.Mediator;
+import org.apache.synapse.config.xml.AbstractMediatorSerializer;
+import org.apache.synapse.config.xml.SynapseXPathSerializer;
+import org.apache.synapse.config.xml.TargetSerializer;
+import org.wso2.esb.mediators.eip.Route;
+import org.wso2.esb.mediators.eip.RouterMediator;
+
+/**
+ * <p>Serializes the <code>RouterMediator</code> into the following 
configuration</p>
+ *
+ * <pre>
+ * &lt;router [continueAfter=(true | false)]&gt;
+ *   &lt;route expression="xpath" [match="regEx"] [breakRouter=(true | 
false)]&gt;
+ *     &lt;target [sequence="string"] [endpoint="string"]&gt;
+ *       &lt;sequence ....../&gt;?
+ *       &lt;endpoint ....../&gt;?
+ *     &lt;/target&gt;
+ *   &lt;/route&gt;+
+ * &lt;/router&gt;
+ * </pre>
+ */
+public class RouterMediatorSerializer extends AbstractMediatorSerializer {
+
+    public OMElement serializeMediator(OMElement parent, Mediator mediator) {
+
+        if (!(mediator instanceof RouterMediator)) {
+            handleException("Unsupported mediator passed in for serialization 
: "
+                + mediator.getType());
+        }
+
+        RouterMediator m = (RouterMediator) mediator;
+
+        OMElement routerElem = fac.createOMElement("router", synNS);
+        saveTracingState(routerElem, m);
+
+        if (m.isContinueAfter()) {
+            routerElem.addAttribute(fac.createOMAttribute("continueAfter", 
nullNS, "true"));
+        }
+
+        for (Route route : m.getRoutes()) {
+
+            OMElement routeElem = fac.createOMElement("route", synNS);
+
+            if (route.getExpression() != null) {
+                SynapseXPathSerializer.serializeXPath(
+                    route.getExpression(), routeElem, "expression");
+            } else {
+                handleException("Incomplete route has been found in the " +
+                    "serialization of the RouterMediator");
+            }
+
+            if (route.getMatch() != null) {
+                routeElem.addAttribute(
+                    fac.createOMAttribute("match", nullNS, 
route.getMatch().pattern()));
+            }
+
+            if (!route.isBreakRouter()) {
+                routeElem.addAttribute(fac.createOMAttribute("breakRouter", 
nullNS, "false"));
+            }
+
+            if (route.getTarget() != null) {
+                
routeElem.addChild(TargetSerializer.serializeTarget(route.getTarget()));
+            } else {
+                handleException("Route without a target has been found in the 
" +
+                    "serialization of the RouterMediator");
+            }
+
+            routerElem.addChild(routeElem);
+        }
+
+        if (parent != null) {
+            parent.addChild(routerElem);
+        }
+
+        return routerElem;
+    }
+
+    public String getMediatorClassName() {
+        return RouterMediator.class.getName();
+    }
+}

Added: 
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/mediators/eip/Route.java
==============================================================================
--- (empty file)
+++ 
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/mediators/eip/Route.java
 Tue May 13 09:48:41 2008
@@ -0,0 +1,309 @@
+/*
+ * Copyright (c) 2006, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.wso2.esb.mediators.eip;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.apache.synapse.MessageContext;
+import org.apache.synapse.SynapseException;
+import org.apache.synapse.endpoints.Endpoint;
+import org.apache.synapse.mediators.base.SequenceMediator;
+import org.apache.synapse.mediators.eip.Target;
+import org.apache.synapse.util.xpath.SynapseXPath;
+import org.jaxen.JaxenException;
+
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+/**
+ * <p>Specifies the <code>Route</code> including the route conditions and the 
routing of a
+ * particular route for the <code>RouterMediator</code>. This stores the 
properties of a particular
+ * route and will be used by the <code>RouterMedaitor</code> in order to route 
the messages.</p>
+ *
+ * <p>This stores the routing path as a <code>Target</code> whihc can contain 
either a sequence or
+ * else and endpoint as the routing path and in the endpoint case the message 
will be delivered to
+ * the specified endpoint</p>
+ *
+ * @see org.wso2.esb.mediators.eip.RouterMediator
+ * @see org.apache.synapse.mediators.eip.Target
+ */
+public class Route {
+
+    /**
+     * <p>The state of the <code>Route</code> after calling the 
<code>doRoute</code> method is this
+     * particular route over the specified message does not match the 
conditions specified in this
+     * route.</p>
+     *
+     * @see Route#doRoute(org.apache.synapse.MessageContext)
+     */
+    public static final int ROUTE_NOT_MACHING_STATE = 0;
+
+    /**
+     * <p>The state of the <code>Route</code> after calling the 
<code>doRoute</code> method is; this
+     * particular route over the specified message matches the conditions 
specified in this
+     * route and hence the message is routed, and the message should not go 
though any more routes
+     * within this router.</p>
+     *
+     * @see Route#doRoute(org.apache.synapse.MessageContext)
+     */
+    public static final int ROUTED_WITH_BREAK_STATE = 1;
+
+    /**
+     * <p>The state of the <code>Route</code> after calling the 
<code>doRoute</code> method is; this
+     * particular route over the specified message matches the conditions 
specified in this
+     * route and hence the message is routed, but the message may go through 
any other matching
+     * routes within this router for further routing.</p>
+     *
+     * @see Route#doRoute(org.apache.synapse.MessageContext)
+     */
+    public static final int ROUTED_WITH_CONTINUE_STATE = 2;
+
+    /**
+     * <p>The state of the <code>Route</code> after calling the 
<code>doRoute</code> method is; this
+     * particular route over the specified message matches the conditions 
specified in this
+     * route and hence the message is routed, at the same time the message 
must not go through any
+     * other matching routes within this router.</p>
+     *
+     * @see Route#doRoute(org.apache.synapse.MessageContext)
+     */
+    public static final int ROUTED_AND_DROPPED_STATE = 3;
+
+    /**
+     * <p>The state of the routing, when there is an error in routing after 
executing the
+     * <code>doRoute</code> method.<p>
+     *
+     * @see Route#doRoute(org.apache.synapse.MessageContext)
+     */
+    public static final int UNEXPECTED_ROUTING_STATE = 4;
+
+    /**
+     * <p>XPath describing the element or the attirbute of the message which 
will be matched
+     * againset the <code>match</code> to check the matching. If there is no 
<code>match</code>
+     * then the presence of this expression will be taken as the matching</p>
+     *
+     * @see org.apache.synapse.util.xpath.SynapseXPath
+     */
+    private SynapseXPath expression;
+
+    /**
+     * <p>Regular expression which will be evaluated to see the string value 
of the
+     * <code>expression</code> evaluated over the current message to check 
whether that value is
+     * matching to the specified pattern to check the matching</p>
+     *
+     * @see java.util.regex.Pattern
+     */
+    private Pattern match;
+
+    /**
+     * <p>Specifies whether to break the route or to continue on further 
routes on matching this
+     * <code>route</code>. If the value is true, and if the <code>route</code> 
is matching then no
+     * further routes will be evaluated inside the <code>router</code>, where 
as if the value is
+     * false the next route will be evaluated to check the matching regardless 
of whether the
+     * current route matches or not.</p>
+     *
+     * <p>Default value for the <code>breakRouter</code> is true implying that 
the router will be
+     * breaked after the route. (i.e. no further routes will occur in this 
router)</p>
+     */
+    private boolean breakRouter = true;
+
+    /**
+     * <p>Represents the <code>target</code> of the route and it can specify a 
<code>sequence</code>
+     * or an <code>endpoint</code> for the matching messages whihc needs to be 
routed to. At the
+     * same time it can also specify the <code>to</code> address as well as 
<code>soapAction</code>
+     * for the routing.</p>
+     */
+    private Target target;
+
+    /**
+     * <p>Holds the log4j based log for the loggin purposes</p>
+     */
+    private static final Log log = LogFactory.getLog(Route.class);
+
+    /**
+     * <p>Checks whether this route is matching for the given message or not. 
In general if the
+     * <code>expression</code> is provided without a <code>match</code> then 
the presence of a
+     * element or attribute in the message specified by the 
<code>expression</code> will be taken as
+     * matching</p>
+     *
+     * <p>If both the <code>expression</code> and the <code>match</code> is 
provided then the
+     * evaluated string value of the <code>expression</code> over the message 
will be matched
+     * againset the given regular expression <code>match</code> to test 
whether the string value is
+     * matching for the pattern or not</p>
+     *
+     * @param synCtx message to be matched to check the route condition
+     * @return whether the route matches the given message or not
+     */
+    public boolean isMatching(MessageContext synCtx) {
+
+        // expression is required to perform the match
+        if (expression != null) {
+
+            // if the match Pattern is not there then we consider the
+            // existance of the xpath in the message
+            if (match == null) {
+
+                try {
+                    // check whether the xpath is present in the message or not
+                    return expression.booleanValueOf(synCtx.getEnvelope());
+                } catch (JaxenException e) {
+                    handleException("Error evaluating XPath expression : " + 
expression, e, synCtx);
+                }
+
+            } else {
+
+                String sourceString = expression.stringValueOf(synCtx);
+
+                if (sourceString == null) {
+                    log.debug("Source String : " + expression + " evaluates to 
null");
+                    return false;
+                }
+
+                Matcher matcher = match.matcher(sourceString);
+
+                if (matcher == null) {
+                    log.debug("Regex pattren matcher for : " + match.pattern() 
+
+                        "against source : " + sourceString + " is null");
+                    return false;
+                }
+
+                // matchese the string value of the xpath over the message and
+                // evalutaes with the specifeid regEx
+                return matcher.matches();
+            }
+
+        } else {
+            handleException("Couldn't find the routing expression", synCtx);
+        }
+
+        return false; // never executes
+    }
+
+    /**
+     * <p>Routes the message in to the specified <code>target</code> whihc can 
be one of the
+     * <code>sequence</code> or else and <code>endpoint</code> after checking 
whether the conditions
+     * specified in this route matches the provided message.</p>
+     *
+     * <p>Also if this particular router specifies the 
<code>breakRouter</code> to be false then the
+     * specified status will be returned to not to break the route and route 
further matchings in
+     * the router. Otherwise it will break the route</p>
+     *
+     * @param synCtx message to be routed
+     * @return state of the routing and this can be one of the 
ROUTE_NOT_MACHING_STATE, or
+     * ROUTED_WITH_BREAK_STATE, or ROUTED_WITH_CONTINUE state.
+     *
+     * @see Route#isMatching(org.apache.synapse.MessageContext)
+     */
+    public int doRoute(MessageContext synCtx) {
+
+        // first check whether this Route matches the specified conditions
+        if (isMatching(synCtx)) {
+
+            // route the messages to the specified target
+            if (target != null) {
+
+                boolean mediationResult = true;
+
+                if (target.getSequence() != null) {
+                    mediationResult = target.getSequence().mediate(synCtx);
+                } else if (target.getSequenceRef() != null) {
+                    SequenceMediator refSequence
+                        = (SequenceMediator) 
synCtx.getSequence(target.getSequenceRef());
+                    if (refSequence != null) {
+                        mediationResult = refSequence.mediate(synCtx);
+                    }
+                } else if (target.getEndpoint() != null) {
+                    target.getEndpoint().send(synCtx);
+                } else if (target.getEndpointRef() != null) {
+                    Endpoint epr = 
synCtx.getConfiguration().getEndpoint(target.getEndpointRef());
+                    if (epr != null) {
+                        epr.send(synCtx);
+                    }
+                }
+
+                if (!mediationResult) {
+
+                    return ROUTED_AND_DROPPED_STATE;
+
+                } else {
+
+                    // returns the state as break route or continue route 
depending on the
+                    // breakRouter attribute
+                    return breakRouter ? ROUTED_WITH_BREAK_STATE : 
ROUTED_WITH_CONTINUE_STATE;
+                }
+            } else {
+
+                handleException("Couldn't find the route taregt for the 
message", synCtx);
+            }
+
+        } else {
+
+            // the route conditions does not match the message
+            return ROUTE_NOT_MACHING_STATE;
+        }
+
+        // does not execute under normal circumstances
+        return UNEXPECTED_ROUTING_STATE;
+    }
+
+    public Pattern getMatch() {
+        return match;
+    }
+
+    public void setMatch(Pattern match) {
+        this.match = match;
+    }
+
+    public SynapseXPath getExpression() {
+        return expression;
+    }
+
+    public void setExpression(SynapseXPath expression) {
+        this.expression = expression;
+    }
+
+    public boolean isBreakRouter() {
+        return breakRouter;
+    }
+
+    public void setBreakRouter(boolean breakRouter) {
+        this.breakRouter = breakRouter;
+    }
+
+    public Target getTarget() {
+        return target;
+    }
+
+    public void setTarget(Target target) {
+        this.target = target;
+    }
+
+    private void handleException(String msg, Exception e, MessageContext 
msgContext) {
+        log.error(msg, e);
+        if (msgContext.getServiceLog() != null) {
+            msgContext.getServiceLog().error(msg, e);
+        }
+        throw new SynapseException(msg, e);
+    }
+
+    private void handleException(String msg, MessageContext msgContext) {
+        log.error(msg);
+        if (msgContext.getServiceLog() != null) {
+            msgContext.getServiceLog().error(msg);
+        }
+        throw new SynapseException(msg);
+    }
+}

Added: 
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/mediators/eip/RouterMediator.java
==============================================================================
--- (empty file)
+++ 
trunk/esb/java/modules/mediators/router/src/main/java/org/wso2/esb/mediators/eip/RouterMediator.java
        Tue May 13 09:48:41 2008
@@ -0,0 +1,192 @@
+/*
+ * Copyright (c) 2006, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.wso2.esb.mediators.eip;
+
+import org.apache.synapse.MessageContext;
+import org.apache.synapse.mediators.AbstractMediator;
+import org.apache.synapse.mediators.eip.Target;
+
+import java.util.LinkedList;
+import java.util.List;
+
+/**
+ * <p>Routes the messages going through this mediator in to the specified 
target sequecne or to the
+ * taregt endpoint if the specified conditions under a particular route is 
matching. There can be
+ * several routes and one can specify to break after the first matching route 
using the
+ * <code>breakRouter</code> attirbute in the routes and hence the route order 
has some impact on the
+ * routings</p>
+ *
+ * <p>Normally message routing is redirecting the message, so this mediator 
also permits further
+ * mediation in this path where as the message is mediated using the roted 
path(s) by default, but
+ * it can be configured by the <code>continueAfter</code> attribute if 
required to continue further
+ * mediation of the path</p>
+ *
+ * <p>Individual routes are stored as <code>Route</code> objects keeping there 
conditions inside it
+ * with the routing targets as <code>Target<code> objects inside a particualr 
route and there is a
+ * linked list of <code>Route</code> per mediator.</p>
+ *
+ * @see org.wso2.esb.mediators.eip.Route
+ * @see org.apache.synapse.mediators.eip.Target
+ * @see org.apache.synapse.Mediator
+ * @see org.apache.synapse.mediators.AbstractMediator
+ */
+public class RouterMediator extends AbstractMediator {
+    
+    /**
+     * <p>List of routes to be checked and routed on arrival of a message. 
These routes has an order
+     * when executing and hence kept in a <code>LinkedList</code>. These route 
will be taken in to
+     * the order and checked for matching of the conditions specified inside 
the routes and then the
+     * routing will be called over the route (i.e. message will be mediated 
using the target)</p>
+     *
+     * <p>By default if there is a matching route then the next routes will 
not be invoked because
+     * the message has been routed, but this can be modified by using the 
<code>breakRouter</code>
+     * attribute in the route.</p>
+     *
+     * @see org.wso2.esb.mediators.eip.Route
+     * @see java.util.LinkedList
+     */
+    private List<Route> routes = new LinkedList<Route>();
+
+    /**
+     * <p>Specifies whether to continue further mediation on the current path 
apart from the routed
+     * path. If the value is set to true this will not permit further 
mediation along the path, but
+     * the defautl value for this is false implying by default the router 
stops the current path
+     * mediation and redirects the message to the routed path</p>
+     */
+    private boolean continueAfter = false;
+
+    /**
+     * <p>Routes the message depending on the specified set of routes if the 
routing condition is
+     * matching over the provided message. There can be a list of routers 
specified in to a
+     * particualr order, and these routes will be invoked to route the message 
in the specified
+     * order.</p>
+     *
+     * <p>If there is a matching route found over the message then the routing 
will occur and after
+     * this synchronized routing further mediation of the message through 
other routes specified
+     * after the matching route will be decided by the value of the 
<code>breakRouter</code>
+     * attribute of the route.</p>
+     *
+     * <p>By default this mediator will drop the message stopping further 
medaition along the
+     * current path and this also can be modified by using the 
<code>continueAfter</code> attribute
+     * of the mediator.</p>
+     *
+     * @param synCtx message to be routed
+     * @return whether to continue further mediaiton or not as a boolean value
+     *
+     * @see 
org.apache.synapse.Mediator#mediate(org.apache.synapse.MessageContext)
+     * @see 
org.wso2.esb.mediators.eip.Route#doRoute(org.apache.synapse.MessageContext)
+     */
+    public boolean mediate(MessageContext synCtx) {
+
+        boolean traceOn = isTraceOn(synCtx);
+        boolean traceOrDebugOn = isTraceOrDebugOn(traceOn);
+
+        if (traceOrDebugOn) {
+            traceOrDebug(traceOn, "Start : Router mediator");
+
+            if (traceOn && trace.isTraceEnabled()) {
+                trace.trace("Message : " + synCtx.getEnvelope());
+            }
+        }
+
+        for (Route route : routes) {
+
+            int routeState = route.doRoute(synCtx);
+
+            // if the message does not match the route conditions
+            if (Route.ROUTE_NOT_MACHING_STATE == routeState && traceOrDebugOn) 
{
+
+                traceOrDebug(traceOn, "The message does not matches the 
routing conditions : " +
+                    "Expression = '" + route.getExpression() + "'" + 
(route.getMatch() != null ?
+                    " Pattern = '" + route.getMatch().toString() + "'" : ""));
+
+            } else {
+
+                // get the route target for logging purposes
+                Target routeTarget = route.getTarget();
+                String targetString = null;
+
+                if (routeTarget != null) {
+
+                    // prepare a target string for loggin purposes
+                    if (routeTarget.getSequenceRef() != null) {
+                        targetString = "Sequence <" + 
routeTarget.getSequenceRef() + ">";
+                    } else if (routeTarget.getSequence() != null) {
+                        targetString = "Sequence <annonymous>";
+                    } else if (routeTarget.getEndpointRef() != null) {
+                        targetString = "Endpoint <" + 
routeTarget.getEndpointRef() + ">";
+                    } else if (routeTarget.getEndpoint() != null) {
+                        targetString = "Endpoint <annonymous>";
+                    } else {
+                        targetString = "without an endpoint or a sequence";
+                    }
+                }
+
+                // if routed and the message may route furhter using the 
existing routes
+                if (Route.ROUTED_WITH_CONTINUE_STATE == routeState && 
traceOrDebugOn) {
+
+                    traceOrDebug(traceOn, "The message has been routed to the 
target : "
+                        + targetString + ", but further routings are allowed");
+
+                // if routed and the message should not be routed with other 
remaining routes
+                } else if (Route.ROUTED_WITH_BREAK_STATE == routeState) {
+
+                    traceOrDebug(traceOn, "The message has been routed to the 
target : "
+                        + targetString + ", and no further routes are 
allowed");
+
+                    // break this router permitting further routings
+                    break;
+                } else if (Route.ROUTED_AND_DROPPED_STATE == routeState) {
+
+                    traceOrDebug(traceOn, "The message has been routed to the 
target : "
+                        + targetString + ", and the message is droped on the 
route");
+
+                    return false;
+                }
+            }
+        }
+
+        if (traceOrDebugOn) {
+            traceOrDebug(traceOn, "End : Router mediator");
+        }
+
+        // normally message routing is redirecting the message, so this 
permits further mediation
+        // in this path where as the message is mediated using the roted 
path(s) by default, but it
+        // can be configured by the continueAfter attribute if required
+        return continueAfter;
+    }
+
+    public List<Route> getRoutes() {
+        return routes;
+    }
+
+    public void setRoutes(List<Route> routes) {
+        this.routes = routes;
+    }
+
+    public void addRoute(Route route) {
+        routes.add(route);
+    }
+
+    public boolean isContinueAfter() {
+        return continueAfter;
+    }
+
+    public void setContinueAfter(boolean continueAfter) {
+        this.continueAfter = continueAfter;
+    }
+}

Added: 
trunk/esb/java/modules/mediators/router/src/main/resources/META-INF/services/org.apache.synapse.config.xml.MediatorFactory
==============================================================================
--- (empty file)
+++ 
trunk/esb/java/modules/mediators/router/src/main/resources/META-INF/services/org.apache.synapse.config.xml.MediatorFactory
  Tue May 13 09:48:41 2008
@@ -0,0 +1 @@
+org.wso2.esb.config.mediator.xml.RouterMediatorFactory
\ No newline at end of file

Added: 
trunk/esb/java/modules/mediators/router/src/main/resources/META-INF/services/org.apache.synapse.config.xml.MediatorSerializer
==============================================================================
--- (empty file)
+++ 
trunk/esb/java/modules/mediators/router/src/main/resources/META-INF/services/org.apache.synapse.config.xml.MediatorSerializer
       Tue May 13 09:48:41 2008
@@ -0,0 +1 @@
+org.wso2.esb.config.mediator.xml.RouterMediatorSerializer
\ No newline at end of file

Modified: trunk/esb/java/pom.xml
==============================================================================
--- trunk/esb/java/pom.xml      (original)
+++ trunk/esb/java/pom.xml      Tue May 13 09:48:41 2008
@@ -771,6 +771,7 @@
         <module>modules/core</module>
         <module>modules/samples</module>
         <module>modules/distribution</module>
+        <module>modules/mediators</module>
         <module>modules/startup</module>
     </modules>
 

_______________________________________________
Esb-java-dev mailing list
[email protected]
http://wso2.org/cgi-bin/mailman/listinfo/esb-java-dev

Reply via email to