NHibernate,Get<TDto>(TId id) - 事务是否应该开始?

NHibernate, Get<TDto>(TId id) - should transaction begin or not?

我是 NHibernate 的新手...我应该 .BeginTransaction() 才能获得物品吗?没有它代码会抛出,但是它看起来很难看,因为没有显式调用 tx.Commit()/.CommitAsync() 。我假设 IDisposable 结束会怎样?

 public override async Task<TDto> Get(int id)
    {
        using (var sessionBuilder = NHibernateConfiguration.Instance.BuildSessionFactory())
        using (var session = sessionBuilder.OpenSession())
        using (var tx = session.BeginTransaction())
        {
            return await session.GetAsync<TDto>(id);
        }
    }

建议将每个调用(单个或多个调用)包装在事务中。这有助于在 multi-threaded/multi-process 环境中其他 thread/process 更改您正在阅读的数据时生成可靠的结果。 调用还包括读取调用。

推荐它的其他原因是因为现代 RDBMS 总是将每个调用包装在事务中(如果尚未完成)。它的成本。如果程序员已经知道工作单元,那就更好了,这样可以节省成本,也可以更好地对调用进行分组。

但是,根据情况,可能不需要任何(创建、读取、更新、删除)调用。这是个案决定。如果您由于 "code looks ugly" 原因避免这样做,请考虑实施 UoW。

顺便说一句,我希望你不是每次都打BuildSessionFactory。这是昂贵的,更重要的是,不需要。而是在您的应用程序启动时调用它。

回复评论:

我的意思和"Oskar Berggren"评论中提到的一样;它只是不够明确。由于问题更多的是关于交易,而 UoW 不仅仅是交易,我更喜欢只 "mention" UoW 而不是深入细节。

关于第一段,"multiple calls" 可以包含在单个工作单元中。请理解 UoW 比交易 。对于像 NHibernate 这样的 ORM,使用 UoW 可以更好地利用事务。另请注意,使用完整的 ORM,您无需为实施 UoW 做太多事情。 ISession本身就是UoW。您只需要正确地对其进行范围-使用-管理。

以下回答可能对您有所帮助: