Answer the question
In order to leave comments, you need to log in
Are the UnitOfWork and Repository patterns for Nhibernate implemented correctly?
I studied the use of NHibernate and patterns and eventually came to this code, this is a test draft, I want to use this in one solution in which there will be two projects, one in the form of services, the other in the form of ASP.NET MVC. I am asking a question in order to understand whether I understood these patterns correctly, whether I used them correctly and whether they are superfluous at all and it was possible not to complicate everything?
Source code (as a single file, requires the System.Data.SQLite, NHibernate, NHibernate.Mapping.Attributes packages to run):
using System;
using NHibernate;
using NHibernate.Cfg;
using NHibernate.Mapping.Attributes;
using NHibernate.Tool.hbm2ddl;
namespace NhSQLiteTest
{
[Class]
[Serializable]
public class Product
{
[Id(0, Name = "Id", Column = "Id", TypeType = typeof (int))]
[Generator(0, Class = "identity")]
public virtual int Id { get; set; }
[Property]
public virtual string Name { get; set; }
}
internal class Program
{
private static void Main()
{
using (var uow = new UnitOfWorkFactory().Create())
{
var productRepo = new Repository<Product>(uow);
productRepo.SaveOrUpdate(new Product {Name = "TestRepo"});
}
Console.WriteLine("Success!");
Console.ReadLine();
}
}
public interface IUnitOfWorkFactory
{
IUnitOfWork Create();
}
public class UnitOfWorkFactory : IUnitOfWorkFactory
{
private ISessionFactory _sessionFactory;
public ISessionFactory SessionFactory
{
get
{
if (_sessionFactory == null)
{
BuildSessionFactory();
}
return _sessionFactory;
}
}
public IUnitOfWork Create()
{
return new UnitOfWork(SessionFactory.OpenSession());
}
private void BuildSessionFactory()
{
var config = new Configuration();
config.Configure();
config.AddAssembly(typeof (Product).Assembly);
HbmSerializer.Default.Validate = true;
var stream = HbmSerializer.Default.Serialize(typeof (Product).Assembly);
stream.Position = 0;
config.AddInputStream(stream);
new SchemaUpdate(config).Execute(false, true);
_sessionFactory = config.BuildSessionFactory();
_sessionFactory.OpenSession();
}
}
public interface IUnitOfWork : IDisposable
{
}
internal class UnitOfWork : IUnitOfWork
{
public UnitOfWork(ISession session)
{
if (session == null) throw new ArgumentNullException(nameof(session));
Session = session;
}
public ISession Session { get; private set; }
public void Dispose()
{
Session.Dispose();
Session = null;
}
}
public interface IRepository<T> where T : class
{
void SaveOrUpdate(T obj);
}
public class Repository<T> : IRepository<T> where T : class
{
private readonly UnitOfWork _uow;
public Repository(IUnitOfWork uow)
{
if (uow == null) throw new ArgumentNullException(nameof(uow));
_uow = uow as UnitOfWork;
if (_uow == null)
{
throw new ArgumentException("Этот репозиторий принимает только единицу работы NHibernate");
}
}
private ISession Session
{
get { return _uow.Session; }
}
public void SaveOrUpdate(T obj)
{
Session.SaveOrUpdate(obj);
}
}
}
Answer the question
In order to leave comments, you need to log in
Didn't find what you were looking for?
Ask your questionAsk a Question
731 491 924 answers to any question