Apache Struts 2 Plugin Registry > Home > Spring Plugin > Spring Session Components Workarounds |
Spring currently does not support session scoped beans/components out of the box. You can decide between singleton or prototype lifecycle, but you cannot have your beans bound to the session lifecycle of web applications. There are plans for integrating such a feature in the Spring 2.0 release.
We will try to point out some possible workarounds for your WebWork based applications. First we look at the general solutions found among the Spring community, dealing with HTTPSession and all that. After that we will discuss the special conditions and requirements found in XWork/WebWork and how that might affect possible solutions. We will show some XWork/WebWork specific solutions for the given problem.
![]() | The first milestone of Spring 2.0 (formerly 1.3) will be released the second week of December 2005. It is confirmed that it does contain Session Scope components using the Proxy (CGLIB or JDK) approach. |
Interface21 added support for session (and request) scoped beans in Spring 2.0. This approach creates a CGLIB or JDK Dynamic proxy of the session scoped bean using the org.springframework.aop.target.scope.ScopedProxyFactoryBean and setting the scopeMap to org.springframework.web.context.scope.SessionScopeMap.
Since the jars are backwards compatible simply build Spring and replace the jars shipped with WebWork. (Spring 2.0 M1 should be out by the time you read this.).
There are 2 ways to set this up depending upon whether or not XML simplification is used. The first method uses the traditional bean definitions and is useful to understand what is happening under the covers.
A modified applicationContext.xml for the shopping cart example using the traditional XML DTD is below.
A modified applicationContext.xml for the shopping cart example using the XML simplification is below.
You will also need to modify the web.xml to include the following filter.
A quite "clean" solution for web applications in general can be found at JA-SIG. The solution is well documented and can be found here. Below you will find a WebWork adoption of this solution.
WebWork is based on XWork, and XWork is not tied to the web layer. So when dealing with session scoped objects, WW users might want to use XWork's session abstraction features to keep their application independent from the web context. This is why we will discuss some XW/WW specific solutions below.
Here is a modified version of the TargetSource solution pointed out above that integrates with the existing WebWork session and doesn't require an additional filter or listener. Usage is pretty much the same, create an interface for your object and make sure that you always use that interface and not the underlying implementation or autowiring will fail. You can find more information on how to make this work by looking at the WebWorkTargetSource Shopping Cart Example.
TODO: Document
TODO: Document
The idea is to simply create a retrieve-or-create bean factory:
Example applicationContext setup (note that the session scoped bean has to be setup with singleton="false"):
Example action use:
For well known session scoped components, you might get more convenience by subclassing SessionBackedBeanFactory:
Again example applicationContext setup:
Example action use:
As said, the solution is very simple. You will get no ties to web layer, and the configuration is really simple, there is no need for proxy definitions in applicationContext.xml etc.
The main disadvantage is that you will not be able to wire session scoped beans directly into your actions, you will have to use the indirection via the session backed bean factory. And, as always when dealing with XWork session abstraction, you have to take care for a action context to be setup.
Does anyone have an implementation of this? (Eric Molitor)
The intention was a bit different for this one, so I tried to clarify headings. Nice idea, though ... (Rene Gielen).
The theory here is to create a custom Pointcut class that utilizes the ComponentConfiguration retrieved from the DefaultComponentManager (which loads the Component list from components.xml). The getClassFilter() matches anything that implements one of the Components in the ComponentConfiguration. The Pointcut is then registered as an advisor for all beans (AutoProxy via Springs DefaultAdvisorAutoProxyCreator). The Advice implementation looks at which Component is implmented and fetches the apporiate value out of the Session and calls the Components setter method.
TODO: Document, create example