Submitted on December 20, 2006 - 22:02.
Since Apache Axis2 has been developed keeping WSDL 2.0 concepts in mind, it has built-in support for all the eight Message Exchange Patterns (MEPs) defined in WSDL 2.0. An MEP describes how communication occurs between two entities, such as, how the client interacts with the server. Some of the pre-defined MEPs in WSDL 2.0 are listed below:
Note : A particular MEP is defined with respect to the server. For example, in the case of In-Out MEP, there is a message coming into the server, and then there is a message going out from the server. So In-Out MEP is exactly equal to the request-response scenario defined in WSDL 1.1. Similarly, Out-Only MEP is a message sent out from the server but does not have a corresponding incoming message or response.
In most of the applications we work with, a client is responsible for starting the conversation to which the server responds. So most of the today's Web service applications support either In-Out or In-Only MEPs. However, in the case of Out-Only the server will start the conversation. In other words, server will send out the message to the client. What is the typical use case of having a service which implements Out-Only MEP? Out-Only MEPs are useful for the applications that need eventing / notification.
A good real time application to which Out-Only MEP is applicable is a 'stock quote application', where you can register to the system with set of rules. And when a rule is satisfied the application will notify the client. So client does not need to poll to get to know what is going on. The client application will automatically get an update and can then act on it.
In this case you need to understand that there should be a running instance of “something” in order to have this MEP. In the case of In-Out and In-Only MEPs what happens is that a client sends the message to the server, at which point the service instance will get called. Then service can process the message and send the response if any. However, in Out-Only case the situation is quite the opposite, the service needs to send a message without having received a message first.
Services with In-Out and In-Only can be considered as “sleeping” service, since only when the server receives a message it wakes up the service and gets the service to process the message. But in the case of Out-Only service, service needs to be active all the time. Therefore, service which has Out-Only MEP can be called an "Active" service.
When implementing a service as an active service you need to remember to make the service active yourself. If you want to have an active service then you need to start a thread when you deploy the service, thus making it active.
There are two main ways of writing an active service in Axis2:
This tutorial will explain writing an active service with ServiceLifeCycle class.
Note: Creating a thread is not the recommended route usually. A thread may kill the CPU performance (an infinite thread can take up to 100% of CPU usage), therefore, the best approach is to use something like "TimerTask". However, in this sample We have used a thread just to show the concepts and usage of this particular MEP.
As the first step let's take a very simple sample application. We assume that there is a service whose job is to notify the users with a random number for each specified time interval. And further assume that client needs to register with the server in order to receive those messages. Therefore, the service will have two operations, one is for users to register with the server and other is actually send the messages to the registered clients.
For better understanding of concepts and their applications, let's try to write the service in few steps. Step1 and Step2 are all about general Web services. Service implementation class has assumed that at the service deployment time user list (an array list of user) will be populated using ServiceLifeCycle implementation class. So whenever some one registers into the system, then new user will be added to the same list. When server shutdowns, all the data will be saved into a file, and next time, user list will be populated using that file, so that user does not need to register twice.
Step 1 : User Registration Method
public void register(String notifyEpr) {
MessageContext msgCtx = MessageContext.getCurrentMessageContext();
AxisService service = msgCtx.getAxisService();
((ArrayList) service.getParameterValue("USER_LIST")).add(notifyEpr);
}
Complete source code is available in ActiveService.java found in the sample code1.
Step 2 : Writing ServiceLifeCycle Implementation Class.
The idea of ServiceLifeCycle class is to provide a way to mange the life cycle of the service. And one thing to note here is that service life cycle management is completely different from service session management. Here the idea is to obtain a way to update services when the system is starting up and shutting down. Therefore, once the services.xml has an entry for implementation class of ServiceLifeCycle interface, Axis2 will call that particular implementation class whenever server starts up and shuts down. You can use this mechanism to fire up threads, start database connection etc. So here I have used the same technique to fire up the Service Thread and to pre-populate the users list.
Complete source can be found in ActiveServiceLifeCycle .java in the sample code1.
Step3 : Writing Service Thread
This is the most important part in the tutorial where we implement Out-Only MEP invocation logic. As stated above Out-Only MEP is sending messages out from the server or simply running client inside the service implementation logic. Service Thread is a thread where we have overridden its run method to run forever (while (true)), so now the thread will be an active one. The logic inside is to generate a random number first, and then create a payload (message SOAP body), create a ServiceClient and send the request. That basically sums up the Out-Only MEP.
If you looking into the code you will realize that what I have used is exactly the same code that you have used to invoke In-Only MEP.
The following list of items can be considered as the key points in the implementation logic of ServiceThread class.
notify.The complete code is available in ServiceThread.java found in sample code1 of this tutorial.
You can easily deploy the ActiveService.aar (download sample source code1) file or you can create your own .aar file just compiling the source. You can deploy the service either into any application server or to SimpleAxisServer.
To demonstrate the full scenario, I have written a sample service (ClientService) for the client side as well. The service only contains one method called notify and it will print out the message it gets. You can deploy either ClientService.aar file or you can build your own service archive file by compiling the code. Then you can deploy that into the same application server or where ever you need it.
Now you have both server side service and client side service up and running. Next step is to register the client with the server. You can do that in two ways provided you have deployed the ActiveService service in an application server such as Apache Tomcat
In order to register, you first need to know the service EPR (End Point Reference) of the client service. Let's say the EPR of client service is http://localhost:7070/axis2/service/ClientService
Then you can register the client using REST API as follows (assuming server is running in 8080);
http://127.0.0.1:8080/axis2/rest/ActiveService/register?notifyEpr=http://localhost:7070/axis2/service/ClientService
Now watch the client side console and what you are getting in it. It will print a random value, something similar to what I received- 8766030962797217830 at every 2 or 3 seconds.
This means that ActiveService is notifying the client service and is acting as an Out-Only service.
The sample demonstrate how to implement Out-Only service with Apache Axis2. You can improve it to use any advanced applications. It's important you remember the concept which will help you to write your own active services.
Anybody tried to use the samples
Hi,
I have tried to use the sample provided by the article and followed the steps described above.
Both services are deployed on Tomcat, as i am able to see them with the axis2 web application.
I mention that when i registered the client with the server i got a blank page.
However if i monitor the messages that are exchanged via SOAPMonitor i cannot see any messages to be sent from the ActiveService to ClientService.
What is meant by client side console, because i don't get any?
Has anyone tried to use the sample applications and succeeded?
I apologize if my questions are hilarious, i am new to web services and axis2 for that mater.
Best regards,
Vlad.
I tried...
Didn't go so well for me either. I did the same where I installed both the client and server services in axis2 1.2 within tomcat6 and, using
http://localhost:8080/axis2/services/ActiveService/register?notifyEpr=http://localhost/axis2/services/ClientService
as the URL to register, I get the following exception:
java.lang.StringIndexOutOfBoundsException: String index out of range: -25
java.lang.String.substring(Unknown Source)
java.lang.String.substring(Unknown Source)
org.apache.axis2.engine.HTTPLocationBasedDispatcher.parseRequestURL(HTTPLocationBasedDispatcher.java:106)
org.apache.axis2.engine.HTTPLocationBasedDispatcher.findOperation(HTTPLocationBasedDispatcher.java:52)
org.apache.axis2.engine.AbstractDispatcher.invoke(AbstractDispatcher.java:100)
org.apache.axis2.transport.http.util.RESTUtil.dispatchAndVerify(RESTUtil.java:138)
org.apache.axis2.transport.http.util.RESTUtil.processURLRequest(RESTUtil.java:95)
org.apache.axis2.transport.http.AxisServlet$ProcessRESTRequest.processURLRequest(AxisServlet.java:776)
org.apache.axis2.transport.http.AxisServlet.doGet(AxisServlet.java:238)
javax.servlet.http.HttpServlet.service(HttpServlet.java:690)
javax.servlet.http.HttpServlet.service(HttpServlet.java:803)
Did some testing and it appears that the notifyEpr parameter value cannot be any greater than 25 characters or else an exception is thrown by Axis2. Has anyone else run into this problem?
V/R,
Jeff
Please try Axis2-1.3RC2
Hi,
Can you try this with Axis2-1.3RC2 (http://people.apache.org/~deepal/axis2/1.3-RC2/)please . I believe this problem is fixed in this release. Sorry for the inconvenience.