Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/.net/22.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 服务层中的会话和事务管理_C#_.net_Nhibernate_Architecture_Orm - Fatal编程技术网

C# 服务层中的会话和事务管理

C# 服务层中的会话和事务管理,c#,.net,nhibernate,architecture,orm,C#,.net,Nhibernate,Architecture,Orm,我有一个应用程序,它将有一些表示层(web、mobile、wpf、wcf、后台工作的windows服务等),我们正在使用NHibernate来持久化域对象。我们将拥有用于持久化数据的存储库(类库),一个根据业务规则使用这些存储库来持久化数据的服务层。我的问题是,我们不知道如何在此服务层中实现事务管理。我们可能会在同一个服务层方法中使用(多个)存储库,并且我们需要控制服务层上的事务。我想实现这样的功能(按属性): 当我们遇到错误时,这个事务属性是否控制提交/回滚的事务。可能吗?还是有其他解决办法

我有一个应用程序,它将有一些表示层(web、mobile、wpf、wcf、后台工作的windows服务等),我们正在使用NHibernate来持久化域对象。我们将拥有用于持久化数据的存储库(类库),一个根据业务规则使用这些存储库来持久化数据的服务层。我的问题是,我们不知道如何在此服务层中实现事务管理。我们可能会在同一个服务层方法中使用(多个)存储库,并且我们需要控制服务层上的事务。我想实现这样的功能(按属性):

当我们遇到错误时,这个事务属性是否控制提交/回滚的事务。可能吗?还是有其他解决办法


谢谢你

你问的问题没有一个直截了当的答案

您希望的行为听起来像是需要实现一个工作单元模式

NHibernate自己的会话实际上是一个工作单元的实现。我个人建议实现您自己的工作单元,这样您就可以更好地控制您的特定应用程序所考虑的工作单元

在服务层类中使用属性对我个人来说真的没有多大意义。我见过有人在处理事务的MVC应用程序中创建自定义控制器属性,但我个人从未同意这种实现

您提到在服务层中使用多个存储库。这是一种非常常见的做法,但也意味着这些存储库中的每一个都需要在同一个工作单元中运行。若您的应用程序正在使用依赖项注入,那个么一个选项是让每个存储库在其构造函数中接受ISession。您选择的依赖项注入框架可以这样设置:将相同的ISession注入所有存储库。您的设置可以配置为在每次创建新ISession时开始新事务

您还提到了不同的表示层,如web、mobile、wpf等。您在这些不同类型的应用程序中处理会话和事务的方式可能会有很大的不同。这就是为什么我总是向人们指出工作单元的方向,因为每一种不同的应用程序类型对于它所认为的工作单元都有完全不同的定义。对于web应用程序,您通常会为每个web请求使用一个新的工作单元。对于wpf应用程序,工作单元可以是每个屏幕,或者直到用户点击保存按钮,等等。此外,通过实现工作单元,您可以更轻松地在这些不同的应用程序类型中重用相同的工作单元实现

同样,这不是一个简单的问题,但一般来说,我通常使用定制的工作单元和依赖注入框架使这个问题更容易处理

以下是一些您可能希望调查的有用链接:


你所问的问题没有一个直截了当的答案

您希望的行为听起来像是需要实现一个工作单元模式

NHibernate自己的会话实际上是一个工作单元的实现。我个人建议实现您自己的工作单元,这样您就可以更好地控制您的特定应用程序所考虑的工作单元

在服务层类中使用属性对我个人来说真的没有多大意义。我见过有人在处理事务的MVC应用程序中创建自定义控制器属性,但我个人从未同意这种实现

您提到在服务层中使用多个存储库。这是一种非常常见的做法,但也意味着这些存储库中的每一个都需要在同一个工作单元中运行。若您的应用程序正在使用依赖项注入,那个么一个选项是让每个存储库在其构造函数中接受ISession。您选择的依赖项注入框架可以这样设置:将相同的ISession注入所有存储库。您的设置可以配置为在每次创建新ISession时开始新事务

您还提到了不同的表示层,如web、mobile、wpf等。您在这些不同类型的应用程序中处理会话和事务的方式可能会有很大的不同。这就是为什么我总是向人们指出工作单元的方向,因为每一种不同的应用程序类型对于它所认为的工作单元都有完全不同的定义。对于web应用程序,您通常会为每个web请求使用一个新的工作单元。对于wpf应用程序,工作单元可以是每个屏幕,或者直到用户点击保存按钮,等等。此外,通过实现工作单元,您可以更轻松地在这些不同的应用程序类型中重用相同的工作单元实现

同样,这不是一个简单的问题,但一般来说,我通常使用定制的工作单元和依赖注入框架使这个问题更容易处理

以下是一些您可能希望调查的有用链接:

public class DomainObjectService
{
   [Transactional]
   public bool CreateDomainObject(DomainObject domainObject, /* other parameters */)
   { 
       foreach(var item in /* collection */)
       {
           _itemRepository.Save(item);
       }

       if (/* some condition */) {
          /* change the domainObject here */
       }

       _domainObjectRepository.Save(domainObject);
   } 
}