Q: So does Axis support sessions?

A: Yes. We have a session abstraction which allows an extensible set of underlying implementations - take a look at the class org.apache.axis.session.Session for details. In particular, we currently support sessions based on HTTP cookies and also transport-independent sessions based on SOAP headers. It is up to some handler on the request chain to set up an appropriate Session implementation and attach it to the  MessageContext  with  MessageContext.setSession()  so that anyone who wants to use session semantics can get at it.

Q: Cool, SOAP header-based sessions? How do I make that work?

A: There is a Handler class called "org.apache.axis.handlers.  SimpleSessionHandler " which implements this functionality. You need to include this handler in the request and response flows of both your client and your server. Take a look at our session test ( test.session.TestSimpleSession ) for an example. Regarding use in clients, look at AxisClientConfiguration.

Q: What else can I do with sessions?

A: Any time after the session context has been established, calling getSession() on the current messageContext will obtain you a reference to a Session object. You may use this object like a Hashtable to store arbitrary data associated with this Session. For instance, on one request you might extract the caller's name and address from a database (an expensive operation), and then cache them in the Session object for fast access on subsequent invocations from the same caller. This functionality can be used either by custom Handlers or by your backend service object itself.

Q: Is it standard to maintain a SOAP session with HTTP Cookies ?

As SOAP is transport agnostic, using HTTP cookies to maintain a session is not part of the standard. However, HTTP Cookies is the most widely used method to maintain session during SOAP calls and it has been integrated in the WS-I Basic Profile 1.0 Specification. This reduces the interoperability problems.

Most of the SOAP implementations (Apache Axis, IBM Websphere, .Net, ...) support it.

To conclude, it is not exactly a standard but it is a de facto standard.

Extract from WS-I Basic Profile 1.0 Specification :

Q: How can I read the session cookie ?

Http Cookies are hold after the invocation by the MessageContext properties HTTPConstants.HEADER_COOKIE and HTTPConstants.HEADER_COOKIE2.

Sample to display the cookies :

// Enable client side session
binding.setMaintainSession(true);

// Invoke service
binding.aMethod();

// Read Cookies
MessageContext messageContext = binding._getCall().getMessageContext();
String cookie1 = (String) messageContext.getProperty(HTTPConstants.HEADER_COOKIE);
String cookie2 = (String) messageContext.getProperty(HTTPConstants.HEADER_COOKIE2);
System.out.println("cookie1 : '" + cookie1 + "'");
System.out.println("cookie2 : '" + cookie2 + "'");

Sample of result :

cookie1 : 'JSESSIONID=FEC9990323740BFD0FECF965F1BCC09A'
cookie2 : 'null'

Sample of client side sessions

To enable stateful invocations on the client, you have to call setMaintainSession(true) on the Stub

Sample :

HelloWorldServiceLocator helloWorldServiceLocatorForJohnDoe = new HelloWorldServiceLocator();
HelloWorldBindingStub bindingStubForJohnDoe = (HelloWorldBindingStub) 
      helloWorldServiceLocator.gethelloWorldBinding();

bindingStubForJohnDoe.setMaintainSession(true);

// Say hello will create a server side session 
String helloJohnDoe = bindingStubForJohnDoe.sayHello("JohnDoe");
System.out.println("helloJohnDoe : " + helloJohnDoe);

// Say good bye will use the same server side session
String goodByeJohnDoe = bindingStubForJohnDoe.sayGoodBye("JohnDoe");
System.out.println("goodByeJohnDoe : " + goodByeJohnDoe);

(!) Client side session support relies on http cookies, all the cookies created by the server (Set-Cookie header in the http response) are kept by the client and re-sent for each following invocation.

(!) The internal behavior of client side session support is to store the cookies as an instance variable of the ServiceLocator (via the AxisEngine)

Sample of multi client side sessions

A SOAP client may have to open several sessions at the same time. To do this, you have to instantiate one ServiceLocator/Stub per session.

Axis supports multi client side sessions with an important restriction : you must instantiate one ServiceLocator per session (ie per Stub).

Sample of mixed invocations :

HelloWorldServiceLocator helloWorldServiceLocatorForJohnDoe = new HelloWorldServiceLocator();
HelloWorldBindingStub bindingStubForJohnDoe = (HelloWorldBindingStub) 
      helloWorldServiceLocatorForJohnDoe.gethelloWorldBinding();
bindingStubForJohnDoe.setMaintainSession(true);

HelloWorldServiceLocator helloWorldServiceLocatorForJohnSmith = new HelloWorldServiceLocator();
HelloWorldBindingStub bindingStubForJohnSmith = (HelloWorldBindingStub) 
      helloWorldServiceLocatorJohnSmith.gethelloWorldBinding();
bindingStubForJohnSmith.setMaintainSession(true);

// Open the JohnDoe session
String helloJohnDoe = bindingStubForJohnDoe.sayHello("JohnDoe");
System.out.println("helloJohnDoe : " + helloJohnDoe);

// Open the JohnSmith session
String helloJohnSmith = bindingStubForJohnSmith.sayHello("JohnSmith");
System.out.println("helloJohnSmith : " + helloJohnSmith);


// Reuse the JohnDoe session
String goodByeJohnDoe = bindingStubForJohnDoe.sayGoodBye("JohnDoe");
System.out.println("goodByeJohnDoe : " + goodByeJohnDoe);

// Reuse the JohnSmith session
String goodByeJohnSmith = bindingStubForJohnSmith.sayGoodBye("JohnSmith");
System.out.println("goodByeJohnSmith : " + goodByeJohnSmith);

/!\ The ServiceLocator is a heavyweight object that holds the HTTPSender. However, as the ServiceLocator holds the session data (the cookie), it can not be shared by several Stubs.

Q: Is it possible to maintain a session for a long duration with Axis Client ?

It can be necessary to maintain a web service session for a long duration (e.g. between two user interactions).

Maintaining the session between SOAP invocations requires to keep a reference on the client Stub. The Stub is a lightweight component that can be kept alive for a long time.

(!) Note that the Stub is lightweight in the sense that :

/!\ Note that maintaining multi client sessions for a long duration is more complex because ServiceLocator can not be reused. You must instantiate one ServiceLocator per session (ie per Stub). Due to this, the memory footprint will be much more important. In suc a case, using the CommonsHTTPSender instead of the HTTPSender will add a big overweight.

FrontPage/Axis/SessionSupport (last edited 2009-09-20 22:48:09 by localhost)