Identity Crisis

Jan 19th, 2010 | By | Category: architecture

It is hard to imagine going through life without having a name.  This dictum applies to the world of objects as well.  But an object’s identity is a little more complex than the normal name. I want to talk about some of these nuances in this post. By the way, I do assume a rudimentary knowledge of Spring in some of the post. 

 I would refer you first to the “Dichotomy of Objects” post to see how we roughly taxonomize the classes into two categories viz. data containers and strategy objects. We would be coming up with different strategies for managing the identities of these two types of objects. 

Data Containers

All domain objects must have an identity since they are usually serialized into some persistence mechanism such as a database. Hence a retrieval of these would need the identity to be known. For instance, how do we get back the Savings Account object with ID 12345? By retrieving the corresponding row in the database and populating a new object with that information.  

In most projects, domain objects typically implement an interface that has a method such as getId(). This ID can be a string, a number or whatever else depending on the design of the project.  But all data containers typically don’t need an ID. Data container objects such as HttpServletRequest can survive without an ID. But sooner than later when the data container needs to be persisted (as is the case with domain objects), we would need an ID. For instance, HTTP session objects need a session ID so that we can refer back to the same session at a later time. 

There are patterns around establishing an identity for the domain object. But it is not my intention to delve into these in this post. Instead I am going to restrict my discussion to strategy objects. 

Strategy Chains & The Request Processing Life Cycle

Strategy objects are an encapsulation of some operation that is being performed in an application. All applications process a request. In the request processing cycle, a multiple data containers are created for each request. These are then passed along in the strategy chain till the request is ultimately serviced.  The entire application request processing cycle can thus be viewed as a series of strategies that are lined up one after the other for execution. Consider the following sequence in a web application for maintaining a user database:

UserController -> UserService -> UserDao -> user table in a database. 

The request goes through the user controller that musters the input parameters and sends it over to the user service. User service starts a transaction and invokes the UserDao for doing the persistence related activity. In this scenario, the three classes UserController, UserService and UserDao are strategies that are lined up for execution. They should be ideally set up during the start up of the application and the “strategy chain” should be re-used for each request. Now for every new request, an existing UserController needs to be hooked to the input and the chain started so that the response would be produced. This is how typically a Spring based application gets set up. 

Strategy Chains & Strategy Catalog

So if we have this strategy chain that is being used in the application, why would the individual strategies in the chain need an identity? In short, why would each strategy in a spring config need an ID? The answer to that is obvious. They need an Id if they need to be re-used multiple times in different “strategy chains”. The ID of the strategy exists in the spring config file. It does not exist in the strategy itself.

For instance take the definition :

<bean id=”x” class=”com.bla.UserController”>

</bean> 

The ID “x” does not make sense outside of the spring config file and is not at all “coded inside” the UserController class. Browse the class and you wont see any awareness of the ID “x”.  So the strategy identity lives inside the spring file for the most part. I call a spring file (or an equivalent file in other frameworks such as struts etc.) as a service or strategy catalog.  All strategies make it into the strategy catalog and are wired there. Hence they need an identity within the context of the catalog so that the same instance can be re-used across multiple strategy chains. Here the identity of the strategy is tied to a strategy catalog. Strategy catalogs are useful things. Besides wiring, they are extremely useful in programs that allow the user to change the application behavior dynamically. (This is a big topic that is beyond the scope of the post) UDDI is a web service catalog in a manner of speaking. 

AOP & Class Categorization

It is not my intention to talk about AOP here. Suffice it to say that we “decorate” classes with “aspects” which implement various “horizontal services” such as logging, security etc. Too many quoted words in the sentence above. But it take too much time for me to explain all these terms in this post.  The key task in AOP is to identify all the classes that need to have an AOP concern attached to them. Here is where the strategy catalog comes handy since it contains all the classes that need to potentially be decorated by AOP wrappers. 

For instance it would be convenient to identify all secure classes so that the methods of these classes can be protected by security layers. How do we do that in a strategy catalog? 

Interface and Class name as Identity

One of the interfaces implemented by a class could be used to identify strategies. For instance all classes that implement the CacheableService interface may have to be surrounded with a cache wrapper. In that context, an interface can give an identity to a strategy. This would of course not be a unique identity but would serve to categorize the class so that a particular action (such as surrounding it with a cache wrapper) happens to it.

Interface as an identity is pretty useful in implementing AOP frameworks.  But what if the interface itself is extremely generic. We can have an interface such as SearchService for instance that can be utilized to retrieve search results from diverse resources such as databases, EAI and the like. What if each one of these classes need special unique treatment ? In that situation, we care not just about the interface but the actual implementation class. To go back to the security example, EAISearchService may have different security requirements from DatabaseSecurityService. The actual class name needs to be known so that we can accordingly use different AOP wrappers. 

Class name is thus a very useful way of identifying the class sometimes.

Identity per Invocation

The final complexity comes in when there is the same class behaving in vastly different ways depending on the parameters passed to it. Consider the following class for instance. 

class WebServiceInvocation {

    public WebServiceResponse execute(WebServiceRequest request){

       // call a different web service depending on the field webServiceToInvoke in the WebServiceRequest.

    }

}

This class executes a web service depending on the super generic WebServiceRequest that is passed to it. The web service call varies depending on the request. There is a field inside WebServiceRequest called “webServiceToInvoke”. Depending on the value of that field, the WebServiceRequest invokes various web services.  Now each one of the web services may have different security requirements. How do we go about decorating it with different security AOP layers ? This would depend on the actual invocation rather than the identity of the class itself.  

To solve this problem, we come up with an interface called ServiceInvocation which is implemented by the parameter that is passed to the WebServiceInvocation class’s execute method. The interface is designed as follows:

public interface ServiceIdentity {

  public String getServiceIdentity();

}

The service identity of the particular invocation is revealed by the object. In this case, the WebServiceRequest class can trivially implement the service identity interface as follows:

public class WebServiceRequest implements ServiceIdentity {

  public String getServiceIdentity() {

    return webServiceToInvoke;

}

}

The AOP wrapper would then have to first interrogate the Service Identity to determine the actual context of the invocation before choosing the right AOP wrapper to decorate the service. This must be done during runtime. I have written a Spring AOP advisor to implement this functionality using Spring AOP. 

Summary

We started off with the need to identify a service in a service catalog. From then on we covered categorization of services for AOP. This categorization is either accomplished by interface, the class name or the argument passed to it.

Be Sociable, Share!

 Raja has been blogging in this forum since 2006. He loves a technical discussion any day. He finds life incomplete without a handy whiteboard and a marker.


Leave Comment