![]() | Draft |
|---|---|
This is a first draft of this chapter. It is technically accurate, but not in the style or state of the final revision. |
AOP (Aspect Oriented Programming) is one of the most interesting ways to abstract programming since Object Oriented programming was developed. Just as Object Oriented programming allows for better abstraction and code reuse, AOP allows for abstraction and code reuse in many areas that it just isn't possible to use Object Oriented programming. These areas are typically called “cross cutting concerns”. An example of a “cross cutting concern” could be the repetitive code around gathering statistics, managing database connections, remote connections, and many other similar things. Using AOP these items can be separated from each method and applied through AOP using pointcuts. A pointcut definition let's advice be applied to a “join point”. A join point can be a field, constructor, or method, but Spring only supports method join points. Advice can be used to inspect or change parameters as they are set, log information or statistics, throw exceptions, and even completely bypass the intercepted method.
Spring uses either Java Dynamic Proxies (http://java.sun.com/javase/6/docs/api/java/lang/reflect/Proxy.html) or CGLIB to dynamically weave advice into classes. Java Dynamic Proxies are part of the Java language since version 1.3. So it doesn't require any external libraries, but to use CGLIB it must be included in the classpath. Spring allows AOP pointcuts and advice to be defined in XML or using AspectJ (http://www.eclipse.org/aspectj) annotation-style. Of course to use AspectJ annotation-style, you'll have to be using Java 5 or higher. So if you're using JDK 1.4, you'll have to use XML based pointcut and advice configuration. Spring still uses Spring's AOP to weave in the advice for either of these, but for AspectJ it will process pointcuts and determine what join points (methods) to apply advice to using the AspectJ libraries. Dynamic Java Proxies can only be applied to interfaces, but CGLIB can be used to dynamically weave advice into a class by transforming the class' byte code. Byte code transformation lets advice be applied not just to interfaces, but to any class. Although it's highly encouraged to use interfaces wherever possible for flexibility since it helps decouple a concrete implementation from where it is actually used. Spring AOP can only be used to advise methods. Which is very powerful and AspectJ annotation-style AOP gives a great deal of control when defining pointcuts. This is actually a subset of all the pointcuts AspectJ supports. I would recommend using AspectJ annotation-style AOP in Spring whenever possible because if you ever have a need for more complex pointcuts around fields or constructors, all your rules are still valid and you easily switch to use AspectJ at compile-time or load-time to weave advice into classes. Compile-time weaving modifies a classes byte code to apply advice during the build process, and load-time weaving modifies the byte code as it's loaded by the class loader. Spring 2.5 provides support to make using AspectJ load-time weaving even easier and it will be covered in a section later in this chapter.
As you begin to use AOP more, you may wonder how you can keep track of how your codes behavior may change because of AOP pointcuts and advice. The Spring IDE for the Eclipse IDE continues to keep adding more AOP support to help with this. AspectJ also has a plugin for Eclipse, but for most people the Spring IDE should help enough and will also provide a lot of value managing beans and classes. The Spring IDE helps identify pointcuts and what advice goes with the pointcut. You can click on the marker identifying this code is part of a pointcut and it will take you to the advice.
The concept of pointcuts and advice are part of the overall AOP concept. So, these ideas can be applied to different AOP frameworks. Although any specifics will be about Spring AOP unless otherwise indicated.
Table 6.1. Spring Supported Pointcuts
| Pointcut Type | Description |
|---|---|
| args | A method matching to the specified arguments. |
| bean | Matches bean names. (New Feature in Spring 2.5) |
| execution | The execution of a method. |
| target | A join point where the target object is an instance of this class. Typically used to bind a value to advice method. |
| this | A join point where the currently executing instance of this class. Typically used to bind a value to advice method. |
| within | A join point matching a package. |
| @annotation | Any join point that matches this annotation. |
| @args | A join point matching annotations of arguments. |
| @target | A join point where the target object has this annotation. |
| @within | A join point where the executing code's class has this annotation. |
Table 6.2. Spring Supported Advice
| Advice Type | Description |
|---|---|
| before | Applies advice before a method is called. |
| after | Advice is always applied after a method, regardless of how it returns. |
| after returning | Applies advice after a method returns successfully. |
| after throwing | Applies advice after a method throws the designated Exception. |
| around | Advice can be given before and after a method executes. |
Table 6.3. Pointcut Boolean Operators
| Boolean Operator | Description |
|---|---|
| && | Logically combines two pointcuts as a boolean AND. |
| || | Logically combines two pointcuts as a boolean OR. |
| ! | Reverses the boolean result of a type pattern. If the pattern was true, it would then be false with this operator in front of it. |
Table 6.4. Wildcards
| Wildcard Symbol | Description |
|---|---|
| * | Matches any number of characters as part of a pattern. |
| .. | In package definitions, it matches any number of directories. In an argument definition, it matches any number of arguments. |
| + | When matching a class, this added as a suffix matches all subclasses. |