-
Notifications
You must be signed in to change notification settings - Fork 55
DesignPatterns
This document highlights where common design patterns are used in FOAM.
The Sink ({put, remove, error, eof}) and the MDAO Index interfaces are uses of the Strategy pattern. (DAO's, parsers, Actions, Views, are also uses of the Strategy pattern, but since they're also uses of other patterns which are specialized versions of the Strategy pattern, they're listed under those patterns instead.)
ProxyDAO is a Proxy for the DAO interface. It is a convenient super-class for DAO Decorators.
SeqNoDAO, CascadingRemoveDAO, ActionFactoryDAO, DefaultObjectDAO, LRUCachingDAO, and WaitCursorDAO are all DAO Decorators.
The various DAO implementations implement the Bridge pattern. The purpose of the DAO interface is to have a common interface which can represent/bridge various underlying storage technologies. Data can be stored in IndexedDB, local-storage, on the server via a REST interface, in a Node.js database like MongoDB, or even just in an array. The DAO interface bridges the gap between these various technologies and makes them all appear identical to the FOAM programmer.
FOAM's EventService class is a direct implementation of the Observable pattern. One interesting extension however is the support for hierarchical topics.
FOAM's PropertyChangeSupport class extends EventService to add support for Java Bean's style property change listeners.
All Modelled objects in FOAM extend PropertyChangeSupport, making them Observable.
DAO's are also observable via the listen() and pipe() methods.
DAO's, Views, and Parsers all implement the Composite pattern.
The Interpreter pattern is a specialization of the Composite pattern. mLang's are a textbook implementation of the Interpreter pattern.
Actions are a directly implementation of the Command pattern.
The create() method of every Model is a factory method for creating objects of the type defined by that Model.
NullDAO is a NullObject implementation of the DAO interface. It is a DAO which stores nothing and does nothing.
MDAO Indices are flyweights. This gives the advantage of OO polymorphism without the overhead of having to build an object for every node in an MDAO tree.
The EasyDAO model is a textbook example of Facade. It makes it easy to create a decorated DAO
The builder pattern is used for building complex objects, or composite objects, from a specification. This is exactly how FOAM uses Model specifications to create Javascript prototypes (classes) at runtime.
Given that Javascript is a prototype-based OO language, prototypes are used as a replacement for classes in traditional class-based OO languages. The Model.getPrototype() method returns the prototype created for a Model. Also, any Modelled object can be used as a prototype by calling the .clone() method to create a copy.
FOAM/JS is an MVC Framework, so almost everything in FOAM relates to the Model View Controller pattern in one way or another. DAO's are Models for storing collections of objects (for use with DAOController, DAOListView or custom controllers and Views). Modelled objects are Observable, so are themselves suitable Models (say, when used with a DetailView). Individual Modeleld object properties implement the Value interface so can serve as the Models for single-field Views like TextFieldView.
FOAM has two View hierarchies: Views, which all extend from AbstractView, and Canvas Views, or CViews, which all extend from CView.
A unique feature of FOAM is its support for reusable collection-level Controllers (ie. DAOController or ThreePaneController). FOAM is unusual in that it implements MVC pattern across at all three levels: collections of objects, individual objects, and single properties of individual objects.