ER Diagrams, Domain Model, and N-Layer Architecture with ASP.NET 3.5 (part2)

Exclusive offer: get 50% off this eBook here
ASP.NET 3.5 Application Architecture and Design

ASP.NET 3.5 Application Architecture and Design — Save 50%

Build robust, scalable ASP.NET applications quickly and easily.

£14.99    £7.50
by Vivek Thakur | June 2009 | .NET Architecture & Analysis Microsoft

This is the second part of two-part article by Vivek Thakur on N-Layer Architecture with ASP.NET 3.5. In the first part we saw the need for a 3-layered solution and examined ER-diagrams, domain models and UML. In this part we will we will explore a 1-tier 3-layer Architecture using a Domain Model and Object Data Source Controls.

1-tier 3-layer Architecture using a Domain Model

Based on the class diagram in the first part, we will create a new simple 3-layered application using the entities defined in the above domain model. We will create a new ASP.NET Web Project in VS. This time, you should create two new folders inside your root web folder (using the Add New Folder option in VS):

  • BL: This folder will contain all of the business logic domain classes
  • DAL: This folder will contain the data access code files (for each entity)

Layer 1: Data Access Layer (DAL)

First, we will create a DAL class for each entity. We will name each DAL class using this naming pattern: EntityDAL. Let us see the CustomerDAL class:

using DomainModel.BL;
namespace DomainModel.DAL
{
public class CustomerDAL
{
public static void AddCustomer(Customer cs)
{
using (SqlConnection con =
new SqlConnection(SQLHelper.GetConnectionString()))
{
SqlParameter[] par = new SqlParameter[4];
par[0] = new SqlParameter("@customerID", cs.ID);
par[0].Direction = ParameterDirection.Output;
par[1] = new SqlParameter("@name", cs.Name);
par[2] = new SqlParameter("@address", cs.Address);
par[3] = new SqlParameter(
"@phoneNo", cs.PhoneNumber);
int rowNo = SQLHelper.ExecuteNonQuery(
con, CommandType.StoredProcedure,
"OMS_AddCustomer", par);
cs.ID = Convert.ToInt32(par[0].Value);
}
}
public static void DeleteCustomer(int customerID)
{
using (SqlConnection con =
new SqlConnection(SQLHelper.GetConnectionString()))
{
SqlParameter[] par = new SqlParameter[1];
par[0] = new SqlParameter("@customerID", customerID);
int rowNo = SQLHelper.ExecuteNonQuery(
con, CommandType.StoredProcedure,
"OMS_DeleteCustomer", par);
}
}
public static void UpdateCustomer(Customer cs)
{
using (SqlConnection con = new
SqlConnection(SQLHelper.GetConnectionString()))
{
SqlParameter[] par = new SqlParameter[4];
par[0] = new SqlParameter("@customerID", cs.ID);
par[1] = new SqlParameter("@address", cs.Address);
par[2] = new SqlParameter("@name", cs.Name);
par[3] = new SqlParameter(
"@phoneNo", cs.PhoneNumber);
int rowNo = SQLHelper.ExecuteNonQuery(
con, CommandType.StoredProcedure,
"OMS_UpdateCustomer", par);
}
}
public static void GetCustomer(Customer cs)
{
using (SqlConnection con =
new SqlConnection(SQLHelper.GetConnectionString()))
{
SqlParameter[] par = new SqlParameter[1];
par[0] = new SqlParameter("@customerID", customerID);
using (SqlDataReader dr =
SQLHelper.ExecuteReader(con,
CommandType.StoredProcedure,
"OMS_GetCustomer", par))
{
c = new Customer();
while (dr.Read())
{
c.Name =
SQLHelper.CheckStringNull(dr["Name"]);
c.PhoneNumber =
SQLHelper.CheckStringNull(dr["PhoneNo"]);
c.Address =
SQLHelper.CheckStringNull(dr["Address"]);
c.ID = SQLHelper.CheckIntNull(dr["ID"]);
}
}
}
}
public static List<Customer> GetAllCustomers()
{
List<Customer> cuList = new List<Customer>();
using (SqlConnection con =
new SqlConnection(SQLHelper.GetConnectionString()))
{
using (SqlDataReader dr =
SQLHelper.ExecuteReader(con,CommandType.
StoredProcedure,"OMS_GetAllCustomer"))
{
while (dr.Read())
{
Customer customer = new Customer();
customer.Name =
SQLHelper.CheckStringNull(dr["Name"]);
customer.PhoneNumber =
SQLHelper.CheckStringNull(dr["PhoneNo"]);
customer.Address =
SQLHelper.CheckStringNull(dr["Address"]);
customer.ID =
SQLHelper.CheckIntNull(dr["ID"]);
cuList.Add(customer);
}
}
}
return cuList;
}
}//end class
}

Here, we have used the SqlHelper class, which contains generic data access utility methods, so that we can avoid code repletion.

Layer 2: Business Layer (BL)

Next, we will create classes for each of the domain entities. We will put all of these classes under the new BL folder with this namespace: DomainModel.BL. Create a new C# class file named Customer.cs under the BL folder. Here is the first Customer class:

using DomainModel.DAL;
namespace DomainModel.BL
{
public class Customer
{
private int _ID;
private string _name;
private string _address;
private string _phoneNumber;
private List<Customer> _customerCollection;
public int ID
{
get { return _ID; }
set { _ID = value; }
}
public string Name
{
get { return _name; }
set { _name = value; }
}
public string Address
{
get { return _address; }
set { _address = value; }
}
public string PhoneNumber
{
get { return _phoneNumber; }
set { _phoneNumber = value; }
}
public List<Customer> CustomerCollection
{
get { return _customerCollection; }
set { _customerCollection = value; }
}
public void Add()
{
CustomerDAL.AddCustomer(this);
}
public void Delete(int customerID)
{
CustomerDAL.DeleteCustomer(this.ID);
}
public void Update()
{
CustomerDAL.UpdateCustomer(this);
}
public void Load()
{
CustomerDAL.GetCustomer(this.ID);
}
public void GetAll()
{
this.CustomerCollection = CustomerDAL.GetAllCustomers();
}
}//end class
}//end namespace

The CustomerDAL class is pretty simple: we are fetching the data from the database using data readers, and performing all data related operations using the Customer business object. This Customer class is defined in the Customer.cs class we created earlier. This BL class is calling DAL methods, so it needs a reference to the DAL namespace (using DomainModel.DAL). Similarly, the DAL class we created earlier used Customer business objects. That's why it also needed the BL namespace.

We are using generics to create a collection of Customer objects. The BL communicates with DAL to get the data and perform updates. Now, we will see how the UI (which is under a different namespace) talks to BL without even knowing about DAL.

Layer 3: The UI Layer

Here is the code in the AllCustomers.aspx.cs page that shows a list of all of the customers from the DB (there is a data list on the web form, which will show a list of the customers):

using DomainModel.BL;
namespace DomainModel.UI
{
//page load
private void FillAllCustomers()
{
Customer c = new Customer();
c.GetAll();
List<Customer> cuList = c.CustomerCollection;
dtlstAllCustomer.DataSource = cuList;
dtlstAllCustomer.DataBind();
}
}

So in the UI class, we neither have any data access code nor are we calling data access class methods from this layer (as was the case with the 1-tier 2-layer style we saw earlier in this article). We have a reference to the BL layer (using DomainModel.BL), and we are using the Customer business object to return a generic list of customer objects, which we are binding to the data list control (showing a list of all the customers). So the GUI layer does not know anything about the DAL layer, and is completely independent of it.

The idea here is to understand how a 3-Layer architecture can provide more flexibility and loose-coupling to your project. In the next section, we will learn how we can use object data source controls to implement a 3-layer architecture without writing much code ourselves.

ASP.NET 3.5 Application Architecture and Design Build robust, scalable ASP.NET applications quickly and easily.
Published: October 2008
eBook Price: £14.99
Book Price: £24.99
See more
Select your format and quantity:

Object Data Source Controls    

Data source controls can replace the data access code but they tightly couple the GUI to the data methods. To overcome this problem, Microsoft introduced object data source controls, so that we can bind directly to business objects, making it possible to use them in a 3-tier architecture.

Let's see how using object data source controls will shape our application:

  1. Create a new web project using VS.
  2. Add a new form named datasource-customer.aspx.
  3. Add an object data source control, as shown here (drag and drop the object data source control from the Data tab under ToolBox in VS):
  4. Now, we need to configure this object data source control. We first need to set the Business object , where we select our customer class:
  5. Then, we need to set the SELECT, UPDATE, and INSERT methods. For our sample, we will just set the SELECT method:
  6. Then, we select Finish. We then add a GridView control on the same page and set the data source to our object data source control:
  7. Now we run the page, and voila! We see all of the records without using any code in the UI layer!

    ER Diagrams, Domain Model, and N-Layer Architecture with ASP.NET 3.5 (part2)

As we can see, using object data source controls complements the domain model and helps us avoid writing the UI layer code, as we can directly bind custom entities to data-bound controls in UI.

However, there are a few issues in using object data source controls:

  • They are not very flexible. Sometimes we need to display data in UI in a complex way (which can be user friendly, but code un-friendly). In such cases, it is best to use and manipulate custom collections using manual coding; you cannot even extend the control to customize it.
  • There is a slight performance hit when using object data source controls instead of using manual coding. This hit comes through the use of reflection by the control to access a class's attributes and methods.

Reflection is a technique which VS uses to get metadata information about other entities, such as a class file or an assembly. Using reflection, the object data source control will first "read" the class to get all of the attributes and then use this metadata to connect to and perform operations on the class. On account of this additional "reading" step, the application suffers a performance hit.

Therefore, for a flexible approach, it is best to use custom code. But for small projects where we don't foresee any major complexity and performance issues, object data source controls are a good option to save on development time while supporting a flexible n-layer option.

Summary

All of the samples we covered in this two-part article were of the 1-tier n-layer style. We learned how to create a 1-tier 2 layer architecture using logical code separation. Then we focused on the need for a 3-layered solution and examined ER-diagrams, domain models and UML, all of which are important tools that aid in the understanding of commercial projects required to build a 3-layered structure.

We then focused on a 3-layered application structure for OMS, and looked at how both custom code and object data source controls can be used in this architecture.

If you have read this article you may be interested to view :

ASP.NET 3.5 Application Architecture and Design Build robust, scalable ASP.NET applications quickly and easily.
Published: October 2008
eBook Price: £14.99
Book Price: £24.99
See more
Select your format and quantity:

About the Author :


Vivek Thakur

Vivek is passionate about architecting and developing applications based on Microsoft .NET platform using ASP.NET, C#, VB.NET, and MS AJAX. He has authored several technical articles on ASP.NET and has also been an All-Star-level contributor on ASP.NET forums. Vivek’s passion for ASP.NET has been formally recognized by the Most Valuable Professional (MVP) award given to him by Microsoft in April 2007, and again in 2008. He is also a Subject Matter Expert for Microsoft ASP.NET 3.5 Certification Exams. He is a leading contributor and moderator in the CodeAsp.Net forums. Vivek is currently working as the Managing Partner in Axero Solutions LLC, a US-based software product development and business consulting firm.

Although his expertise lies in Microsoft's .NET platform, Vivek is also knowledgeable in J2EE and C/C++. He has a deep interest in programming, chaos theory and artificial intelligence, and is a strong advocate of chaos theory in software systems and management.

Besides his love for software architecture and design, Vivek also focuses on project management skills and has substantial experience in managing small to medium sized projects. He has also conducted numerous training sessions and provided concept-based tutoring in different software firms across India.

Vivek received his Bachelors degree in engineering from the Indian Institute of Technology (IIT), New Delhi, India.

Contact Vivek Thakur

Books From Packt

Software Testing with Visual Studio Team System 2008
Software Testing with Visual Studio Team System 2008

SOA Patterns with BizTalk Server 2009
SOA Patterns with BizTalk Server 2009

LINQ Quickly
LINQ Quickly

Entity Framework Tutorial
Entity Framework Tutorial

ASP.NET 3.5 Social Networking
ASP.NET 3.5 Social Networking

C# 2008 and 2005 Threaded Programming: Beginner's Guide
C# 2008 and 2005 Threaded Programming: Beginner's Guide

Expert Cube Development with Microsoft SQL Server 2008 Analysis Services
Expert Cube Development with Microsoft SQL Server 2008 Analysis Services

Small Business Server 2008 – Installation, Migration, and Configuration
Small Business Server 2008 Installation, Migration, and Configuration

Code Download and Errata
Packt Anytime, Anywhere
Register Books
Print Upgrades
eBook Downloads
Video Support
Contact Us
Awards Voting Nominations Previous Winners
Judges Open Source CMS Hall Of Fame CMS Most Promising Open Source Project Open Source E-Commerce Applications Open Source JavaScript Library Open Source Graphics Software
Resources
Open Source CMS Hall Of Fame CMS Most Promising Open Source Project Open Source E-Commerce Applications Open Source JavaScript Library Open Source Graphics Software