首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >共享IDbConnection以保持事务本地

共享IDbConnection以保持事务本地
EN

Stack Overflow用户
提问于 2016-01-21 10:58:27
回答 1查看 387关注 0票数 0

Data处理从泛型接口继承的数据实体,DAL层被实现为泛型类,它将泛型接口作为依赖项注入。设计如下:

数据实体-车辆

代码语言:javascript
复制
public class Vehicle
{
    public int Id {get; set;}

    public string Brand {get; set;}
}

通用接口- IData

代码语言:javascript
复制
public interface IData<T>
{
   IEnumerable<T> Select(IDictionary<string,object> parameters);

   int Update(IDictionary<string,object> parameters);

   int Delete(IDictionary<string,object> parameters);

   int insert(IDictionary<string,object> parameters);
}

车辆仓库

代码语言:javascript
复制
public class VehicleData : IData<Vehicle>
{
   IEnumerable<Vehicle> Select(IDictionary<string,object> parameters)
   {
      using(IDbConnection conn = (Fetch Connection))
      {
         // Select Operation
      } 
   }

   int Update(IDictionary<string,object> parameters)
    {
      using(IDbConnection conn = (Fetch Connection))
      {
         // Update Operation
      } 
   }

   int Delete(IDictionary<string,object> parameters)
    {
      using(IDbConnection conn = (Fetch Connection))
      {
         // Delete Operation
      } 
   }

   int insert(IDictionary<string,object> parameters)
    {
      using(IDbConnection conn = (Fetch Connection))
      {
         // Insert Operation
      } 
   }
}

DAL类实现:

代码语言:javascript
复制
public class DAL<T>
{
  public static IEnumerable<T> Select(IData<T> dataRepository, IDictionary<string,object> parameters)
   {
       return dataRepository.Select(parameters);
   }

// Implementation for Insert, Update and Delete
}

我使用调用类中的VehicleData执行DAL,如下所示。

代码语言:javascript
复制
IData<Vehicle> vehicleData = new VehicleData();

IDictionary<string,object> parameters = // Filled from client

DAL<Vehicle>.Select(vehicleData,parameters);

我面临的问题是,在每个CRUD方法中,IDbConnection都是在Using块中创建的,因此最终被处理,就像在本地上下文中一样,但是有这样的场景,在不同实体上的多个DAL操作需要成为单个事务上下文的一部分,如果我继续以类似的方式进行,那么打开的事务上下文将被提升到分布式级别,因为多个连接资源正在打开,即使我可以在相同的连接上下文上逐个执行它们。问题仍然存在:

  1. 如何在多个调用(如DAL<Vehicle>.Update, DAL<Driver>.Update and DAL<Truck>.Update )之间共享连接,从而避免从本地到分布式的事务升级
  2. 不确定,在事务上下文中打开和处理连接是否意味着在不升级到分布式事务的情况下可以打开另一个连接,在我看来,这种情况不会发生。
EN

回答 1

Stack Overflow用户

发布于 2016-01-21 12:10:37

您是否使用IoC容器进行依赖注入?在IoC中有一些生活方式(每线程、每个web请求等等)例如,在温莎城堡中,您可以使用范围生活方式。你的代码会是这样的:

创建连接(linq2db):

代码语言:javascript
复制
container.Register(
    Component.For<DataConnection>().UsingFactoryMethod(x => 
        CreateDataConnection()).LifestyleScoped(),
    Component.For<IData<Vehicle>>()
        .ImplementedBy<VehicleData>().LifestyleScoped()
);

private static DataConnection CreateDataConnection()
{
    return new DataConnection(new SqlServerDataProvider("", SqlServerVersion.v2008), 
        @"Data Source=(local);Initial Catalog=DB1;Persist Security Info=True;User ID=user;Password=pwd");
}

执行一些db操作:

代码语言:javascript
复制
using (container.BeginScope())
{
    var db = container.Resolve<DataConnection>();
    db.BeginTransaction();
    container.Resolve<IData<Vehicle>>().Update(...);
    container.Resolve<IData<Vehicle>>().Update(...);
    container.Resolve<IData<Vehicle>>().Update(...);
    db.CommitTransaction();
}
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/34921876

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档