zondag 21 oktober 2007

Using openESB SMTP components inside ServiceMix

Using openESB SMTP components inside ServiceMix

One of the advantages of using a JBI compliant container is that it should be easy to use components from other containers. So in theory using a component from the openESB JBI container in ServiceMix would be as simple as dropping in the component in the deploy directory and create a serviceunit that can be deployed to it.

In practice however, for a change, it isn't that much more difficult. I was playing around with the SMTP component of openESB and wanted to check whether it worked in ServiceMix, since ServiceMix itself didn't provide this connectivity yet. So for those of you who want to play around with the components of openESB inside ServiceMix, here are the steps to follow:

1. Download the latest SMTP components:

You can find the daily builds at:

http://download.java.net/jbi/binaries/open-jbi-components/main/nightly/latest/ojc/

Here download the smtpbc.jar file and also the encoderlib.jar file. The first one is the binding component that will be using from ServiceMix and the second one is the shared library the smtpbc.jar file needs.

2. Fix a classcast problem:

The first problem we'll encounter when we start using this component is because most of the components from openESB use a different version of wsdl4j. If we don't fix this we'll get a strange classcast exception when we start deploying the serviceunits to this component.
So the first thing we need to do is replace the wsdl4j from the ServiceMix, from the newer version from this archive. Just copy the wsd4j.jar file from this component to the lib directory of ServiceMix replacing the version there. And then while you're at it, remove the wsd4j.jar file from the component.

3. Install the component in ServiceMix:

To now install the component in ServiceMix, you only need to drop the archive in the 'HotDeploy' directory and you'll see some output in the console. Before we do this though, first drop the encorderlib.jar file in this directory, so that we're sure it can find it's needed shared libraries.
Now we're ready to start using the component.

4. Create a new serviceassembly for deployment:
For those of you who haven't worked with openESB yet, probably aren't familiar with the way you need to deploy to these JBI components. In ServiceMix you just create a simple XBean configuration and be done with it. For openESB it's a bit different. You first create a WSDL describing the messages, operations and services. And by using WSDL extensions you configure how you want to connect to an external system.

Let's first look at how the WSDL file looks:
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<wsdl:definitions xmlns:osesb="http://opensourceesb/mailBC/"
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
xmlns:wsdl="http://schemaswri.xmlsoap.org/wsdl/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema" name="mailBC"
xmlns:smtp="http://schemas.sun.com/jbi/wsdl-extensions/smtp/"
targetNamespace="http://opensourceesb/mailBC/">

<!-- define the message we need to sent -->
<wsdl:message name="emailReceiverOperationRequest">
<wsdl:part name="bodypart" type="xsd:string"/>
<wsdl:part name="subjectpart" type="xsd:string"/>
<wsdl:part name="frompart" type="xsd:string"/>
</wsdl:message>

<!-- define the operation on this port -->
<wsdl:portType name="emailReceiverPortType">
<wsdl:operation name="EmailReceiverOperation">
<wsdl:input message="osesb:emailReceiverOperationRequest" name="input1"/>
</wsdl:operation>
</wsdl:portType>

<!-- define a concrete implementation -->
<wsdl:binding name="emailReceiverBinding" type="osesb:emailReceiverPortType">
<smtp:binding/>
<wsdl:operation name="EmailReceiverOperation" >
<smtp:operation/>
<wsdl:input name="input1">
<smtp:input message="bodypart" subject="subjectpart" from="frompart"/>
</wsdl:input>
</wsdl:operation>
</wsdl:binding>

<wsdl:service name="mailBCService">
<wsdl:port binding="osesb:emailReceiverBinding" name="emailReceiverPort">
<smtp:address location="mailto:jos.dirksen@gmail.com" smtpport="10025" />
</wsdl:port>
</wsdl:service>
</wsdl:definitions>

We won't go into too much detail here. The most important part for us here, is the wsdl:binding and the wsdl:port where we extend the normal wsdl with smtp specific settings. For more info on what you can configure here look at the smtp bc documentation on the jbi-components site (http://wiki.open-esb.java.net/Wiki.jsp?page=SMTPBC). In our case we just want to be able to send a mail to the ESB and then send the content to a file. With the above configuration we've specified that we'll start listening on 10025 and look for an email to jos.dirksen@gmail.com.
Now we have to create a jbi.xml file for the serviceunit that tells the container what to do with this interface. Do we implement it (provide a service) or are we going to use it (consume it).

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<jbi xmlns="http://java.sun.com/xml/ns/jbi"
xmlns:ns1="http://opensourceesb/mailBC/"
version="1.0">
<services binding-component="true">
<!-- receive messages from external -->
<consumes endpoint-name="emailReceiverPort"
interface-name="ns1:emailReceiverPortType"
service-name="ns1:mailBCService"/>
</services>
</jbi>

What this jbi.xml file tells us is that if we receive a message on the specified address, we send the content of this message to the service as specified in this jbi.xml file. So this ServiceUnit serves as a proxy from an email client to a service inside the jbi container.

We can now deploy this serviceunit in the standard way. Just create an archive (SU-example-mail.zip) that contains the following:

+ META-INF/jbi.xml
+ mailBC.wsdl

Since we also want to do something with the message we've received we'll also quickly define an endpoint in an xbean for the file component.

<beans xmlns:f="http://servicemix.apache.org/file/1.0"
xmlns:proj="http://opensourceesb/mailBC/"
xmlns:sm="http://servicemix.apache.org/config/1.0">
<f:sender service="proj:mailBCService"
endpoint="emailReceiverPort"
directory="servicemix_work/myOutbox/">
</f:sender>
</beans>

As you can see we create a component that provides the service/endpoint that the mailBC wants to consume (so in hindsight, I'd might have chosen some better names). For this one also create a simple serviceunit (again an archive) with the name (SU-example-file.zip):

+ xbean.xml

Add both of these together in an service assembly with the following descriptor:

<?xml version="1.0" encoding="UTF-8"?>
<jbi xmlns="http://java.sun.com/xml/ns/jbi" version="1.0">
<service-assembly>
<identification>
<name>MailServiceAssembly</name>
<description>Assembly showing usage of openesb mail component</description>
</identification>
<service-unit>
<identification>
<name>Mail-SU</name>
<description>test</description>
</identification>
<target>
<artifacts-zip>SU-example-mail.zip</artifacts-zip>
<component-name>sun-smtp-binding</component-name>
</target>
</service-unit>
<service-unit>
<identification>
<name>Simple file flow</name>
<description>Simple sender</description>
</identification>
<target>
<artifacts-zip>SU-example-file.zip</artifacts-zip>
<component-name>servicemix-file</component-name>
</target>
</service-unit>
</service-assembly>
</jbi>


5. Deploy the serviceassembly:

Just copy the create archive into the hotdeploy directory from servicemix and that's it. Now we only need to test it.

6. Testing the deployment:

For this open a mail client, add a new SMTP server (localhost:10025) and use that SMTP server to send an email to the specified address from the WSDL. If all goes correctly you'll see the content of the message being sent to the file directory specified.

The resulting file will look something like this (which is customizable):

<?xml version="1.0" encoding="UTF-8"?><jbi:message xmlns:jbi="http://java.sun.com/xml/ns/jbi/wsdl-11-wrapper" xmlns:msgns="http://opensourceesb/mailBC/" type="msgns:emailReceiverOperationRequest" version="1.0"><jbi:part>This is the content
</jbi:part><jbi:part>This is a mail to test sun smtp</jbi:part><jbi:part>Jos Dirksen <jos@test></jbi:part></jbi:message>

Pretty much the same scenario can be used for the other sun-jbi components.

On a side note, I'm also trying to get the jbi components from the Petals project to run on ServiceMix, but no luck so far.

2 opmerkingen:

Unknown zei

Can I directly put the wsdl4j.jar into the component package and not need to replace another one in servicemix/lib

Unknown zei
Deze reactie is verwijderd door de auteur.