就其将NHibernate引入到项目中的实现方式而言,与Rhino.Commons中所提倡的方式如出一辙,那就是基于IRepository模式。关于IRepository这个接口的定义在之前的这篇文章中已提到并做了相应说明,所以这里就不多做解释了。
左侧的类NHibernateRepository就是基于IRepository 基本的具体实现,也就是所谓的CRUD操作。下面就是其具体实现代码:
{
private readonly ISessionManager sessionManager;
public NHibernateRepository(ISessionManager sessionManager)
{
this.sessionManager = sessionManager;
}
private ISession Session
{
get
{
return sessionManager.OpenSession();
}
}
public T GetById(int id)
{
return Session.Load<T>(id);
}
public IQueryable<T> GetAll()
{
return Session.Linq<T>();
}
public void InsertOnSubmit(T entity)
{
Session.Save(entity);
}
public void DeleteOnSubmit(T entity)
{
Session.Delete(entity);
}
public void SubmitChanges()
{
Session.Flush();
}
object IRepository.GetById(int id)
{
return GetById(id);
}
IQueryable IRepository.GetAll()
{
return GetAll();
}
void IRepository.InsertOnSubmit(object entity)
{
InsertOnSubmit((T)entity);
}
void IRepository.DeleteOnSubmit(object entity)
{
DeleteOnSubmit((T)entity);
}
}
该类的构造方法中接收ISessionManager实例做为其会话管理器。在castle中提供了"NHibernateIntegration"对NHibernate进行了集成,对Session和Transaction进行了封装。所以这里可以使用该ISessionManager对Model中的数据对象进行所谓的CRUD操作。因为这里还使用了NHibernate.Linq.dll,以此来替代Linq to Sql,所以其余的代码比较与Linq有些相似,这里就不多做说明了。
下面再看一下NHibernateEntityTypeResolver(Suteki.Common\Services\NHibernateEntityTypeResolver.cs),其功能就是将指定的Model中的指定实体类映影成NHibernate中的Entity,下面是其具体实现:
{
public Type GetTypeOf(IEntity entity)
{
return NHibernateProxyHelper.GuessClass(entity);
}
public Type GetRealTypeOf(Type type)
{
var nhibernateProxyInterface = type.GetInterface("INHibernateProxy");
if(nhibernateProxyInterface == null)
{
return type;
}
return type.BaseType;
}
}
下面就有这个示例来看一下其具体的测试代码。首先下载并解压该示例的ZIP文件,并修改其中的config文件"Keith.WindsorHNibernate.Tests.dll.Windsor.config",找出里面的数据连接串,替换成为我们本地的数据库链接。
public class RepositoryTests : WindsorNHibernateContainerTest
{
private IRepository<Customer> customerRepository;
[SetUp]
public void SetUp()
{
customerRepository = GetComponet<IRepository<Customer>>();
}
[Test]
public void Customer_RepositoryShouldNotBeNull()
{
var customers = customerRepository.GetAll();
foreach (var customer in customers)
{
Console.WriteLine("Customer: {0}", customer.ContactName);
foreach (var order in customer.Orders)
{
Console.WriteLine("\tOrder: {0}", order.OrderID);
}
}
Assert.That(customers, Is.Not.Null);
}
注意,其中customerRepository为IRepository<Customer>类型,其最终绑定的类型就是上面所定义的NHibernateRepository(通过IOC绑定实现)。
一种是Linq To Sql,一种是 NHibernate。