使用ASP.NET MVC的NHibernate会话+事务3

Kez*_*zer 3 nhibernate asp.net-mvc-3

我现在正在编写一个新的应用程序,虽然公司标准是使用NHibernate(因为这是所有项目的标准),而我现在正在使用ASP.NET MVC 3,因为它已经成熟.我已经在控制器中实现了我的事务(据说这是你应该这样做的方式),所以它在我的根控制器中看起来像这样:

[TransactionPerRequest]
public class FbsController : Controller
{

}
Run Code Online (Sandbox Code Playgroud)

然后我的所有控制器都继承了这个FbsController.这样做的原因是因为90%的所有操作都将转移到数据库,因此创建事务并将其处理剩余10%的操作(很少会执行)的开销不值得装饰每一个动作[TransactionPerRequest].

总是困扰我的事情是关于NHibernate会话.在存储库类中,这与我所拥有的一致,尽管这在其他项目中是不同的:

    public void Add(User user)
    {
        using (ISession session = NHibernateHelper.OpenSession())
        {
            session.Save(user);
        }
    }

    public void Remove(User user)
    {
        using (ISession session = NHibernateHelper.OpenSession())
        {
            session.Delete(user);
        }
    }

    public User GetById(int userId)
    {
        using (ISession session = NHibernateHelper.OpenSession())
        {
            return session.QueryOver<User>()
                .Where(c => c.UserID == userId)
                .SingleOrDefault();
        }
    }
Run Code Online (Sandbox Code Playgroud)

那么对于我的存储库中的大多数函数,我必须打开一个会话.有没有办法避免这种行为,所以我不必在每个存储库方法中打开一个会话?这似乎有点反直觉,因为我通常必须为每一个人做这件事.我想知道其他人的解决方案是什么解决了交易和会话问题,我看到各种各样的代码乱七八糟.

实际上我希望我的存储库方法如下所示:

    public void Add(User user)
    {
        session.Save(user);
    }

    public void Remove(User user)
    {
        session.Delete(user);
    }

    public User GetById(int userId)
    {
        return session.QueryOver<User>()
            .Where(c => c.UserID == userId)
            .SingleOrDefault();
    }
Run Code Online (Sandbox Code Playgroud)

随着一切被隐含地处理.