Desing Patterns in Action
Today we will develop a custom output caching provider in asp.net 4.0. In .net framework 4.0 microsoft has emphasized on provider model for pluggable development. The provider model in .net 4.0 has been used and promoted extensively.
Developers can write their custom provider for logging, membership, caching, viewstate without affecting the existing application and plug that up with just configuration changes.
I will try to show this by writing custom file based output caching for asp.net 4.0 application. There may be scenario where memory based caching is expensive, so we can make use of provider model and write our own custom output caching.
1. Create a C# Library Project
2. Add reference to System.Web dll
Abstract Factory Design Pattern
We have already seen about factory method design pattern. abstract factory is about grouping similar family of factory pattern and providing abstract layering for them.
The main motto of abstract factory design pattern is "Provide an interface for creating families of related or dependent objects without specifying their concrete classes." as specified in GoF. Below are the main members of this design pattern:
AbstractFactory - An interface with Get operations for each of the abstract products
Factory1, Factory2 - Implementations of all the AbstractFactory creation operations
AbstractProduct - An interface for a kind of product with its own operations
ProductA1, ProductA2, ProductB1, ProductB2 - Classes that implement the AbstractProduct interface and define product objects to be created by the corresponding factories
Client - A class that accesses only the AbstractFactory and AbstractProduct interfaces
Factory Method Pattern
Factory method pattern is a very light weight pattern. It is used in the scenarios where we do not want the client directly refer to the concrete classes for object instantiation, rather we handover the responsibility to a "Creator" class which will be instantiating the appropriate object based on the client requirement and thus centralizing the code of object creation. And client deals with interface instead of concrete classes. Factory method is also termed as "Virtual Constructor" in C++.
Intent & Motivation of Factory Pattern: "Define an interface for creating an object, but let subclasses decide which class to instantiate." Since library knows when an object needs to be created, but not what kind of object is going to be created. As this is specific to the application it can use the Factory Method.
Factory pattern is used when:
- Flexibility is important.
- Objects can be extended in subclasses
- There is a specific reason why one subclass would be chosen over another. This logic forms part of the Factory Method.
We can think of below scenarios where Factory method pattern can be implemented:
- Set upa system to draw circles, squares, and lines. Create a Factory Method that instantiates one of these classes at random and uses it to draw a shape of random size on the screen. Run the program to see what interesting shapes you get.
A company has a web site to display test results from a plain text file. The company recently purchased a new computer that produces a binary data file, and it has another new machine on the way that will possibly produce a different data file. The company is also considering switching to an XML format. Write a system to deal with such changes. The web site just needs data to display; your job is to provide the specified data format for the web site.
We have list of movies categorized into genre. Client wants to get the specific genre movies. Here client can deal with movie interface and based on his parameter passed to FactoryMethod he will get the list of movies.
So let us work on the 3rd movie list example. More...
Singleton Design Pattern
This pattern is used where only one instance of the object is required and shared among all the clients. The same instance is maintained throughout the entire life cycle of the class object. This is not handled by the client code rather it is the responsibility of the class to make sure that only one intsance exists throughout all the client calls.
So how this is possible? If I have access to the class I can create as many instances by just using new.
That is not true. If I make the constructor private, I can not create object using new.
But then how I will get the object? This is further done by exposing a public static GetInstance (you can give it any meaningful name) method/property.
- A private static variable of the Singleton Class type is defined and intantiated in the private static constructor of the class. So when a call occurs to the GetInstance method this same static object is returned.
- Also as best practice it is ensured that private static instance variable is instantiated only when it is required.
- Also there exist thread safe version of this Singleton Class by putting a lock while instantiating the class object. We also mark singleton class as sealed to make it more safe, so that no subclass can attempt to intantiate and get more that one instance.
- It makes sure that only one instance of the class exists
- Can get access to data in this class from anywhere
- Acts like global variable
- Can cause methods to have unintended and unintefied side effects due to data sharing via state in the singleton
Steps to implement Singleton Pattern:
- Make constructor private
- Add a private static object which will be internally instantiate using the private static constructor
- Add a public static property which will return the instance of the class
Decorator Design Pattern
What is Decorator Pattern?
Decorator expands the functionality of an instance of class without changing the class code. It provides a way to attach new state and behavior to an object dynamically. The object does not know it is being decorated. It takes and existing object and adds new functionality to it.
We can take example of a window which can be decorated with a scroll bar if the content displayed on the window is gets over-flowed. Also we can think example of decorating an existing image with border/watermark at runtime. So we can see that the beauty of this pattern is:
- The original object is unaware of decoration.
- Now we don't need to create one big class full of all the features, rather we can decorate the object at runtime mixing the decorations to them.
So what are the various essential players to the decorator pattern?
Original class(es) which are going to be expanded by adding new features to them.
An interface IComponent, which contains the operations which can be replaced.
A class which implements/inherits from IComponent and adds state and/or behaviour to the Component.
Decorator pattern has 2 kind of relationship:
Decorator inherits of IComponent and can be used in place of IComponent by client.
Decorator instantiates one or more IComponent objects, decorates them and they can be replace the original IComponent objects.
Repository pattern is one of the pattern which is most frequently used in Data access layer. This provides an abstraction to underlying database. This is also useful when database is not ready and we want to test the application by building an stub.
So repository pattern provides testability, abstration and dependency injection.
Repository is defined as "an abstraction that provides us with persistence ignorance and a separation of concerns where the responsibility of persisting domain objects is encapsulated by the Repository that leaving the domain objects to deal entirely with the domain model and domain logic."
I am going to show a sample of repository pattern implementation with c# and entity framework. Our entity framework DataContext object will be inside the constructor of the repository class. This will implement IDisposable interface to make sure that object is disposed properly in case of any failure or when object is no more required.
We will delcare some of the most frequenlty used operations in interface such as GetOne, GetMany, Filter, Save, Delete.
So IRepository and RepositoryImplementation Class will be the building blocks of repository pattern.More...