Spring-Enhanced Abstract Beans

The Spring framework provides a mechanism for replacing abstract bean methods with bean instances defined in the Spring configuration context. This functionality is provided by the 'lookup-method' element in the Spring context.

In this article we present a utility that combines the functionality of the 'lookup-method' element with the convenience of Spring by-name autowiring.

Implementing bean attributes for use in Java-bean aware environment such a Spring context consists of 2 steps:

  • defining a private variable for the attribute
  • implementing the get{Attribute}() and a set{Attribute}() whose implementations are trivial

As trivial as it is, this task becomes tedious for several beans and attributes. The approach employed in the Tapestry web framework is much easier:
When a bean attribute is read or set, the framework looks for the corresponding  methods get{Attribute}() and set{Attribute}() in the component or page. If these methods are abstract, the frameworks intercepts the call and dynamically provides a default implementation for them.

This functionality is already provided by Spring with the use of the 'lookup-method' element.
E.g. in the following bean definition:

<bean id="service" class="service"/>
<bean id="user" class="User">
  <lookup-method name="getService" bean="service"/>
</bean>

calls to the bean "user" abstract method getService() will return the "service" bean instance.

Although very close to the desired behaviour, the approach can be further enhanced with the convenience of Spring's autowiring by-name. In this case the mapping of bean instance to method name is not needed. The bean is defined in the Spring context as any other concrete bean implementation. Then for every abstract method get{Attribute}, a bean instance with ID "Attribute" is looked up in the Spring context. Similarly a call to set{Attribute} will assign the bean with ID "Attribute" to the bean's "Attribute" property.

Spring does not provide such a utility, but implementing this is not very hard. This is the purpose of the BeanContextFactory bean factory. It enhances a bean's implementation by replacing abstract bean get/set methods with concrete implementations using CGLIB. It will then perform autowiring by-name on the bean and return the configured bean instance.

E.g. for context ctx.xml:

<bean id="bean" class="Bean">
  <property name="value" value="result"/>
</bean>
and an abstract bean:
public static abstract class Example {
  public abstract Bean getBean();
  public String call() {
    return getBean().getValue();
  }
}
 
Example use:
Example proxy = (Example)BeanContextFactory.get(Example.class,
  new ClassPathXmlApplicationContext("ctx.xml")); proxy.call();
 

The last call returns the string "result".

Articles

Patterns of design and methodologies are documented in this series of articles which targets J2EE systems.

   Integrating Presence into J2EE Environments

User presence is the domain normally represented by instant messaging systems, and while libraries supporting presence have existed for Java for a while, presence isn't normally represented in J2EE. This article shows you how to change that.

   Spring-Enhanced Abstract Beans

The Spring framework provides a mechanism for replacing abstract bean methods with bean instances defined in the Spring configuration context. This functionality is provided by the 'lookup-method' element in the Spring context.

In this article we present a utility that combines the functionality of the 'lookup-method' element with the convenience of Spring by-name autowiring.

   EJB Container Events in the JOnAS Application Server

The following describes a JOnAS service that registers an MBean listener to EJB container registration/unregistration events. These events are generated when an EJB jar file is deployed/undeployed. Handling these events allows running custom setup/cleanup code when EJBs are added or removed respectively from the EJB container.