Recipe 15.1. Inheriting Pointcut DefinitionsProblemYou want to create pointcut declarations in an aspect that can then be reused using inheritance. SolutionCreate an abstract aspect. Define within the abstract aspect the reusable pointcut logic using the appropriate public, protected, or default access modifiers. Finally, inherit that abstract aspect into your subaspects to reuse the declared pointcuts. DiscussionPointcuts are subject to a similar set of rules as normal methods when using inheritance. If a pointcut is declared public, protected, or default, then its logic can be inherited and reused within other aspects. Example 15-1 shows an abstract aspect that provides a base for inheriting its defined pointcuts. Example 15-1. Using an abstract aspect to define reusable pointcut logicpublic abstract aspect BasePointcutDefinitionsAspect { public pointcut callPointcut( ) : call(void MyClass.foo(int, String)); }
Example 15-2 shows the ReusePointcutsRecipe aspect inheriting the callPointcut( ) declaration from the aspect in Example 15-1. Example 15-2. Reusing pointcut logic from the abstract base aspectpublic aspect ReusePointcutsRecipe extends BasePointcutDefinitionsAspect { // Advice declaration before( ) : callPointcut( ) && !within(ReusePointcutsRecipe +) { System.out.println( "------------------- Aspect Advice Logic --------------------"); System.out.println( "In the advice attached to the call point cut"); System.out.println( "Signature: " + thisJoinPoint.getStaticPart( ).getSignature( )); System.out.println( "Source Line: " + thisJoinPoint.getStaticPart( ).getSourceLocation( )); System.out.println( "------------------------------------------------------------"); } } Figure 15-1 shows the static structure of the inheritance relationship defined in Examples Example 15-1 and Example 15-2. Figure 15-1. Inheritance between aspectsThe ability to define abstract aspects that encapsulate just pointcut logic opens up the possibilities for pointcut libraries. This powerful concept is useful in large-scale enterprise environments. Specific pointcuts for patterns of weaving throughout the application can be defined and reused without having to repeat the generic pointcut logic over and over again. See AlsoRecipe 4.1 shows the definition of the call(Signature) pointcut; the within(TypePattern) pointcut is described in Recipe 9.1; the NOT(!) operator is described in Recipe 12.4. |