寻找一种更简单的方法,Nhibernate和存储库?

时间:2012-01-31 20:19:15

标签: c# nhibernate

这似乎是一堆额外的数据访问工作。我目前使用一个非常基本的CRUD的通用存储库,我也有一些特定的存储库,我可能需要急切加载一些实体来绕过可爱的N + 1反模式。显然没有N + 1问题使数据库感到满意。所以这是我提出的一个例子。我想要一些反馈,也许是一个更好的方式来处理事情。

从下面的代码中可以看出,我的自定义存储库派生自Repository,我也有自定义存储库的接口。这一切对我来说都是错误的。

public class EmailQueueRepository:Repository,IEmailQueueRepository
{
    private readonly ISessionWrapper<ISession> _sessionWrapper;

    public EmailQueueRepository(ISessionWrapper<ISession> sessionWrapper) : base(sessionWrapper)
    {
        _sessionWrapper = sessionWrapper;
    }

    public void AddEmailQueueItem(IEmailQueueItem queueItem)
    {
        _sessionWrapper.Session.CreateCriteria(typeof (EmailQueue)).SetFetchMode("User", FetchMode.Eager).SetFetchMode("EmailDeliveryStatus",FetchMode.Eager);
        var emailQueueEntity = new EmailQueue
                                   {
                                       User = _sessionWrapper.Session.QueryOver<User>().Where(u=>u.UserId == queueItem.UserId).SingleOrDefault(),
                                       ToAddress = queueItem.ToAddress,
                                       Subject = queueItem.Subject,
                                       MessageBody = queueItem.MessageBody,
                                       EmailDeliveryStatus = _sessionWrapper.Session.QueryOver<EmailDeliveryStatus>().Where(x=>x.DeliveryStatus=="Pending").SingleOrDefault(),
                                       Active = 1,
                                       DateCreated = DateTime.Now,
                                       LastUpdated = DateTime.Now

                                   };
        Insert(emailQueueEntity);

    }
}

1 个答案:

答案 0 :(得分:2)

你有什么不对劲?这基本上就是我做的事情,除了:

  • 我没有包装ISession,我让我的代码直接使用ISession进行保存,更新,获取和加载操作以及控制事务。我的存储库包含预定义的查询,但应用程序可以直接使用ISession。
  • 我公开公开ISession作为只读属性。这样就可以从现有存储库中新建第二个存储库。
  • 我没有通用存储库。我将相关查询组合在一起并将它们放在适当的存储库中。例如,检索Customer和CustomerStatus的查询都进入CustomerRepository,而不是每个类都有一个存储库。

这对我来说非常有效,其他开发人员也很容易理解。在我看来,使用存储库模式避免的最大缺陷是拥有一个通用存储库并且每个类都有一个存储库。