NHibernate - 只选择的最佳实践

时间:2012-05-10 12:22:52

标签: nhibernate transactions

A对我的MVC应用程序执行了一个id并返回一个人姓名的操作。

最佳做法是什么?我正在关注NHProf的提示,但代码听起来有些奇怪或适合我。

using (var session = Helper.SessionFactory.OpenStatelessSession())
{
    using (var tran = session.BeginTransaction(IsolationLevel.ReadCommitted))
    {
        return session.Query<Person>().Where(x => x.Id == id).Select(x => x.Name).SingleOrDefault();
        tran.Rollback();
    }
}

3 个答案:

答案 0 :(得分:4)

NHProf警报页面很好地解释了我认为 -

http://nhprof.com/Learn/Alerts/DoNotUseImplicitTransactions

基本上它说如果你不自己管理事务,数据库将创建一个“隐式事务”并自动提交每个语句,包括查询。误解是事务仅对插入/更新操作有用。

在上面的例子中,这不是什么大问题,因为你的事务只执行一个语句。如果你的方法运行了几个语句,那么将它们包装在一个事务中是个好习惯。

答案 1 :(得分:0)

不要在一个HTTP请求上创建多个会话,理想情况下,您需要做的是在请求范围内打开会话和相应的事务,并在所有操作中使用此会话。

这是一篇博客文章,解释了如何实现它:http://hackingon.net/post/NHibernate-Session-Per-Request-with-ASPNET-MVC.aspx

我建议使用IOC容器并创建一个为您创建会话的类,并将此类的范围扩展到请求范围。

网上有很多资源可以解决这个问题.Google it ..

答案 2 :(得分:-1)

以下是我如何处理此选择:

    using (var session = Helper.SessionFactory.OpenStatelessSession())
    using (var tran = session.BeginTransaction(IsolationLevel.ReadCommitted))
    {
        try
        {
            string personName = session.Query<Person>()
            .Where(x => x.Id == id)
            .Single(x => x.Name);

            tran.Commit();
            return personName;
        }
        catch(Exception ex)
        {
            // handle exception
            tran.Rollback();
        }
    }

这个SO答案为处理事务提交提供了很好的建议:

NHibernate - Is ITransaction.Commit really necessary?

关于你的LINQ,这是一篇关于如何使用扩展方法样式语法来处理查询的有趣文章:

http://compiledexperience.com/blog/posts/how-not-to-use-linq