Title: Module SEO01 Software Evolution
1Module SE-O-01Software Evolution
Topic 7 Aspect Oriented Software Evolution
2Contents
- Introduction
- Crosscutting concerns
- Core concepts of AOP
- Implementing AOP
- Aspectual refactoring
3What is AOP?
- The programming paradigm which attempt to aid
programmers in the separation of concerns,
specifically cross-cutting concerns, as an
advance in modularization wikipedia
4Separation of Concerns (SoC)
- Separation of Concerns (Dijkstra, Parnas)
realization of problem domain concepts into
separate units of software. - There are many benefits associated with having a
concern of a software system being expressed in a
single modular unit. - Better analysis and understanding of systems,
easy adaptability, maintainability and high
degree of reusability. - Crucial to software development.
- How to best achieve it is an open issue.
5Contents
- Introduction
- Crosscutting concerns
- Core concepts of AOP
- Implementing AOP
- Aspectual refactoring
6Crosscutting concerns
- In OOP, decomposition (through mechanisms
provided by current languages) is one-dimensional
focusing on the notion of a class. - In large systems, interaction of components is
very complex. - Current programming languages do not provide
constructs to address certain properties in a
modular way. - OOP cannot address the design or implementation
of behavior that spans over many modules (often
unrelated).
7Crosscutting concerns
- Certain properties cannot be localized in single
modular units, but their implementation cuts
across the decomposition hierarchy of the system. - These properties are called crosscutting
concerns, or aspects.
8An initial picture of crosscutting
Component
Component
Component
9A first example
- In this example, authentication, contract
checking and logging are tangled with the core
operation (methods) of the component (class)
public class BusinessLogic data members
for business logic data members for
authentication, contract checking and
logging public void someOperation
// perform authentication // ensure
preconditions // log the start of an
operation perform core operation
// authentication // ensure
postconditions // log successful
termination of // operation //
more operations similar to the above
10Some observations
- Two issues are of interest here
- Implementation for authentication, contract
checking and logging is not localized. - Code spans over many methods of potentially many
classes and packages. - Implementation of someOperation() does much more
than performing some core functionality. - It contains code for more than one concerns.
11Symptoms of crosscutting
- Crosscutting imposes two symptoms on software
development - Code scattering implementation of some concerns
not well modularized but cuts across the
decomposition hierarchy of the system. - Code tangling a module may contain
implementation elements (code) for various
concerns. - Scattering and tangling describe two different
facets of the same problem.
12Where does crosscutting originate?
- There might not always be a one-to-one mapping
from problem domain to solution space. - Requirements space is n-dimensional, but
Implementation space is one-dimensional (In OOP
everything must belong to a class)
Implementation
Requirements
R1
C1
R2
C2
R3
C3
R4
C4
scattering
tangling
13Tyranny of dominant decomposition
- The fact that there is a single axis of
decomposition has been termed decomposition
tyranny. - Decomposition tyranny is the source of
crosscutting. - The decomposition tyranny (and crosscutting)
apply to artifacts across the life-cycle of
software (not confined to implementation)
14Negative implications of crosscutting
- As a result of crosscutting, the benefits of OOP
cannot be fully utilized, and developers are
faced with a number of implications - Poor traceability of requirements Mapping from
an n-dimensional space to a single dimensional
implementation space. - Lower productivity Simultaneous implementation
of multiple concerns in one module breaks the
focus of developers. - Strong coupling between modular units in classes
that are difficult to understand and change.
15Negative implications of crosscutting
- Low degree of code reusability. Core
functionality impossible to be reused without
related semantics, already embedded in component.
- Low level of system adaptability.
- Changes in the semantics of one crosscutting
concern are difficult to trace among various
modules that it spans over. - Programs are more error prone.
- Difficult evolution.
- Crosscutting affects the quality of software.
16Contents
- Introduction
- Crosscutting concerns
- Core concepts of AOP
- Implementing AOP
- Aspectual refactoring
17We would like to move from this picture
Component
Component
Component
18to this one!
We want to provide a new unit of modularity, that
explicitly captures a crosscutting concern.
aspects
component
component
component
19Structure of an AOP program
- In AOP, program components aspects
join point model JPM. - JPM rules are not part of component definitions
(they may be placed in aspect definitions or in
separate definitions).
aspect A whenever ltconditiongt perform
ltactiongt
class C1 ...
class C2 ...
class C3 ...
20Join point models
- A JPM defines three things
- When the advice can run. These are called join
points because they are points in a running
program where additional behavior can be usefully
joined. - A way to specify (or quantify) join points,
called pointcuts. Pointcuts determine whether a
given join point matches. - A means of specifying code to run at a join
point. This code is called advice, and can run
before, after, and around join points.
21Core AOP concepts
whenever execution reaches this point
or this point
execute advice code!
C1
C2
C3
- In program P, when condition C occurs, execute
action A. - Condition (C2 or C3) specified by a pointcut
22Obliviousness principle
A
C1
C2
C3
- Note that neither C2 nor C3 make calls to A !
- Even though components C2 and C3 are enhanced by
the aspectual behavior defined by A, they are not
aware of this (nor have they been implemented to
accept such enhancements). - Contrast this with procedure calls or message
passing.
23Contents
- Introduction
- Crosscutting concerns
- Core concepts of AOP
- Implementing AOP
- Aspectual refactoring
24Putting everything together - weaving
(Core Functionality Classes)
Compiler
(Crosscutting Behavior Aspects)
Equivalent program in the original language
(Composition Rules)
25Runtime combining
public class BusinessLogic data members
for business logic public void someOperation
perform core operation // more
operations similar to the above
compiler
public aspect Authenticator data members
for authentication public void authenticate()
compiler
Runtime
compiler
public aspect Logger data members for
logging public void log()
compiler
public aspect ContractChecker data members
for contract checking public boolean
precondition() public boolean
postcondition()..
26Benefits of AOP
- Provisions of AOP should be compared with those
of other paradigms, such as OOP. - Clear (two-dimensional) separation of concerns.
- Less tangled and less scattered code.
- Improves modularity Makes concerns easier to
manipulate (reason about, debug, change, and
reuse). - Higher level of abstraction.
- Good maintenance and higher level of
adaptability. - AOP is not bound to OOP.
- In the literature you can find proposals for AOP
with functional, logical and procedural
programming.
27This is what I meant by focusing ones
attention upon a certain aspect it does not
mean completely ignoring the other ones, but
temporarily forgetting them to the extend that
they are irrelevant for the current topic. Such
separation, even if not perfectly possible, is
yet the only available technique for effective
ordering of ones thoughts that I know of. E.
W. Dijkstra, A Discipline of Programming,
1976 last chapter, In retrospect
28Contents
- Introduction
- Crosscutting concerns
- Core concepts of AOP
- Implementing AOP
- Aspectual refactoring
29Aspectual refactoring
- refactoring an object-oriented legacy system in
an aspect-oriented way - makes it possible to reorganize code containing
crosscutting concerns to get rid of code tangling
and code scattering - These techniques also could be applied to aspect
oriented code to improve its structure
30Some aspectual refactorings
- Extract method calls
- Extract introduction
- Extract interface implementation
- Extract exception handling
- Replace override with advice
31Extract Method Calls
- When different parts of a program include similar
behavior and so that the program has a duplicated
piece of code in multiple places - extract method refactoring (non AOP) gt
- encapsulate the duplicated logic in a new method,
and replace each original piece of code with a
call to the new method. - But then there will be calls to the new method in
multiple places of the program. - Extract method calls refactoring can be used to
- encapsulate those calls in an aspect,
- which contains a pointcut capturing all the
points where the method must be called and - advises this pointcut with the call to the
refactored method.
32Extract Method Calls
33Extract advice
- Extract advice refactoring, deals with the same
problem with extract method calls refactoring. - But also, if different parts of a program can
include similar behavior that cannot be
refactored into a separate method, extract advice
refactoring can be used to extract the behavior
into a piece of advice.
34Extract interface implementation
- When more than one class implements an interface,
this may result in duplicated code required to
implement this interface (even with classical
Extract interface refactoring) - Solutionwriting an aspect that introduces
default implementation to the interface
35Example extract interface impl.
- Original code
- public interface ServiceCenter
- public String getId()
- public void setId(String id)
-
- public String getAddress()
- public void setAddress(String address)
- public class ATM extends Teller implements
ServiceCenter - private String _id
- ...
- public String getId()
- return _id
-
-
- public void setId(String id)
- _id id
-
36Example extract interface impl.
- Refactored interface
- public interface ServiceCenter
- public String getId()
- public void setId(String id)
- . . .
- static abstract aspect IMPL
- private String ServiceCenter._id
- private String ServiceCenter._address
-
- public String ServiceCenter.getId()
- return _id
-
-
- public void ServiceCenter.setId(String
id) - _id id
-
-
-
37Example extract interface impl.
- Now we can take out the implementation of the
methods declared in ServiceCenter from the ATM
class - Class ATM after refactoring
- public class ATM extends Teller implements
ServiceCenter - ...
-
38Extract exception handling
- Exception handling is a crosscutting concern that
affects most nontrivial classes. Due to the
structure of exception handling code (try/catch
blocks), conventional refactoring cannot perform
further extraction of common code. Each class (or
a set of classes) may have its own way to handle
exceptions encountered during execution of its
logic. With AO refactoring, you can extract
exception handling code in a separate aspect
39Example extract exception handling
- Code before refactoring
- public class MainSystem
- ...
- public ArrayList getDrugNames() throws Exception
- ArrayList namesnew ArrayList()
- for (int i0iltthis.drugs.size()i)
- names.add(((Drug)drugs.get(i)).getName())
-
- if (names.size()0) throw new Exception("No
drugs have been added.") - return names
-
- public ArrayList getPatientNames() throws
Exception - ArrayList namesnew ArrayList()
- for (int i0iltthis.patients.size()i)
- names.add(((Patient)patients.get(i)).getNam
e()) -
- if (names.size()0)
- throw new Exception("No patients have
been Registered.") - return names
40Example extract exception handling
- We are introducing an aspect covering all
exception handling (AspectJ) - public aspect ExceptionHandlerAspect
- after(MainSystem ms) returning(ArrayList arr)
throws Exception - target(ms) execution (ArrayList
getPatientNames()) - if (arr.size()0)
- throw new Exception("No patients are
registered.") -
- after(MainSystem ms) returning(ArrayList arr)
throws Exception - target(ms) execution (ArrayList
getDrugNames()) - if (arr.size()0)
- throw new Exception("No drugs are
added.") -
41Example extract exception handling
- Code after refactoring
- public class MainSystem //no exception handling
code -
- public ArrayList getDrugNames()
- ArrayList namesnew ArrayList()
- for (int i0iltthis.drugs.size()i)
- names.add(((Drug)drugs.get(i)).getName())
-
- return names
-
- public ArrayList getPatientNames()
- ArrayList namesnew ArrayList()
- for (int i0iltthis.patients.size()i)
- names.add(((Patient)patients.get(i)).ge
tName()) -
- return names
-
42Replace override with advice
- It is often required to augment additional common
behavior to many methods of a class. - A typical solution is to create a subclass and
override methods to perform some additional
logic. - For example, you may have a model class without
any support for observer notification. You can
add such a support by creating a subclass and
overriding each state-modifying method to notify
the observers. - With AO refactoring, you can use an aspect to
advise the needed method with additional logic.
For example, instead of overriding, you may
simply advise methods of the subclass that
notifies the observers.
43Other AOP refactorings
- Extract concurrency control
- Extract worker object creation
- Replace argument trickle by wormhole
- Extract Lazy initialization
- Extract contract enforcement
- Explained in Laddad
44Bibliography
- Tzilla Elrad, Robert E. Filman and Atef Bader,
"Aspect-Oriented Programming", Communications of
the ACM, Vol. 44, No. 10, October 2001, pp.
29-32. - Ramnivas Laddad, AspectJ in Action Practical
Aspect-Oriented Programming, Manning, 2003. - TheServerSide.com features two sample chapters
from AspectJ in Action/articles/AspectJreview.t
ss