Showing posts with label enterprise service bus. Show all posts
Showing posts with label enterprise service bus. Show all posts

Tuesday, September 2, 2014

API Facade Pattern

A simple interface to a complex system!

Furniture showrooms display the furniture to customers in a pleasing manner so that buyers can make better choices.

Figure: Furniture showroom

It is not practical to store the furniture like that for variety of reasons including space, transportation, identification, etc. Furniture warehouses are not so pleasing to browse with piled up with furniture but they do serve the business requirements of storing them in a way that helps the business.

Figure: Furniture warehouse

It is difficult for customers to visualize what the end product look like if the business only operated a warehouse. It looks way too complicated for customers. Showrooms hide all the complexity of storing the furniture in a warehouse and showing furniture in a way that helps customers to make smart buying choices. In other words, showrooms are facades of warehouses.

You've just learnt the facade pattern!

This is exactly what happens in the digital world as well. Organizations have complex and legacy systems. They are way too complex and inflexible to consume. Further, most consumer applications now obtain information from multiple systems. The API facade pattern hides all the complexity and present a simple interface to consumers.

It looks all spaghetti with no Facade. It is just like customers browsing the warehouse:

Figure: No Facade Architecture

Facade pattern hides the complexity of connecting to multiple systems, dealing with multiple security issues, message formats by presenting a simple interface to clients.

Figure: Facade Pattern in Action

How do we implement such a system? It is actual a simple three step process:

Figure: Three Step Process of Implementation

OK great. Do I have to implement these three steps from scratch? That sounds a lot of work. Yes, you are right - it's a lot of work to implement them on your own. The good news is that there are both commercial as well as open source products available for you to just focus only on the business logic and let these products take care of the rest. Can you give a practical architecture for it? You can use an API gateway together with an ESB. You just need to write the 

Figure: A Practical Architecture to Realize Facade Pattern


Friday, June 27, 2014

Writing a simple class mediator and deploying it in WSO2 ESB

Recently I was playing around with WSO2 ESB for my own pet project. In particular, I wanted to write my own mediator to do some custom message processing on inbound messages. I am pleasantly surprised by the ease with which you can write and deploy a class mediator in WSO2 ESB. I just want to give you a sense of it by showing you an example mediator written for an already existing client and service shipped WSO2 ESB binaries. (The real mediator that I am writing involves quite some coding as it is written to process any messages going through the ESB. For this post, let's focus on the basics by using existing samples.) Specifically, StockQuoteService and stockquote clients are utilized.

First we create the mediator class by extending AbstractMediator:

package org.example.mediator;

import org.apache.synapse.MessageContext;
import org.apache.synapse.Mediator;
import org.apache.synapse.mediators.AbstractMediator;
import org.apache.axiom.om.OMElement;
import org.apache.axiom.om.OMAbstractFactory;
import org.apache.axiom.om.OMFactory;
import org.apache.axiom.soap.SOAPBody;
import org.apache.axiom.soap.SOAPFactory;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import javax.xml.namespace.QName;

public class MyMediator extends AbstractMediator {

    private static final Log log = LogFactory.getLog(MyMediator.class);

    public MyMediator(){}

    public boolean mediate(MessageContext mc) {
       //get the SOAP body from message context
    SOAPBody soapBody = mc.getEnvelope().getBody();
       //now you can modify the SOAP body as you wish
       //...

        return true;
    }

    public String getType() {
        return null;
    }

    public void setTraceState(int traceState) {
        this.traceState = traceState;
    }

    public int getTraceState() {
        return 0;
    }
}

Create a base folder, say mymed, and place MyMediator class in mymed/src/main/java/org/example/mediator. You may create other non-mediator classes and place according to the package name.

Save the following pom.xml file in mymed/ folder.
<project xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://maven.apache.org/POM/4.0.0 xsi:schemalocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
<modelversion>4.0.0</modelversion>
<groupid>org.example.mediator</groupid>
<artifactid>org.example.mediator</artifactid>
<packaging>jar</packaging>
<version>1.0</version>
<name>org.example.mediator</name>
<url>http://maven.apache.org</url>
<repositories>
       <repository>
           <id>wso2-maven2-repository</id>
           <url>http://dist.wso2.org/maven2</url>
       </repository>
       <repository>
           <id>apache-Incubating-repo</id>
           <name>Maven Incubating Repository</name>
           <url>http://people.apache.org/repo/m2-incubating-repository</url>
       </repository>
       <repository>
           <id>apache-maven2-repo</id>
           <name>Apache Maven2 Repository</name>
           <url>http://repo1.maven.org/maven2/</url>
       </repository>
   </repositories>

   <build>
       <plugins>
           <plugin>
               <groupid>org.apache.maven.plugins</groupid>
               <artifactid>maven-compiler-plugin</artifactid>
               <version>2.0</version>
               <configuration>
                   <source></source>1.5
                   <target>1.5</target>
               </configuration>
           </plugin>
       </plugins>
   </build>

   <dependencies>
       <dependency>
           <groupid>org.apache.synapse</groupid>
           <artifactid>synapse-core</artifactid>
           <version>2.1.1-wso2v7</version>
       </dependency>
   </dependencies>
</project>


Inside mymed/ folder run "mvn clean install". This will create org.example.mediator-1.0.jar in mymed/target folder.

Copy this jar to WSO2-ESB-HOME/repository/components/lib.

Now run the ESB server:
cd WSO2-ESB-HOME/bin
Run wso2server.sh (or .bat in windows)

Now you should be able to log into the ESB console by typing https://localhost:9443/carbon.

As explained here, deploy the StockQuoteService in the axis2server provided with the ESB.

cd WSO2-ESB-HOME/samples/axis2server/src/SimpleStockQuoteService
Run ant

This will create the SimpleStockQuoteService.aar and deploy it in the axis2server's repository.

Now start the axis2server:
cd WSO2-ESB-HOME/samples/axis2server
Run axis2server.sh (or .bat in windows)

In order to make sure everything is fine, let's run the client shipped with the ESB.
cd WSO2-ESB-HOME/samples/axis2Client
Run "ant stockquote -Daddurl=http://localhost:9000/services/SimpleStockQuoteService -Dtrpurl=http://localhost:8280 -Dsymbol=IBM -Dmode=quote"

This should return a random stock quote price.

Now, as explained here, we create a proxy service name StockQuoteProxy to mediate requests to SimpleStockQuoteService.

In the in sequence of this proxy service, we add our mediator inline as shown below. If you cannot load the mediator class successfully, there is something wrong with your mediator. You will have to go back and check your code.


Now execute the stockquote client again, you will see the modifications that the mediator does to the SOAP message are reflected in the SimpleStockQuoteService's received message. That demonstrates the successful deployment of the class mediator!

You may add another mediator in the out sequence to modify the reply messages from the service to the client following similar steps as above as well
.