Patterns of Software Architecture - Buschmann, Meunier, Rohnert, Sommerlad, Stal

Architectural Patterns

Layers (31) (context - a large system that requires decomposition) Helps to structure applications that can be decomposed into groups of subtasks in which each group of subtasks is at a particular level of abstraction.

Pipes and Filters (53) (context - processing data streams) Provides a structure for systems that process a stream of data. Each processing step is encapsulated in a filter component. Data is passed through pipes between adjacent filters. Recombining filters allows you to build families of related systems.

Blackboard (71) (context - an immature domain in which no closed approach to a solution is known or feasible) Useful for problems for which no deterministic solution strategies are known. In Blackboard, several specialized subsystems assemble their knowledge to build a possibly partial or approximate solution.

Broker (99) (context - the environment is a distributed and possibly heterogeneous system with independent cooperating components) Can be used to structure distributed software systems with decoupled components that interact by remote service invocations. A broker component is responsible for coordinating communication, such as forwarding requests, as well as for transmitting results and exceptions.

Model-View-Controller (125) (context - interactive application with a flexible HMI) Divides an interactive application into three components. The Model contains the core functionality and data. Views display information to the user. Controllers handle user input. Views and Controllers together comprise the user interface. A change-propogation mechanism ensures consistency between the user interface and the Model.

Presentation-Abstraction-Control (145) (context - development of an interactive application with the help of an agent [handles incoming events, updates its own state, and produces new events]) Defines a structure for interactive software systems in the form of a hierarchy of cooperating agents. Every agent is responsible for a specific aspect of the application's functionality and consists of three components: presentation, abstraction, and control. This subdivision separates the human-machine interaction aspects of the agent from its functional core and its communication with other agents.

Microkernal (171) (context - the development of several applications that use similar programming interfaces that build on the same core functionality) Applies to software systems that must be able to adapt to changing system requirements. It separates a minimal functional core from extended functionality and customer-specific parts. The microkernal alaso serves as a socket for plugging in these extensions and coordinating their collaboration.

Reflection (193) (context - building systems that support their own modification a priori) Provides a mechanism for changing structure and behavior of software systems dynamically. It supports the modification of fundamental aspects, such as type structures and function call mechanisms. In this pattern, an application is split into two parts. A meta level provides information about selected system properties and makes the software self-aware. A base level includes the application logic. Its implementation builds on the meta level. Changes to information kept in the meta level affect subsequent base-level behavior.

Design Patterns

Whole-Part (225) (context - implementing aggregate objects) Helps with the aggregation of components that together form a semantic unit. An aggregate component (the Whole): encapsulates its constituent components (the Parts), organizes their collaboration, and provides a common interface to its functionality. Direct access to the Parts is not possible.

Master-Slave (245) (context - partitioning work into semantically-identical subtasks) Supports fault tolerance, parallel computation, and computional accuracy. A master component distributes work to identical slave components and computes a final result from the results these slaves return.

Proxy (263) (context - a client needs access to the services of another component; direct access is technically possible, but may not be the best approach) Make the client of a component communicate with a representative rather than to the component itself. Introducing such a placeholder can serve many purposes, including enhanced efficiency, easier access, and protection from unauthorized access.

Command Processor (277) (context - applications that provide flexible and extensible user interfaces, or provide services related to the execution of user functions such as scheduling or undo) Separates the request for a service from its execution. A Command Processor component manages requests as separate objects, schedules their execution, and provides additional services such as the storing of request objects for later undo.

View Handler (291) (context - providing multiple views of application-specific data) Helps to manage all views that a software system provides. A view handler component allows clients to open, manipulate, and dispose of views. It also coordinates dependencies between views and organizes their update.

Forwarder-Receiver (307) (context - peer-to-peer communication) Provides transparent communication for software systems with a peer-to-peer interaction model. It introduces forwarders and receivers to decouple peers from the underlying communication mechanisms.

Client-Dispatcher-Server (323) (context - a software system integrating a set of distributed servers, with the servers running locally or distributed over a network) Introduces an intermediate layer between clients and servers - the Dispatcher component. It provides location transparency by means of a name service, and hides the details of the establishment of the communication connection between clients and servers.

Publisher-Subscriber (339) Helps to keep the state of cooperating components synchronized. To achieve this, it enables one-way propagation of changes - one Publisher notifies any number of Subscribers about changes to its state.


Counted Pointer (353) Makes memory management of dynamically allocated shared objects in C++ easier. It introduces a reference counter to a body class that is updated by handle objects. Clients access body class objects only through handles via the overloaded "operator->()".