Advance Java

Learn New things from Rixosys

Aspect oriented programming with Java

Aspect oriented programming with Java

The Basic Concepts of AOP

Software development has progressed a long way in the last 20 or 30 years. Twenty years ago it was not uncommon to find assembler and high-level code mixed together in the same (pages long) source code listing. However, we have improved awareness of the benefits of highly cohesive, but loosely coupled code, we have accepted the need for modularity in our systems, and we have adopted (within Java at least) Object Orientation as a basic software engineering technique.

However, I can still find myself looking at a source code listing and having to try to pull out the basic business logic, from all the "stuff" that sits around it.

All this "stuff", such as calls to logging components, authentication checks, exception handling, transaction management, etc, is all very important within any large software system. However, it adds to the fog that can surround a potentially simple piece of business logic.

Interestingly, one of the compelling arguments for making techniques such as Automatic Garbage Collection and Memory Management mainstream was that it separated out the implementation detail of managing memory from the business logic required by an application. Mixing the two made software more difficult to read, understand, and maintain; by placing the memory management in the background, the core business logic was that much simpler. This is essentially the premise behind AOP.

Let's take logging as an example. It's quite possible to design and implement a logging subsystem (indeed many have done this for Java including the Apache Log4J Logging framework).

However, the problem is that such a subsystem just provides the ability to log; it says nothing about where and when you should log system behaviour. To do this you most go through your software system and add such logging statements to appropriate points within methods. The end result is that the user of the logger needs to know that it is available, what its API is and, of course, must decide where to place the logging statements.

In turn the pure business logic methods are now augmented by additional (non-business related) method calls. As this process may be repeated for numerous such subsystems, the initially clean code may now be far more complex. This, in extreme cases, may make it more difficult to understand the underlying, relatively simple, business logic.

Logging here is an example of a cross cutting concern. That is, it is an aspect of the systems behaviour that cuts across many other modules. AOP allows Logging to be implemented as a completely self-contained module that is dynamically linked with the initial business logic in such a way that the original source code is unchanged. The self-contained, or stand-alone modules, are referred to as Aspects within AOP.

AOP programs can achieve the linking of the Aspect with the pure business logic code in a number of ways. For example, a pre-processor could be used to produce a combined program that is then compiled to produce the runtime executable (this was the approach originally used by AspectJ back in 2001). Another approach is to provide some form of post compilation modification.

In Java';s case, this means modification of the byte codes generated for classes such that links to an appropriate Aspect are incorporated into the byte codes. Such byte code weavers can be deployed during the build process or, if the weave model is per-class, during class loading. AspectJ has evolved from providing per-class bytecode weaving in 2002 to advanced load-time integration form 2005. The final approach is to augment the underlying execution environment (in Java's case the JVM) so that it understands AOP language elements directly.

AspectJ for Java

AspectJ is currently the most complete implementation of an AOP language for Java. In practical terms, it is an extension to Java that treats AOP concepts as first-class elements of the language. It allows aspects to be implemented as part of a Java based application using familiar Eclipse based tools.

As AspectJ is an extension to Java, Java is the implementation language for the constructs that comprise an Aspect. That is, you use Java to implement whatever behaviour the Aspect should provide. A set of rules is then used to determine how to weave the aspect into the main body of your Java application. These rules are implemented by pointcuts, join points, and advice. A pointcut specifies what join points there are. In turn, a join point defines where in a Java programs' execution the aspect should be applied and advice is the implementation of what to do at that point.

A simple example

As a simple example of an implementation of an Aspect let us implement the world's simplest logging Aspect. To do this we will log what happens during the execution of the classic Hello World Java program. For the purposes of this example, the Hello World program I shall use is presented below:


public class HelloWorld {

        public void print() {
                System.out.println("Hello World");
        public static void main(String [] args) {
                HelloWorld hw = new HelloWorld();

We can now implement an Aspect using AspectJ to provide for system logging. To do this I downloaded the AJDT: AspectJ Development Tools Eclipse Based plug-in (make sure you get the correct version for your Eclipse) from here. This provided me with not only the AspectJ runtime, but also various Wizards and browsers to support AOP development.

I then implemented my logging aspect within Eclipse. A screen dump of this is presented in Figure 1. Note that the file generated has a *.aj extension and that the implementation of the before and after advice is a piece of standard Java code. Before exploring what the implementation does, let us describe in plain English the purpose of this Aspect. Essentially this aspect specifies that before executing the HellWorld.print method, we will printout "Entering print" and after returning normally from the method we will printout "Existing print".

Screenshot showing an AspectJ Logger Aspect

In the example in Figure 1, the whole aspect is called Logger, log is the pointcut that implements the join point for this aspect and there are two advice points. Note that AspectJ makes the following pointcuts available:

  • Method call and execution
  • Constructor call and execution
  • Read/write access to a field
  • Exception handler execution
  • Object and class initialization execution

In the example above, I have defined a single execution pointcut. This specifies that on the execution of the HelloWorld.print method two advices should be applied. One before the method executes and one after the method has returned (other options include running after an exception has been thrown). The advice implements the behaviour of the aspect.

To run the combined application (i.e. the HelloWorld program and the Aspect) within Eclipse, I merely run the HelloWorld application as normal. However, the byte codes of the class and the aspect point cuts are dynamically weaved to create the following output:

Entering print
Hello World
Exiting print

Thus the core behaviour of the HelloWorld program and the behaviour of the logging Aspect have successfully been interwoven in the running system without the need to clutter up the original clean source code with calls to the logging subsystem.

Development methodology

A quick note on AOP development. It is clear to me that to identify the concerns which should be implemented as an Aspect is not necessarily straightforward nor is it directly covered by traditional software engineering methodologies. However, a fairly intuitive approach is to separate the AOP development process into some basic steps. These are essentially:

  • Aspectual decomposition: Decompose systems requirements in order to identify crosscutting and common concerns.
  • Concern implementation: Design and implement each concern as a separate aspect. Test and debug.
  • Aspectual re-composition: Identify the cross cut points within your application where the aspect should be applied.

See the References, below for more information on Aspect Oriented Software Development.