ArchJava: Connecting Software Architecture to Implementation
Download
Report
Transcript ArchJava: Connecting Software Architecture to Implementation
Architectural Reasoning
in ArchJava
Jonathan Aldrich
Craig Chambers
David Notkin
University of Washington
ECOOP ‘02, 13 June 2002
Software Architecture
Compiler
scanner
parser
codegen
• High-level system structure [GS93,PW92]
– Components and connections
• Automated analysis
• Support program evolution
– Source of defect
– Effect of change
– Invariants to preserve
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
2
Architecture and Implementation
Compiler
scanner
parser
codegen
• Inconsistency caused by evolution
– Architecture documentation becomes obsolete
• Problems
– Suprises
– Misunderstandings lead to defects
– Untrusted architecture won’t be used
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
3
Architecture and Implementation
Compiler
scanner
parser
codegen
• Does code conform to architecture?
• Communication integrity [LV95,MQR95]
– All communication is documented
• Interfaces and connectivity
– Enables effective architectural reasoning
• Quickly learn how components fit together
• Local information is sufficient
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
4
ArchJava
• Specifies architecture within Java code
• Verifies control flow architecture
– Statically checked (except for casts, as in Java)
– Code and architecture evolve together
• Is flexible
– Supports dynamically changing architectures
– Allows common implementation techniques
• Case study on a 12,000-line program
– Evaluates expressiveness, benefits, limitations
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
5
A Parser Component
Parser
public component class Parser {
Component class
• Defines architectural object
• Must obey architectural constraints
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
6
A Parser Component
in
Parser
out
public component class Parser {
public port in {
requires Token nextToken();
}
public port out {
provides AST parse();
}
Components communicate through Ports
• A two-way interface
• Define provided and required methods
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
7
A Parser Component
in
Parser
out
public component class Parser {
public port in {
requires Token nextToken();
}
public port out {
provides AST parse();
}
Ordinary (non-component) objects
• Passed between components
• Sharing is permitted
• Can use just as in Java
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
8
A Parser Component
in
Parser
out
public component class Parser {
public port in {
requires Token nextToken();
}
public port out {
provides AST parse();
}
AST parse() {
Token tok=in.nextToken();
return parseExpr(tok);
}
AST parseExpr(Token tok) { ... }
...
}
Can fill in architecture with ordinary Java code
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
9
Hierarchical Composition
Compiler
out in
scanner
out in
parser
public component class Compiler
private final Scanner scanner
private final Parser parser =
private final CodeGen codegen
codegen
{
= new Scanner();
new Parser();
= new CodeGen();
Subcomponents
– Component instances inside another component
– Communicate through connected ports
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
10
Hierarchical Composition
Compiler
out in
scanner
out in
parser
codegen
public component class Compiler {
private final Scanner scanner = new Scanner();
private final Parser parser = new Parser();
private final CodeGen codegen = new CodeGen();
connect scanner.out, parser.in;
connect parser.out, codegen.in;
Connections
– Bind required methods to provided methods
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
11
Evaluation Questions
• Does ArchJava guarantee communication integrity?
• Is ArchJava expressive enough for real systems?
• What are the benefits and limitations of ArchJava?
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
12
Communication Integrity
Compiler
scanner
parser
codegen
A component may only communicate with the
components it is connected to in the architecture
ArchJava enforces integrity for control flow
• No method calls permitted from one component to
another except
– From a parent to its nested subcomponents
– Through connections in the architecture
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
13
Communication Integrity
Compiler
scanner
parser
codegen
A component may only communicate with the
components it is connected to in the architecture
ArchJava enforces integrity for control flow
• No method calls permitted from one component to
another except
– From a parent to its immediate subcomponents
– Through connections in the architecture
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
14
Communication Integrity
Compiler
scanner
parser
codegen
A component may only communicate with the
components it is connected to in the architecture
ArchJava enforces integrity for control flow
Other communication paths
– Shared data (current work)
– Run-time system
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
15
Control Communication Integrity
Compiler
scanner
parser
codegen
• Architecture allows
– Calls between connected components
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
16
Control Communication Integrity
Compiler
scanner
parser
codegen
• Architecture allows
– Calls between connected components
– Calls from a parent to its immediate subcomponents
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
17
Control Communication Integrity
Compiler
scanner
parser
codegen
• Architecture allows
– Calls between connected components
– Calls from a parent to its immediate subcomponents
• Architecture forbids
– External calls to subcomponents
–
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
18
Control Communication Integrity
Compiler
scanner
parser
codegen
• Architecture allows
– Calls between connected components
– Calls from a parent to its immediate subcomponents
• Architecture forbids
– External calls to subcomponents
– Calls between unconnected subcomponents
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
19
Control Communication Integrity
compiler1
scanner
parser
compiler2
codegen
scanner
parser
codegen
• Architecture allows
– Calls between connected components
– Calls from a parent to its immediate subcomponents
• Architecture forbids
– External calls to subcomponents
– Calls between unconnected subcomponents
– Calls violating architectural hierarchy
• Benefit: local reasoning about control flow
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
20
Control Communication Integrity
compiler1
scanner
parser
compiler2
codegen
scanner
parser
codegen
• Architecture allows
– Calls between connected components
– Calls from a parent to its immediate subcomponents
• Architecture forbids
– External calls to subcomponents
– Calls between unconnected subcomponents
– Calls violating architectural hierarchy
• Benefit: local reasoning about control flow
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
21
Why Not Use Modules?
scanner
parser
codegen
Action
• Implicit Invocation Example
– Jiazzi [MFH01] : strong encapsulation, module linking
– Action object is passed down pipeline
– Invocations through action violate architecture
• Other issues
– First-class functions
– Dynamic architectures
– Instance encapsulation
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
22
Why Not Use Modules?
scanner
parser
codegen
Action
• Implicit Invocation Example
– Jiazzi [MFH01] : strong encapsulation, module linking
– Action object is passed down pipeline
– Invocations through action violate architecture
• Other issues
– First-class functions
– Dynamic architectures
– Instance encapsulation
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
23
Why Not Use Modules?
scanner
parser
codegen
Action
• Implicit Invocation Example
– Jiazzi [MFH01] : strong encapsulation, module linking
– Action object is passed down pipeline
– Invocations through action violate architecture
• Other issues
– First-class functions
– Dynamic architectures
– Instance encapsulation
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
24
Why Not Use Modules?
scanner
parser
codegen
Action
• Implicit Invocation Example
– Jiazzi [MFH01] : strong encapsulation, module linking
– Action object is passed down pipeline
– Invocations through action violate architecture
• Other issues
– First-class functions
– Dynamic architectures
– Instance encapsulation
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
25
Why Not Use Modules?
scanner
parser
codegen
Action
• Implicit Invocation Example
– Jiazzi [MFH01] : strong encapsulation, module linking
– Action object is passed down pipeline
– Invocations through action violate architecture
• Other issues
– First-class functions (like Actions)
– Instance encapsulation (2 compiler example)
– Dynamically changing architectures
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
26
Action Example in ArchJava
scanner
parser
codegen
X
Action
• Classes can’t refer to components
– Action can’t store reference to scanner component
• Components can share Action
– Allows communication through side effects
• current work: specify & enforce this
– Type system prevents control flow through Action
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
27
Enforcing Communication Integrity
• Communication integrity for direct method calls
– Can only call self or subcomponents
• Invariant
– All component-typed references in a component (and
called objects) are to self or subcomponents
– Key lemma in integrity proof
• Enforcement
– No component types in port interfaces
– No fields of component type in objects
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
28
Enforcing Communication Integrity
• What about casts?
– Store components in data structures
– But, data structures can be shared
– Downcasts could violate communication
integrity
• Solution: additional dynamic check
– Components store parent
– Casted object or its parent must be this
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
29
Other Integrity Issues
• Dynamically changing architectures
– Patterns specify permissible connections
– Dependent types
• Relate a connection to a component instance
• Restrictions on inheritance, inner classes
– e.g., components may not implement interfaces
– Reasonable in component libraries
• Relax to use existing Java libraries
– Investigating ways to relax restrictions safely
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
30
ArchFJ : A Formal Framework
• Based on Featherweight Java [OOPSLA 99]
– Includes components, ports, connections
• Benefits
– Precise semantics
– Shows how integrity is enforced
• Proven:
– Type safety
– Control communication integrity
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
31
Evaluation Questions
• Does ArchJava guarantee control communication
integrity?
– Yes, using the type system
• Is ArchJava expressive enough for real systems?
• What are the benefits and limitations of ArchJava?
• Two case studies
– 12,000 lines of Java code each
– Asked developer to draw architecture
– Tried to specify architecture in ArchJava
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
32
Evaluation Questions
• Does ArchJava guarantee control communication
integrity?
– Yes, using the type system
• Is ArchJava expressive enough for real systems?
• What are the benefits and limitations of ArchJava?
• Case study: Taprats
– 12,000 lines of Java code
– Two challenges
• Drawn by original developer
• Dynamic changes
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
33
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
34
Architectural Comparison
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
35
ArchJava Architecture
• Architecture shows design characteristics
– Pipeline of components
– Dynamically created
– Largely independent
• Architecture matches intuition
– But ArchJava guarantees correctness!
• Architecture evolves with implementation
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
36
Evaluation Questions
• Does ArchJava guarantee control communication
integrity?
– Yes
• Is ArchJava expressive enough for real systems?
– Yes (validated by 2 other case studies)
• Three experiments
– Understanding Aphyds communication
– Refactoring Aphdys
– Reparing a defect
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
37
Evaluation Questions
• Does ArchJava guarantee control communication
integrity?
– Yes
• Is ArchJava expressive enough for real systems?
– Yes (validated by 2 other case studies)
• What are the benefits and limitations of ArchJava?
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
38
Coupling in Taprats
RenderPanel
PreviewPanel
RenderView
render.getView().setTheta(t);
• PreviewPanel coupled to RenderPanel
– Depends on View representation of RenderPanel
– Programs are fragile, change is difficult
• Law of Demeter [Lieberherr et al.]
– Design guideline
– “Only talk with your neighbors”
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
39
Taprats in ArchJava
RenderPanel
PreviewPanel
RenderView
render.getView().setTheta(t);
• Control communication integrity
– Components only talk with connected components
• Compile-time error in ArchJava
– PreviewPanel can only reference local connections
– Call through architecture, reducing coupling
Hypothesis: Enforcing communication integrity helps to
reduce system coupling
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
40
Taprats in ArchJava
RenderPanel
PreviewPanel
RenderView
render.getView().setTheta(t);
• Control communication integrity
– Components only talk with connected components
• Compile-time error in ArchJava
– PreviewPanel can only reference local connections
– Call through architecture, reducing coupling
Hypothesis: Enforcing communication integrity helps to
reduce system coupling
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
41
Taprats in ArchJava
RenderPanel
PreviewPanel
RenderView
render.getView().setTheta(t);
• Control communication integrity
– Components only talk with connected components
• Compile-time error in ArchJava
– PreviewPanel can only reference local connections
– Call through architecture, reducing coupling
Hypothesis: Enforcing communication integrity helps to
reduce system coupling
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
42
Case Study Summary
• Successful overall
–
–
–
–
Expressed dynamic architecture
Made design explicit
Reduced coupling
Low cost (5 hours, 500 lines of additional code)
• Lessons Learned
– Some unnecessary casts
– Creation slightly awkward
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
43
Case Study Summary
• Successful overall
–
–
–
–
Expressed dynamic architecture
Made design explicit
Reduced coupling
Low cost (5 hours, 500 lines of additional code)
• Directions for improvement
– Some unnecessary casts
– Creation slightly awkward
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
44
More in paper
•
•
•
•
Formalization of language & properties
Architectural design principles
Architectural refactoring patterns
Comparison to earlier case study
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
45
Current and Future Work
• ICSE ’02
– ArchJava language design
– Case study with static architecture
• ECOOP: communication integrity & dynamic architecture
• OOPSLA ’02
– Specification of data sharing
• ownership type system [Clarke et al.]
• Extend ML-style modules to enforce architecture
• Refine language design
– Distributed systems, flexible connectors
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
46
Conclusion
• ArchJava integrates architecture with Java code
• Control communication integrity
– Keeps architecture and code synchronized
• Initial experience
– ArchJava expresses dynamically changing architectures
– ArchJava may improve program structure
• Download the ArchJava compiler and tools
http://www.archjava.org/
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
47
Limitations of ArchJava
• Some idioms are awkward
– Implicit invocation architectures
– Dynamic component creation and connection
– Some extra casts
• Architecture is very concrete
– Connections must be method calls
• Can’t express all architectural properties
– Data sharing (partial solution: OOPSLA ‘02)
– Others (temporal protocols, styles, etc.)
13 June 2002
Jonathan Aldrich - ECOOP '02 - ArchJava
48