Click here to Skip to main content
65,938 articles
CodeProject is changing. Read more.
Articles / web / HTML

Using NHibernate in ASP.NET

5.00/5 (7 votes)
25 Mar 2011CPOL3 min read 49.8K  
How to use NHibernate in ASP.NET

Introduction

We often need to create a Data Access Layer (DAL) which takes our business objects and performs CRUD (Create, Read, Update and Delete) in physical data store. If you have ever created the DAL, you will come to know how tedious it is to do it again and again. Also, it’s very time consuming to map our objects to the relational database. Here comes Object Relational Mapper (ORM).

Object Relational Mapping (ORM) is a technique by which we map our objects in Object Oriented Programming to get mapped to the underlying relational database. For example, if we have a student object with attributes Name, Age, Roll No, etc. and a database table name Student with columns Name, Age, Roll no, etc. In traditional approach, we will run an insert/update/delete/select query with scalar values to perform manipulations in database. But, what if we have the ability to directly save/remove/read/update the student object without thinking about the underlying database. The query itself is getting removed.

Why NHibernate?

NHibernate is an ORM framework which has the built in capability of concurrency checks, transactions, lazy loading (objects are not initialized until in use) and transparent persistence (allows to change the DAL without changing Domain Model). To download the latest version of NHibernate, visit NHibernate.

Let’s see the steps involved in configuring NHibernate to use in ASP .NET. Following are the common steps to be followed:

  1. Design your database
  2. Create your class files
  3. Create Mapping files to map class to database
  4. Create a Session Factory class
  5. Configure web.config file to use the datasource
  6. Create a Service class for CRUD

Design Your Database

We start our example by creating a simple database name Students and creating a table name Student with following columns:

Note: The Id is auto generated.

Create the Class File (POCO Class)

Plain old CLR objects (POCO means that they do not need to inherit from or implement an interface) business entities are mapped into the table entity. We now create a class file with these columns as properties. The Id column will be read only as it is getting generated in the database as identity. Our class file would look like:

C#
Public class Student
{
private string name;
private int id;
private DateTime dateofbirth;
private string address;
public int ID
{
get { return id; }
private set { id = value; }
}
public string Name
{
get { return name; }
set { name = value; }
}
public string Address
{
get { return address; }
set { address = value; }
}
public DateTime DateOfBirth
{
get { return dateofbirth; }
set { dateofbirth = value; }
}
}

Create Mapping Files

Once our class files and table design is complete, we need to create a mapping file which tells the framework what column to map with what properties in the class. It’s a simple XML file. The naming format of the file is Student.hbm.xml. Note the hbm in between student and xml.

XML
<?xml version="1.0″ encoding="utf-8″ ?>
<hibernate-mapping
xmlns="urn:nhibernate-mapping-2.2″
namespace="NHibernate.Demo.Dal"
assembly="NHibernate.Demo.Dal">
<class name="Student" table="Student" lazy="false">
<id name="ID" column="id" unsaved-value="0″>
<generator />
</id>
<property name="Name">
<column name="Name" not-null="true" />
</property>
<property name="Address">
<column name="Address" not-null="true" />
</property>
<property name="DateOfBirth">
<column name="DateOfBirth" not-null="true" />
</property>
</class>
</hibernate-mapping>

From the above mapping, we can see that we first need to define the namespace and assembly where our class files are located and have the same namespace and assembly. Next the class tag attribute name takes class name and table attributes the database table name. Next the ID tag is the identification section to identify the identity column. It uses reflection to accomplish it so that only database is able to create those IDs. You see the ID tag is defined above differently. Inside this class tag, we define all the properties with property tag, where name is class property and column tag name is the table column name.

We need to change the build action to embedded resource so that it gets embedded in the assembly.

Define a Session Factory Class

This class will read all of the mapping files and configuration data and build a session that will enable you to talk to the database.

C#
public class SessionFactory
{
private static NHibernate.ISessionFactory sFactory;
private static void Init()
{
NHibernate.Cfg.Configuration config = new NHibernate.Cfg.Configuration();
config.AddAssembly("NHibernate.Demo.Dal");
sFactory = config.BuildSessionFactory();
}
public static NHibernate.ISessionFactory GetSessionFactory()
{
if (sFactory == null)
{
Init();
}
return sFactory;
}
public static NHibernate.ISession GetNewSession()
{
return GetSessionFactory().OpenSession();
}
}

Configure web.config File to Use the datasource

We specify the database details with which we are making connection and the connection string in the web.config file. You also need to add reference to NHibernate.ByteCode.LinFu.dll and LinFu.DynamicProxy.dll which you can find in the NHibernate download.

XML
<configSections>
<section name="hibernate-configuration" 
    type="NHibernate.Cfg.ConfigurationSectionHandler, NHibernate"/>
</configSections>
<hibernate-configuration xmlns="urn:nhibernate-configuration-2.2″>
<session-factory>
<property name="connection.provider">
NHibernate.Connection.DriverConnectionProvider
</property>
<property name="dialect">
NHibernate.Dialect.MsSql2005Dialect
</property>
<property name="connection.driver_class">
NHibernate.Driver.SqlClientDriver
</property>
<property name="connection.connection_string">
Data Source=.\SQLEXPRESS;
AttachDbFilename=|DataDirectory|\QuickDemo.mdf;
Integrated Security=True;
User Instance=True
</property>
<property name="proxyfactory.factory_class">NHibernate.ByteCode.LinFu.ProxyFactoryFactory, 
    NHibernate.ByteCode.LinFu</property>
</session-factory>
</hibernate-configuration>

Create a Service Class for CRUD

Finally, we need a service class which will talk to NHibernate and the datasource to perform operations. Operations like taking the list, inserting new record, etc.

C#
public class StudentService
{
public static ICollection<Student> GetAllStudents()
{
using (NHibernate.ISession session = SessionFactory.GetNewSession())
{
return session.CreateCriteria(typeof(Student)).List<Student>();
}
}
public static void Add(Student student)
{
using (NHibernate.ISession session = SessionFactory.GetNewSession())
{
using (NHibernate.ITransaction transaction = session.BeginTransaction())
{
session.Save(student);
transaction.Commit();
}
}
}
}

As you can see, there is no single code written for query statements. This is because the NHibernate framework has taken care about the underlying process. NHibernate exposes two interfaces, IQuery and ICriteria, to perform query operations.

Download the complete project here.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)