Formal Foundation for Pattern-Based Modelling
Paolo Bottoni1 , Esther Guerra2 , and Juan de Lara3
1
2
Università di Roma “Sapienza” (Italy),
[email protected]
Universidad Carlos III de Madrid (Spain),
[email protected]
3
Universidad Autónoma de Madrid (Spain),
[email protected]
Abstract. We present a new visual and formal approach to the specification of patterns, supporting pattern analysis and pattern-based model
completion. The approach is based on graphs, morphisms and operations from category theory and exploits triple graphs to annotate model
elements with pattern roles. Novel in our proposal is the possibility of
describing (nested) variable submodels, as well as inter-pattern synchronization across several diagrams (e.g. class and sequence diagrams for
UML design patterns). We illustrate the approach on UML design patterns, and discuss its generality and applicability on different types of
patterns, e.g. workflow patterns using Coloured Petri nets.
1
Introduction
Patterns are increasingly used in the definition of software frameworks, as well as
in Model Driven Development, to indicate parts of required architectures, drive
code refactorings, or build model-to-model transformations. The full realisation
of their power is however hindered by the lack of a standard formalization of the
notion of pattern. Presentations of patterns are typically given through natural
language, to explain their motivation, context and consequences; programming
code, to show usages of the pattern; and diagrams, to communicate their structure and behavior. However, the use of domain modelling languages, such as
UML for design patterns, or Coloured Petri Nets for workflows, forces pattern
proposers to provide only examples of their realisation, appealing to intuition
to extend them to the complete semantics of the pattern. For instance, the fact
that in the Visitor pattern there must be a distinct operation in the Visitor
interface for each ConcreteElement is only understood through generalisation
of the examples or reading the associated text [4].
The search for a general definition of patterns, independent from the specific
modelling language, has led to several proposals based on the association of constraints to diagrammatic definitions, or to extensions of the UML meta-model,
in order to distinguish roles from concrete modelling types. However, these proposals incur some problems to define the relations between different components
of a patterns specification, as will be illustrated in Section 2.
We propose a formal notion of pattern, grounded in category theory [9],
which sees them as formed of: i) a vocabulary of roles; ii) a collection of diagrams, possibly in different modelling languages, defining cardinalities and associations between roles, and supplemented with indications of variable regions; iii)
a collection of interfaces between these diagrams, to identify roles across different diagrams. Two main results are thus obtained, representing a distinguishing
novel feature of the approach. First, dependencies among different components
of a pattern specification can be formally defined. Second, a clear specification of
the parts of the pattern which can be replicated (and of the admissible number
of replicas) is given, without recurring to concrete examples. As our notion of
pattern generalises patterns from different fields, it opens the way to the extension of pattern-based techniques to new areas, to the formalisation of existing
ones, and in general, to the development of pattern-based languages.
The paper is organized as follows. Section 2 presents related approaches.
Section 3 introduces our new definition of pattern. Section 4 shows the procedure
for pattern application. Finally, Section 5 ends with the conclusions.
2
Related Work
The shortcomings of presenting patterns in the GoF (Gang of Four [4]) style have
been addressed by several researchers, who advocate a more formal approach.
For example, [3] extends the UML meta-model for class diagrams with specific
roles and constraints. Conformance of a model to a pattern is checked as the
usual model/meta-model relationship. The technique works for UML class and
sequence diagrams, and the emphasis is on specification of patterns, but not
on their use for model completion. A non-uniform interpretation of interaction
diagrams is provided, where reference to interaction fragments is translated to
their unfolding with respect to the instantiation of roles.
The limitations posed by reference to UML diagrams, in particular as regards premature commitment to hierarchical structures, are overcome in [10]
by extending the UML meta-model with stereotypes accounting for possible realizations of a given pattern. A distinction between roles, types and classes is
used in [8] to decouple representations of roles, at which level the semantics of
the pattern is abstractly described by incorporating constraint diagrams into
the UML notation, from their refinement as types, and their implementation
into classes. This way, the GoF presentation of patterns is shown to be a realization of the abstract level. However, commitment to names and multiplicities
is already needed at the type level, with the class level providing concrete implementations. Our proposal, on the contrary, provides the separation through
triple graphs which establish a correspondence between roles in a pattern model
and types in a pattern specification. Variability is thus maintained also at the
type level, leaving matching morphisms to provide the relation with any given
realization of the pattern. Independence from UML is achieved in [7] by using
Object-Z, but it is limited to structural aspects. Constraints on the use of patterns are exploited in [14] to maintain the consistency of a pattern-based software
framework through the use of high-level transformations specific to each pattern.
In [1] a method is proposed for visualizing the roles of the elements in UML
class and communication diagrams. The technique extends the UML Profile
meta-model with stereotypes and tagged values for pattern annotation. This
also allows pattern composition through single instances. In [6] the intent of
design patterns is described with an ontology, which can be queried to obtain
suggestions about the most appropriate pattern solving a certain problem.
In [13], the authors propose a logic-based approach, using subsets of First
Order Logic – for structural aspects – and Temporal Logic of Actions – for
behavioral ones – and supporting pattern combinations. As the language does
not include implications, support for complex constraints appears limited.
Graph transformation [2] has also been used to formalise patterns. In [11],
patterns are represented with rules, applied to abstract syntax trees to annotate the pattern instances found. In [12], models are transformed to conform to
patterns, after having exploited graph queries that detect needs for transformations. In [16] Spatial Graph Grammars provide a graph representation of GoF
patterns, to transform object structure graphs so that they conform to patterns.
Although declarative, the rules are based on a concrete presentation of patterns,
and not on a meta-model characterisation.
In general, we observe the lack of an integrated, domain-independent formalism able to give account of mutual synchronization constraints within a pattern
and across different ones, and to support pattern checking, identification and
application. In the rest of the paper we present such a formalism.
3
3.1
Pattern Specification
Variable Patterns
We define a variable pattern as made of a fixed part root and a number of variable parts Vi , which can be replicated according to a given interval (low, high).
Variable patterns support nesting – variable parts inside variable parts – and can
be used with any graph model, from unattributed graphs G = (VG , EG , src, tgt :
EG → VG ), to typed node and edge attributed graphs (e.g. E-graphs [2]). Here
we use typed attributed graphs and injective morphisms.
Definition 1 (Variable Pattern). A variable pattern is defined as V P =
(P = {Vi }i∈I , root ∈ P, int : P → N × (N ∪ {∗}), Emb = {vi,j : Vi → Vj |∃Vi , Vj ∈
P }), where Vi are non-empty graphs, vi,j are injective morphisms, Emb is a tree
with graphs Vi ∈ P as nodes and morphisms vi,j as edges, rooted in root ∈ P ,
and int is a function returning the variability interval for each graph Vi ∈ P .
A finite set S satisfies interval (l, h), written S ⊳ (l, h), iff |S| ≥ l and
h = ∗ ∨ |S| ≤ h. Note that if (l, h) is such that l > h, then it cannot be satisfied.
Example. The GoF Observer pattern captures one-to-many dependencies between objects so that when the subject object changes its state, all the dependent observer objects are notified and updated automatically. Fig. 1 presents a
simplified version of this pattern using Def. 1. The left part directly encodes the
theoretical form, with full definition V P = (P = {VOb , VConc }, root = VOb , int =
{(VOb , (0, ∗)), (VConc , (1, ∗))}, Emb = {vOb,Conc }). The variability interval is related to the satisfiability of the pattern by a model. VOb has (0, ∗) as variability
VOb (0, *)
VConc (1, *)
Subject
Observer
Subject
(0, *)
Observer
v Ob,Conc
Subject
Observer
(1, *)
ConcreteSubject
ConcreteSubject
ConcreteObserver
ConcreteSubject
ConcreteObserver
Fig. 1. The Observer Pattern in Theoretical (left) and Compact (right) Forms.
interval, thus the pattern is not mandatory and we may have any number of
instances. As int(VConc ) = (1, ∗), we require at least one ConcreteObserver in
each pattern instance. The right part of the figure shows a compact form, where
fixed and variable parts are presented together. In the figure, we use the concrete
syntax of UML class diagrams, but the abstract syntax can also be used. ¥
The next definition states when a given graph satisfies a variable pattern.
Definition 2 (Pattern Satisfaction). Given a graph G and a variable pattern
V P as in Def. 1, G satisfies V P , written G |= V P , iff:
– Mroot = {pkroot : root → G} ⊳ int(root).
– ∀vi,j : Vi → Vj ∈ Emb:
• ∀pki ∈ Mi , Mjk = {plj : Vj → G|pki = plj ◦ vi,j } ⊳ int(Vj ).
S
• Define Mj = Mjk , with k = 1..|Mi |.
v
VOb
ij
V ...
i
v
v
ij
root,i
root
V
VConc
Subject
...
v
root, i
1
p
1
i
p
root
ij
V ...
i
n vij
p
i
v Ob,Conc
Subject
Observer
j
...
V
j
1
p
j
V
j
...
V
ConcreteSubject
ConcreteSubject
...
v
Observer
s
p
j
G
...
Subject
VConc
Observer
Subject
ConcreteSubject
ClockTimer
DigitalClock
AnalogClock
Observer
2
p Conc
j
m
p ... pn
j
j
ConcreteObserver
v Ob,Conc
1
p Ob
ConcreteObserver
1
p Conc
G
Fig. 2. Pattern Satisfaction (left). Pattern Satisfaction Example (right).
Remark. The procedure in Def. 2 induces a tree traversal for Emb, because
when Vi → Vj is traversed, Mi must have been previously calculated. ¥
The left of Fig. 2 describes the morphisms for the satisfaction checking for a
variable pattern with one level of nesting, i.e. Emb = {root → Vi , Vi → Vj }. We
assume one morphism p1root ∈ Mroot . The procedure checks that the set Mi1 of all
p1
vroot,i
root
morphisms p1i , ..., pni : Vi → G commuting with G ←
root → Vi satisfies the
interval int(Vi ) = (lowi , highi ). Similarly, given each morphism pki ∈ Mi = Mi1 ,
pk
vi,j
i
each set Mjk of morphisms p1j , ..., psj : Vj → G commuting with G ←
Vi → Vj
satisfies the interval int(Vj ). In the figure, we have replicated Vj and Vi for each
different morphism pkj and pki , to show more intuitively the tree traversal.
Example. The right of Fig. 2 shows a model G that satisfies the specification of
the observer pattern of Fig. 1. The fixed part VOb occurs once, and the variable region VConc twice. This is checked by building the set MConc = {p1Conc : VConc →
G, p2Conc : VConc → G} ⊳ (1, ∗). In the figure, the dotted lines indicate some of
the mappings induced by p1Ob , p1Conc and p2Conc . ¥
3.2
Annotating Structure with Roles: Triple Patterns
In order to specify a pattern, we need its structure (as given by a variable
pattern), a vocabulary of pattern roles, and a mapping from the elements in
the pattern to the vocabulary. We call this structure annotated pattern and
ground it in the notion of triple graph [5], composed of two graphs, source and
target, related through a correspondence graph. Nodes in the correspondence
graph (also called mappings) have morphisms to nodes or edges in the other two
graphs. Thus, mappings may relate two nodes, two edges, an edge and a node,
or just point to a single element in the source or target graphs [5].
Definition 3 (Triple Graph). A triple graph T rG = (Gs , Gc , Gt , cs , ct ) has
three graphs Gi (i ∈ {s, c, t}), and two functions cj : VGc → VGj ∪ EGj ∪ {·}
(j = s, t).
The element “·” in the codomain of cj denotes that the correspondence funcct
cs
Gt ).
Gc −→
tion cj can be undefined. A triple graph is also written as (Gs ←−
We say that a node or edge x of Gs is related to a node or edge y of Gt iff
cs
ct
n 7−→
∃n ∈ VGc s.t. x ←−[
y and we write x relT rG y. As [5] showed, triple
graphs and morphisms form the category4 TrGraph [9].
Example. Fig. 3 shows a triple graph. Its source graph Gs at the bottom conforms to the UML meta-model, its target Gt at the top is a pattern vocabulary
model, and the correspondence graph Gc maps UML elements to vocabulary
elements. The morphisms from the nodes in Gc are shown as dotted arrows.
The correspondence function cs is undefined for node :PatternInstance (i.e.
cs (:PatternInstance) = ·) and this is represented by omitting the edge. ¥
Triple graphs are typed by meta-model triples [5] made of two meta-models,
source and target, related through a correspondence meta-model. In our case, a
meta-model triple relates the meta-model of a specific language (e.g. UML) with
that of a generic pattern vocabulary, which can be refined by subclassification in
order to define patterns for the language. The top of Fig. 4 shows the meta-model
for the vocabulary. All classes except the subclasses of PatternRole allow defining patterns in any language. A Pattern has a name and a type, contains participating roles, and can be documented with its motivation, applicability, intent
4
A category is made of objects (e.g, triple graphs) and arrows (e.g., triple morphisms)
satisfying some conditions [9].
:Pattern
name=’SimpleProxy’
type=’structural’
:OperationRole participant
name=’rReal’
participant
Pattern
Vocabulary
for UML Proxy
participant
participant
:OperationRole
:ClassRole
:ClassRole
name=’RealSubject’ name=’request’
:OperMap
:ClassMap
participant
participant
:ClassRole
:OperationRole
name=’Subject’ name=’realSubject’ name=’Proxy’ name=’rProxy’
:OperMap
:ClassMap
:AssocMap
:ClassMap
:OperMap
:Pattern
Instance
Corresp. Model
request:Operation
UML Model
owned
Operation
participant
:AssociationRole
ownedOperation
subject:Class
name = x
isAbstract = true
realSubject:Class specific
isAbstract = true
:Generalization
:Generalization
specific proxy:Class
request:Operation
owned
Operation
request:Operation
:Property
name = x
realSubject:Association
:Property
name = x
Fig. 3. Annotated Pattern with the Structural Part of the Proxy (in Abstract Syntax).
and consequences. Relations between patterns are given through the Relation
association class. We have specialized the meta-model for UML, so that roles are
applicable to operations, classifiers, classes, structural features and associations.
The bottom of Fig. 4 partially shows the UML meta-model, and the correspondence meta-model maps roles to UML elements. The PatternInstance class is
used to group the mappings of each pattern instantiation.
Consequence
+ desc: String
Intent
Applicability
+ when: String
*
*
*
1
+ why: String
1
Motivation
1
+ how: String
Relation
+ rel: String
*
UML Meta−Model
*
1
1..*
Pattern
PatternRole
1..*
participant + name: String
+ name: String
+ type: String
Pattern Vocabulary
Meta−Model (for UML)
Correspondence
Meta−Model
*
Pattern
Instance
OperationRole
RoleMap
AssociationRole
OperMap
Operation
AssocMap
Association
Structural
FeatureRole
Classifier
Role
ClassRole
StructMap
ClassiMap
ClassMap
StructuralFeature
Classifier
Class
Fig. 4. Meta-model Triple for UML Patterns.
A pattern-annotated model is a triple graph whose source is a model in some
language (e.g. UML), and the target contains a subgraph isomorphic to a pattern
vocabulary, for each pattern used in the source model. The correspondence graph
is called annotation graph and has a PatternInstance node for each pattern
instance and one RoleMap for each element playing a role in the instance. For
example, the annotated pattern in Fig. 3, specifying the structure of the Proxy
pattern [4], conforms to the meta-model triple in Fig. 4. The intent of this design
pattern is to provide a surrogate or placeholder proxy for an object with role
realSubject in order to control access to it. The bottom part of Fig. 3 uses the
abstract syntax for UML class diagrams. For simplicity, we only show the pattern
and the roles in the vocabulary model. The pattern has only one fixed graph,
no variable part, and requires that the operations in Subject, RealSubject and
Proxy have the same name, which is modelled with a variable x. More complex
attribute conditions such as in [2] are possible. We have omitted the name of
classes and associations, so they can be mapped to any name.
An annotated pattern is a variable pattern where all the graphs in Def. 1 are
triple graphs, and morphisms are triple morphisms. The notion of pattern satisfaction remains as in Def. 2, but using triple graphs. Thus, annotated patterns
are satisfied by triple graphs, called pattern-annotated models.
Example. Workflow patterns [15] collect recurring constructs from existing
workflow systems and provide descriptions of their usage. Their presentation
is textual in the style of GoF patterns. For control flow patterns, dealing with
synchronization policies, an intuitive semantics is given through Coloured Petri
Nets showing example realizations of the pattern, to be inferred by the reader.
Fig. 5 shows three annotated patterns expressed via a syntax identifying the roles
of places and transitions, as input, split, out- Multi−merge Parallel Split Generalized
AND−Join
put, and, and merging. ¥
(2, *)
<<input>>
<<input>>
(0, *)
As seen before, a tool need not show
<<input>>
the triple graph to the user, but the anno(2, *)
<<split>>
<<merging>>
<<and>>
tation can be done by marking the source
(0, *)
(0, *)
<<output>>
graph [1]. However for the theory, an explicit
<<output>>
(2, *)
<<output>>
triple graph has some advantages: (i) we do
not modify or extend the source meta-model
(e.g. the UML one) with additional classes or
Fig. 5. Workflow Patterns.
attributes for tagging; (ii) triple graphs help
in enforcing the patterns, as shown in Section 4; (iii) it is easier to distinguish
the instances of a pattern, as these are identified by PatternInstance nodes.
3.3
Synchronizing Different Variable Patterns
A pattern specification can be composed of more than one diagram. For instance,
the GoF patterns are described using class and sequence diagrams. Thus, relationships have to be established between the elements in the different diagrams,
which we do through their roles in the pattern.
Example. The Visitor pattern explicitly represents as objects the operations to
be performed on the elements of an object structure, so that new operations can
be defined without changing the classes of the elements on which they operate.
It is one of the most complex GoF patterns as it requires two levels of variation
for the two hierarchies of Visitor (i.e. the operations) and Element (i.e. the
object structure), with the set of operations for Visitor varying together with
the ConcreteElement set. This covariance cannot be expressed through a constraint on cardinalities, as it requires an exact match on types of parameters.
The pattern is shown in Fig. 6, where the presence in the same variance region of
the signatures for the visit operations constrains the types of their parameters
to satisfy the constraint of equality with the types of ConcreteElement.
structural diagram
<<ObjectStructure>>
ObjectStructure
(0, *)
<<Element>>
Element
+ accept (Visitor) <<accept>>
(1, *)
behavioural diagram
(0, *)
<<Visitor>>
<<ObjectStructure>>
<<ConcreteElement>>
<<ConcreteVisitor>>
Visitor
ObjectStructure
ConcreteElement
ConcreteVisitor
class
+ visitConcreteElement
(ConcreteElement)<<visit>>
(1, *)
class
ce:
os:
class
(1, *)
(1, *)
cv:
accept(cv)
<<ConcreteElement>>
<<ConcreteVisitor>>
ConcreteElement
ConcreteVisitor
<<accept>>
visitConcreteElement(this)
<<visit>>
Fig. 6. Visitor Pattern.
Both the structural and the behavioral part of Visitor require two variable
parts, relative to the two hierarchies. However, while in the structural part the
two regions are independent, in the behavioral part they are nested. This reflects the double constraint that each concrete visitor can be accepted by each
concrete element and that each concrete visitor has an operation to visit each
concrete element. The synchronization between the different regions involved is
represented by the equality of the colours used in the different pattern graphs,
and formally as a synchronization graph.
Fig. 7 shows the scheme of the two patterns for Visitor: SP : V1SP ← V0SP →
SP
V2 and IP : V0IP → V1IP → V2IP . SP has V0SP as root and two variable parts,
and describes the structural part (a class diagram).
IP
v IP
v01
/ V IP 12 / V IP
IP has root V0IP and a variable part V1IP with nested
V0IP
1
2O
O
O
V2IP , modelling a sequence diagram. The synchronizaiIP
iIP
iIP
11
22
tion graph I11 ← I → I22 declares the intersections be'
22
/
e
I
I
I
tween the roots and pairs of variable parts of each pat11
22
e11
tern. Morphism I → I11 is derived as we have V0SP → iSP
iSP
iSP
² 22
² vSP ² 11
V1SP and V0IP → V1IP , and similar for I → I22 . All
01
SP
/ V SP
V0SP
1
6 V2
squares in the diagram must commute to ensure coSP
herence, so I → V0SP → V1SP = I → I11 → V1SP , and
v02
IP
similar for V0 with I11 and I22 . ¥
Example. Fig. 8 shows a variation of the Proxy pat- Fig. 7. Synchronization
tern, in concrete syntax, allowing several proxies for
a given subject (V0SP → V1SP ). The upper part (V0IP → V1IP ) shows the annotated sequence diagram. For clarity, we show the classifiers of the p and rs
objects, as both classifiers play a role in the pattern. ¥
In Fig. 8 and others, we use a shortcut notation, shown below, for sequence
diagrams. The OperMap node in the annotation graph points to the message
arrow for the invocation, while in the abstract syntax the morphism reaches the
operation to be executed through a MessageOccurrenceSpecification object.
V IP
0
V IP
1
:Pattern
I
:Pattern
name=’Proxy’
type=’structural’
I 11
:Pattern
:Pattern
name=’Proxy’
type=’structural’
name=’Proxy’
type=’structural’
name=’Proxy’
type=’structural’
:ClassRole
:OpRole
:ClassRole
:OpRole
:ClassRole
:OpRole
:ClassRole
:ClassRole
:OpRole
n=’RSubject’
n=’rProxy’
n=’Proxy’
n=’rReal’
n=’RSubject’
n=’rProxy’
n=’Proxy’
n=’RSubject’
n=’rReal’
:ClassMap
:OperMap
:ClassMap
:OperMap
:ClassMap
RealSubject
Proxy
class
:ClassRole
:OperMap
:ClassMap
RealSubject
class
rs:
:OperMap :ClassMap
Proxy
class
p:
+ request ()
RealSubject
+ request ()
rs:
request()
n=’RSubject’
request()
:ClassMap
RealSubject
V SP
0
V SP
1
:Pattern
:Pattern
name=’Proxy’
type=’structural’
name=’Proxy’
type=’structural’
:OpRole
:ClassRole
:ClassRole
:OpRole
:OpRole
:ClassRole
:ClassRole
:OpRole
:ClassRole
:OpRole
:AssocRole
n=’rReal’
n=’RSubject’
n=’Subject’
n=’request’
n=’rReal’
n=’RSubject’
n=’Subject’
n=’request’
n=’Proxy’
n=’rProxy’
n=’rSubject’
:ClassMap
:ClassMap
:OperMap
:OperMap
:ClassMap
:ClassMap
:OperMap
:ClassMap
:OperMap
:OperMap
RealSubject
+ request ()
Subject
+ request ()
RealSubject
+ request ()
Subject
Proxy
+ request ()
+ request ()
:AssocMap
Fig. 8. Synchronization Example for the Proxy Pattern.
The two variable patterns to be synchronized
:OperMap
share the same vocabulary model, as they dep:Object
scribe different diagrams of the same pattern.
:OperMap
:ConnectableElement
Given the parts to be synchronized, the synp:
:Lifeline
request()
chronization graph is automatically calculated
:MessageOccurrenceSpecification
by the intersections w.r.t. the roles. Thus,
:GeneralOrdering
two elements in two patterns SP and IP , if
:ExecutionOccurrenceSpecification
mapped to the same role, will be present in I.
:ExecutionSpecification
Once the intersection graphs Iij (and the
request:Operation
morphisms ViSP ← Iij → VjIP ) are derived,
the morphisms of the synchronized graph are derived as well. Morphism Iik → Ijl
is added, iff there is a path ViSP → VjSP in the Emb tree of SP and a path
VkIP → VlIP in the Emb tree of IP .
Definition 4 (Synchronization Graph). Let AP k = (P k = {Vik }i∈I k , rootk ∈
k
P k , intk , Embk = {vi,j
: Vik → Vjk }), k = {1, 2}, be two annotated patterns on
i1
i2
the same vocabulary V P ; their synchronization graph SG = (V = {root1 ← I →
i1ij
i2ij
root2 , ..., Vi1 ← Iij → Vj2 , ...}, E = {ekl
ij : Iij → Ikl }) is calculated as follows:
– For each pair of triple graphs V k = (Vsk ← Vck → Vtk ) to be synchronized:
• Build the triple graph O = (Os ← Oc → V P ), and triple morphisms
f1
f2
V 1 −→ O ←− V 2 , jointly surjective on Os and Oc as follows: (i) VP is
the common vocabulary model, so there are inclusions Vtk ֒→ V P (ii) if
two elements a ∈ Vs1 , b ∈ Vs2 are mapped to the same role in V P , (i.e. a
relV 1 x, b relV 2 x) only one element ab is added to Os , and the functions
f 1 and f 2 identify a and b to such element, f 1 (a) = ab = f 2 (b) (if ab
does not exist, the graphs cannot be synchronized).
i1
f2
f1
i2
• Intersection I is given by the pullback 5 V 1 ← I → V 2 of V 1 → O ← V 2 .
– Given two intersection nodes Vr1 ← Irs → Vs2 and Vu1 ← Iuv → Vv2 s.t. there
are paths Vu1 → Vr1 in Emb1 and Vv2 → Vs2 in Emb2 , add edge ers
uv : Iuv →
Irs to SG, as morphism ers
uv uniquely exists due to the pullback universal
property [2], see the left of Fig. 9.
Remark. Two graphs V 1 and V 2 can be synchronized only if their variability
intervals overlap (i.e. ∃M |M ⊳ int1 (V 1 ) and M ⊳ int2 (V 2 )).
I
V IP
0
:Pattern
Vr1
O
¨C [777
¨
¨
f1
f 27
77
¨¨¨
O [666
1
vur
P.B.
i1
rs
Vs2
C O
©©© 2
i2
rs
vvs
66
6 ©©©
Irs
Vv2
Vu1
O
C
[777
¨
¨¨
rs
2
1
iuv7 euv iuv
77 ¨¨
¨
Iuv
:Pattern
name=’Proxy’
type=’structural’
name=’Proxy’
type=’structural’
O
:AssocRole
:ClassRole
:OpRole
n=’rSubject’
n=’Proxy’
n=’rProxy’
:ClassRole
:ClassRole
:Pattern
n=’RSubject’
n=’RSubject’
name=’Proxy’
type=’structural’
:ClassMap
:ClassMap
rs:
RealSubject
class
RealSubject
:OpRole
:ClassRole
:ClassRole
:OpRole
n=’rReal’
n=’RSubject’
n=’Subject’
n=’request’
:ClassMap
:ClassMap
:OperMap
:OperMap
V SP
0
:Pattern
name=’Proxy’
type=’structural’
RealSubject
+ request ()
class
:OpRole
:ClassRole
:ClassRole
:OpRole
n=’rReal’
n=’RSubject’
n=’Subject’
n=’request’
:ClassMap
:ClassMap
:OperMap
:OperMap
RealSubject
+ request ()
Subject
+ request ()
rs:
Subject
+ request ()
Fig. 9. Calculating Intersection Edges (left). Example (right).
Example. The right of Fig. 9 shows an example of the calculation of an intersection graph for the synchronization scheme shown in Fig. 8. ¥
3.4
Full Pattern Specification
We now put all elements together to define a full pattern, made of a primary
structuring pattern SP , and a number of secondary patterns IPi synchronized
with SP through synchronization graphs SGi .
Definition 5 (Full Pattern Specification). A Full Pattern Specification P S =
(V P, SP, Sec = {(IPs , SGs )}s∈S ) is composed of:
5
Roughly, a pullback [9] is the biggest intersection of two objects Ai through a common one B to which both are mapped. The pullback A1 ← C → A2 identifies the
elements of A1 and A2 that are mapped to a common element in B.
1. A Pattern Vocabulary V P , mentioning the relevant roles for the patterns.
2. A Structuring Pattern Diagram SP = (P SP = {ViSP }i∈I , rootSP , intSP ,
SP
EmbSP = {vi,j
: ViSP → VjSP }), an annotated pattern where the ViSP are
triple graphs whose target is a subgraph of the pattern vocabulary V P .
3. A set Sec of pairs made of a Secondary Pattern Diagram IPs = (PsIP =
IP
IP
IP
= {vi,j
: ViIP → VjIP }) and a Synchro{ViIP }i∈Is , rootIP
s , ints , Embs
isp
ij
iip
ij
nization Graph SGs = (Vs = {ViSP ← Iij → VjIP }, Es = {ekl
ij : Iij → Ikl }),
which synchronizes the secondary patterns with the primary one.
For UML patterns, the primary pattern SP is a class diagram, and Sec
generally contains a sequence diagram synchronized with the class diagram.
The satisfaction of full patterns is similar to Def. 2, but using annotated
patterns and taking into account the synchronization graphs.
Definition 6 (Full Pattern Satisfaction). Given a pattern-annotated model
cG
cG
s
t
T rG = (Gs ←−
Gc −→
Gt ), and a full pattern specification P S = (V P, SP, {(IPs ,
SGs )}s∈S ) as in Def. 5, T rG satisfies P S, written T rG |= P S, iff:
– ∀(IP, SG) ∈ Sec (i.e. for each secondary pattern and synchronization graph):
psk
pik
isp
iip
• Let Mroot,root = {rootSP → T rG ← rootIP |rootSP ← I → rootIP is
pullback}, then Mroot,root ⊳ intSP (rootSP ) and Mroot,root ⊳ intIP (rootIP ).
• ∀elm
jk : Ijk → Ilm ∈ E (i.e. for each edge in SG):
psr
pir
psu
piu
r
⋄ ∀VjSP → T rG ← VkIP ∈ Mj,k , let Ml,m
= {VlSP → T rG ←
IP
u
SP
SP
r
u
Vm |ps ◦ (Vj → Vl ) = ps and pi ◦ (VkIP → VmIP ) = pir and
isp
iip
r
⊳ intSP (VlSP ) and
VlSP ← Ilm → VmIP is pullback}. Then Ml,m
r
IP
Ml,m
⊳ intIP (VS
m ). See Fig. 10(a).
r
⋄ Define Ml,m = Ml,m
, with r = 1..|Mj,k |.
Example. Fig. 10(b) shows in compact notation the satisfaction of the Proxy
pattern of Fig. 8. The model contains a class diagram and two sequence diagrams, enclosed in different regions, which a tool would present in three views.
The model has one instance of the Proxy pattern, and the variability region
that affects the Proxy role has been instantiated twice (classes ImageProxy and
RemoteProxy). Fig. 10(c) shows the first step in the satisfaction checking, where
the pullback of the fixed parts is depicted, corresponding to the intersection
graph shown to the right of Fig. 9. The satisfaction check follows by computing
two additional pullbacks for the two instantiations of the variable parts. ¥
4
Pattern-Based Model Completion
Patterns as defined above can be used in different scenarios: (i) to query how
many instances of each pattern a model contains, or to analyse pattern instance
interactions; (ii) for pattern extraction; (iii) to check whether a part of the
Ilm
O
elm
jk
sp
ilm
ip
Ijk OO iip
OOjk
nnn
OO'
wnnn
sp
ilm
V SP
0
ijk
|
VlSP o
SP
vjl
VjSP P
PPP
P(
r
ps
psu
P.B.
0 T rG n
IP
V
nn k
vnnnpir
IP
vkm
I
<<Subject>>
/ VmIP
V IP
0
<<RSubject>>
class
rs:
{(Subject,Graphic),(request,draw),
(request,draw),(RealSubject,Image)}
{(RealSubject,Image)}
M
<<Subject>>
Graphic
+ draw ()
<<request>>
1111111111111111111111111
0000000000000000000000000
00000000000000000000000000
11111111111111111111111111
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
<<Proxy>>
<<Proxy>>
<<RSubject>>
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
RemoteProxy
ImageProxy
Image
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
+ draw ()
+ draw ()
+ draw ()
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
class
class
class
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
p:
p:
rs:
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
draw()
draw()
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
draw()
draw()
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
0000000000000000000000000
1111111111111111111111111
00000000000000000000000000
11111111111111111111111111
(b)
<<rProxy>>
<<rReal>>
<<rProxy>>
<<rProxy>>
<<rReal>>
RealSubject
+ request () <<rReal>>
Graphic
<<rProxy>>
<<RSubject>>
RealSubject
<<Subject>>
+ draw ()
RealSubject
+ request () <<request>>
"
piu
(a)
<<RSubject>>
Subject
<<rReal>>
<<request>>
<<Proxy>>
<<RSubject>>
<<Proxy>>
ImageProxy
Image
RemoteProxy
+ draw () <<rProxy>>
class
+ draw ()<<rReal>>
class
+ draw ()<<rProxy>>
class
p:
rs:
p:
draw()
draw()
<<rProxy>>
draw()
draw() <<rReal>>
<<rReal>>
<<rProxy>>
(c)
Fig. 10. (a) Satisfaction of Full Pattern, where Outer Square is Pullback. (b) Annotated
Model Satisfying the Proxy Pattern. (c) First Step in Satisfaction Checking.
model (maybe created by hand) conforms to a pattern; and (iv) to automatically
complete a model according to a pattern. In this section we concentrate on the
latter, giving the algorithm for pattern application for model completion and
proving its correctness.
We start by showing how to apply the primary pattern, and then present
how synchronization with the secondary patterns is achieved. Given a pattern
(V P, SP, Sec = {(IPs , SGs )}s∈S ), the application of the primary pattern SP to
an annotated model M = (Ms ← Mc → Mt ) is as follows:
1. Vocabulary Extension. Add the vocabulary of the pattern to Mt if it was
not added before (i.e. this is the first instance of the pattern).
2. Role Annotation. The user selects in Ms the elements playing some role
in the pattern. Thus, a RoleMap node is created in Mc for each of these
elements, associated with a node pm of type PatternInstance. pm is a new
node for a new instance of the pattern, or an existing one, if extending a
previous instance. Construct the morphisms from the modified annotation
graph Mc to Mt and Ms . A new instance cannot be created if the number
of existing instances would exceed the interval for the pattern root.
3. Instance Extraction. Construct a pattern graph P G by navigating from
pm to the elements in Mc belonging to the defined instance of the pattern,
and from these to elements in Mt and Ms along the cs and ct morphisms.
4. Variability Instantiation. The user selects a number ri in the range
int(Vi ) = (li , hi ) for each variable part Vi of the pattern, such that the
existing number of instances ei plus the new ones ri satisfy the interval.
Build a graph P C as the colimit6 of the fixed part of the pattern P and
ri + ei instantiations of each variable part.
5. Model Extension. Construct the pushout7 M ′ of P C and M through P G.
v1 o root OOv1
Example. Fig. 11 shows the application of a patOO'
oo
o
w
tern with variable part V1 and nested part V2 .
...
V1 < v12
V
1
v12
Once V1 and V2 are instantiated, we build the col- v12 £¥¥ ::¿ v12
£¥¥ <Á
V2 ... V2
imit P C and the pushout M ′ of P C ← P G → M . V2 ... V2 A
AÃ ~}}
Fig. 12 shows the application of the Proxy to a
. PC p
/ M′
O
O
model M containing a class Image, which the user
P.O.
/M
mapped to role RealSubject. The name of the
PG
operation in the pattern (“request”, a variable) is
mapped to the name of the operation in the model Fig. 11. Application of
(“draw”), and similarly for class names. The user Structural Pattern.
selected two instantiations of the variable part;
hence two proxies are created in the resulting model M ′ . In the pushout, the
new elements may contain variables, like the name of the Proxy class to be added.
In this case, either the user provides a value (ImageProxy and RemoteProxy in
the example), or default ones are obtained from the role names. ¥
V SP
0
<<Subject>>
V SP
1
Subject
<<Subject>>
Subject
+ request () <<request>>
V SP
1
+ request () <<request>>
<<Subject>>
Subject
+ request () <<request>>
<<RSubject>>
RealSubject
<<RSubject>>
<<Proxy>>
Proxy
+ request () <<rProxy>>
+ request () <<rReal>>
PC
<<RSubject>>
<<Proxy>>
+ request () <<rReal>>
RealSubject
RealSubject
Proxy
+ request () <<rProxy>>
+ request () <<rReal>>
M’
<<Subject>>
Subject
<<Subject>>
Subject
+ draw ()
+ request () <<request>>
<<RSubject>>
<<Proxy>>
RealSubject
Proxy
+ request () <<rProxy>>
+ request () <<rReal>>
PG
<<RSubject>>
RealSubject
+ request () <<rReal>>
<<request>>
<<Proxy>>
<<Proxy>>
<<RSubject>>
<<Proxy>>
Proxy
ImageProxy
Image
RemoteProxy
+ request () <<rProxy>>
+ draw () <<rProxy>>
+ draw ()<<rReal>>
+ draw () <<rProxy>>
M
<<RSubject>>
Image
+ draw ()<<rReal>>
Fig. 12. Applying a Structural Pattern to an Annotated Model.
The application of the secondary patterns continues by enlarging the model
M ′ obtained in the previous procedure by a sequence of pushouts. Hence, we first
6
7
Roughly, a colimit [9] is the smallest object in which a diagram made of objects and
morphisms is embedded (assuming injective morphisms).
Given two objects Ai , whose “intersection” is given by A1 ← I → A2 , the pushout
A1 → B ← A2 is their union, where the common elements (given by I) are “merged”.
check which variable parts ViSP were added to M to yield M ′ (steps 2a and 2b).
This is necessary as the user may have extended an existing instance. Then, the
synchronization graph is used to locate the variable part of the secondary pattern
VlIP synchronized with ViSP , and a pushout is built. We use an intermediate
IP
graph Bkl
(step 1) as pushout object, as it contains the intersection between
IP
Vl and the previous graph in the nesting structure, preventing the addition of
too many elements. The procedure is repeated for each secondary pattern:
1. ∀eil
jk : Ijk → Iil , edge in the synchronization graph, calculate the pushout
IP
IP
object Bkl
as shown in Fig. 13(left). Morphism Bkl
→ VlIP exists due
to the pushout universal property. Note also that if there are morphisms
IP
VkIP → M ′ and Iil → M ′ , then we uniquely have Bkl
→ M ′ due to the
IP
pushout universal property. Graph Bkl will be used later in this procedure.
2. For each (IP, SG) ∈ Sec do (i.e. for each sec. pattern and synch. graph):
– Traverse the graphs used to build the colimit P C in step 4 of the previous
procedure (see Fig. 11) in depth first order.
(a) Let ViSP be the current node; calculate the pullback object X of
ViSP → P C ← P G.
(b) If X ≇ ViSP then
i. If ViSP = rootSP then update the model M ′ according to the
pushout shown in the center of Fig. 13.
ii. Else let VjSP be the predecessor of ViSP in EmbSP and update
the model M ′ according to the diagram to the right of Fig. 13.
iii. Repeat
• Let VmIP be the child of VlIP in EmbIP . Update the model
(like in steps i and ii) for each instance VnSP s.t. VnSP ← Inm →
VmIP , and whose pullback object X in VnSP → P C ← P G is
not isomorphic to VnSP .
Until all descendants of VlIP ∈ EmbIP have been visited.
/ Iil
Ijk
Ijk SS
Iij
SSSS
??
kkk
k
Ä
k
?
SSSS
k
Ä
??
kk
k
² P.O. ²
ÄÄ
SS)
k
²
k
Â
Ä
Ä
u
k
IP
IP
SP
/ Bkl
P.O.
Vk
Vj
Iil F
VkIP
VjIP
ViSP
HH
F
x
@@
w
F
w
FF
HH
xx
@@
² ¨
{www
"
²
$
{xx
@Â ² P.O. ²
+ V IP
IP
SP
/ VlIP
Bkl
Vi
l
HH
M ′ / M ′′
HH
P.O.
¹³
#
{
²
- M′
, M′
/ M ′′
IP
Fig. 13. Building Bkl
(left). First (center) and Second (right) Cases for Model Update.
The procedure is incremental – one can update an existing instance – and
supports heterogeneous synchronization, e.g. Fig. 7, where the structural pattern
has two independent variable parts and nesting in the interaction pattern.
Example. For Proxy, Fig. 14 shows how the first sequence diagram is created
starting from M ′ of Fig. 12. Note that, as there were two instantiations of V SP ,
the procedure would follow by adding an additional sequence diagram. ¥
V IP
0
I
<<RSubject>>
B IP
RealSubject
<<RSubject>>
class
<<Proxy>>
<<RSubject>>
Proxy
RealSubject
+ request () <<rProxy>>
RealSubject
rs:
V IP
1
<<Proxy>>
<<RSubject>>
Proxy
RealSubject
+ request () <<rReal>>
class
p:
<<Subject>>
Subject
Subject
Subject
+ draw () <<request>>
+ draw ()
<<request>>
ImageProxy
RemoteProxy
+ draw () <<rProxy>>
RemoteProxy
ImageProxy
+ draw () <<rProxy>>
+ draw () <<rProxy>>
Image
Image
+ draw ()<<rReal>>
class
rs:
RemoteProxy
ImageProxy
+ draw () <<rProxy>>
class
+ draw () <<rProxy>>
<<RSubject>>
p:
<<RSubject>>
<<RSubject>>
+ draw ()<<rReal>>
<<Proxy>>
<<Proxy>>
<<Proxy>>
<<Proxy>>
<<Proxy>>
+ draw () <<rProxy>>
<<Subject>>
<<Subject>>
+ draw () <<request>>
<<Proxy>>
request() <<rReal>>
<<rProxy>>
M’’’
M’
rs:
request()
rs:
M’’
class
class
Image
+ draw ()<<rReal>>
class
rs:
draw()
<<rProxy>>
draw()
<<rReal>>
Fig. 14. Synchronization: Building the First Sequence Diagram.
Finally, it can be shown that, after applying a pattern according to the
previous procedure, the resulting model satisfies such pattern according to Def. 6.
′
Proposition 1 (Application Correctness). If model M k is obtained from
′
M by applying pattern SP according to the previous procedure, then M k |= SP .
Proof Sketch. The nodes Iij of SG are the pullbacks of ViSP → O ← VjIP . When
applying the primary pattern, the vocabulary model is added to M , and after the
′
′
pushouts for the secondary pattern are made, yielding M k , we have O → M k .
k′
IP
SP
This implies that all Iij are the pullback objects of Vi → M ← Vj . The
′
satisfaction M k |= SP then follows as the application procedure takes care of
the correctness of the replications w.r.t. the allowed variability intervals (step 4
of the application of the primary pattern). ¥
5
Conclusions and Future Work
We have presented a formal approach to the specification of patterns, as well
as procedures for checking whether a model satisfies a pattern and applying a
pattern to a model for model completion. In the proposed formalization, patterns
are annotated by roles in a vocabulary, support the synchronization of different
types of diagrams, and allow the definition of variable parts, possibly nested.
The proposal relies on a general meta-model for patterns, not necessarily based
on UML.
Our approach presents several benefits w.r.t. existing ones. First, variability regions – with the possibility of nesting – are more flexible than current
proposals, which annotate single elements with cardinalities [3] and for which
it is more difficult to express that several elements have to vary together. Second, our mechanism for pattern application considers synchronization of several
diagrams. Third, we separate the roles from the pattern structure by a triple
graph, without extending existing meta-models. This clean and non-intrusive
solution facilitates the manipulation and querying of the vocabulary models, as
well as the identification of pattern instances. Our formal treatment facilitates
the derivation of rules for refactoring towards patterns.
We plan to investigate pattern conflicts and reason about pattern interaction
effects, e.g. using graph constraints or critical pairs [2] in pattern application.
Acknowledgments. Work supported by the Spanish Ministry of Science
and Innovation, projects METEORIC (TIN 2008-02081) and MODUWEB (TIN
2006-09678). We thank the referees for their insightful and detailed comments.
References
1. J. Dong, S. Yang, and K. Zhang. Visualizing design patterns in their applications
and compositions. IEEE Trans. Software Eng., 33(7):433–453, 2007.
2. H. Ehrig, K. Ehrig, U. Prange, and G. Taentzer. Fundamentals of Algebraic Graph
Transformation. Springer, 2006.
3. R. B. France, D.-K. Kim, S. Ghosh, and E. Song. A UML-based pattern specification technique. IEEE Trans. Software Eng., 30(3):193–206, 2004.
4. E. Gamma, R. Helm, R. Johnson, and J. M. Vlissides. Design Patterns. Elements
of Reusable Object-Oriented Software. Addison Wesley, 1994.
5. E. Guerra and J. de Lara. Event-driven grammars: Relating abstract and concrete
levels of visual languages. Software and System Modeling, 6(3):317–347, 2007.
6. H. Kampffmeyer and S. Zschaler. Finding the pattern you need: The design pattern
intent ontology. In MoDELS, volume 4735 of LNCS, pages 211–225. Springer, 2007.
7. S. K. Kim and D. Carrington. Using integrated metamodeling to define OO design
patterns with Object-Z and UML. In APSEC, pages 257–264. IEEE Computer
Society, 2004.
8. A. Lauder and S. Kent. Precise visual specification of design patterns. In ECOOP,
volume 1445 of LNCS, pages 114–134, 1998.
9. S. Mac Lane. Categories for the Working Mathematician. 2nd Edition. Graduate
Texts in Mathematics Vol 5. Springer, 1998.
10. J. K.-H. Mak, C. S.-T. Choy, and D. P.-K. Lun. Precise modeling of design patterns
in UML. In ICSE, pages 252–261. IEEE Computer Society, 2004.
11. J. Niere, W. Schäfer, J. P. Wadsack, L. Wendehals, and J. Welsh. Towards patternbased design recovery. In ICSE, pages 338–348. ACM, 2002.
12. A. Radermacher. Support for design patterns through graph transformation tools.
In AGTIVE, volume 1779 of LNCS, pages 111–126. Springer, 1999.
13. T. Taibi and D. C. L. Ngo. Formal specification of design pattern combination
using BPSL. Information and Software Technology, 45:157–170, 2003.
14. T. Tourwé and T. Mens. High-level transformations to support framework-based
software development. In SET, volume 72-4 of ENTCS, 2003.
15. W. van der Aalst, A. ter Hoefstede, B. Kiepuszewski, and A. Barros. Workflow
patterns. Distributed and Parallel Data Bases, 14(3):5–51, 2003.
16. C. Zhao, J. Kong, J. Dong, and K. Zhang. Pattern-based design evolution using
graph transformation. J. Vis. Lang. Comput., 18(4):378–398, 2007.