Introduction
This article will show you how to use the observer pattern in an ASP.NET application.
What is Observer Pattern ?
Observer Pattern is a Behavioural Pattern which allows one-to-many dependencies between objects so that when one object state changes, all dependent objects can be notified and updated automatically. The following diagram will show you the class hierarchy of the Observer pattern. A typical Dashboard Web page could be a good example for the Observer pattern implementation. Imagine a Sales dashboard web page with several reports. When any of the values change in the Dashboard page, all the relevant reports should change/update accordingly. Observer pattern allows the flexibility to add/remove reports to the dashboard page dynamically and hence works independently. The following diagram will give you an elaborated view on the Observer pattern class hierarchy.
Implementation
To understand the observer pattern thoroughly, follow the following Observer pattern implementation in the ASP.NET application. This should give you a clear understanding about the Observer pattern and its usage.
The requirement is to create a Sales dashboard Web page which can attach several Sales reports. (We'll create Web User controls for each report). The values of the report depend on the Dashboard page product selection. This is a perfect scenario to introduce the Observer pattern.
Walkthrough
Step 1 - To start the project, create an ASP.NET Web Application project.
Step 2 - Create a Subject class (DashboardPage
) and then create the following properties and methods:
Properties
List<IReport> _ReportCollection
– To hold the list of observers
public string SelectedProduct
– Selected Product Value
Methods
Add(IReport module)
– To add an observer
Remove(IReport module)
– To Remove an observer
Update()
– This method will update all the dependent observers
The complete code for Subject
class (DashboardPage
) is as follows:
public class DashboardPage : System.Web.UI.Page {
private List<IReport> _ReportCollection = new List<IReport>();
public string SelectedProduct { get; set; }
public DateTime SelectedDate { get; set; }
public DashboardPage() {
}
public void Add(IReport module) {
_ReportCollection.Add(module);
}
public void Remove(IReport module) {
_ReportCollection.Remove(module);
}
public void Update() {
foreach (IReport m in _ReportCollection) {
m.Update(this);
}
}
}
The DashboardPage
will act as the main subject for all the Sub Reports.
Step 3 - Create an Observer interface and add an Update
method definition by passing the Subject
as a parameter.
The complete code for the observer interface is as follows:
public interface IReport
{
void Update(DashboardPage page);
}
Note: The reason for creating an observer as an interface is to give the flexibility to do its own implementation in derived classes.
Step 4 - Create a SalesDashboard.aspx web page and inherit it from the DashboardPage
class.
Step 5 - Drag & drop a Dropdownlist
control to the SalesDashboard.aspx page and bind some string
values. The bound values will be sample product names. The selected value will be assigned to the SelectedProduct
property inside the Page.OnLoad
event handler.
The complete code for the SalesDashboard.aspx page is as follows:
public partial class SalesDashboard : DashboardPage
{
protected override void OnLoad(EventArgs e) {
SelectedProduct = this.DropDownList1.SelectedValue;
Add(SalesReport11);
Add(SalesReport21);
base.OnLoad(e);
}
protected void Button1_Click(object sender, EventArgs e) {
Update();
}
}
Step 6 - We also need to create WebUserControls
as observers. Create two Web user controls and name them Report1
and Report2
respectively.
Implement the IReport
interface and write your own implementation for the Update
method as shown below:
public void Update(DashboardPage page) {
this.Label1.Text = page.SelectedProduct;
this.Label2.Text = page.SelectedDate.ToLongDateString();
}
Basically, the first report will show the selected Product
in a label control and for the second report, you can write your own implementation.
After creating Report1
and Report2 WebUserControls
, drag & drop them into the SalesDashboard.aspx page. In the code behind file, add those reports to the page’s ReportCollection
property as shown in the following code:
protected override void OnLoad(EventArgs e) {
………
Add(SalesReport11);
Add(SalesReport21);
base.OnLoad(e);
}
……………
Step 7 - Add the Update
method in the button click event and then run the web application.
Here you have completed the Observer pattern implementation in ASP.NET web application. When you click on the button, all the dependant observers will get updated by taking the value which is set on the Dashboard
page (subject). The best way to observe the code behaviour is to run the debugger through the code.
Tips
You can add the Reports (observers) dynamically when the page loads by validating its interface type. But doing so will compromise the application performance, web pages are stateless and for each page load it has to iterate through all the controls and then bind the IReport
interface type controls. So adding a report statically is the best option, moreover it will give you the flexibility to add/remove reports whenever required easily without modifying the underlying code.
Conclusion
Observer pattern is a behavioural pattern in the Software Patterns family. By extending the observer pattern, applications design flexibility can be increased drastically.
History
- 10th September, 2009: Initial post