使用StructureMap,Repository Pattern和UoW在MVC应用程序中通过LINQtoSQL更新问题

时间:2010-09-13 14:35:19

标签: linq-to-sql model-view-controller structuremap repository-pattern

我有一个使用LINQ to SQL进行数据访问的ASP MVC应用程序。 我正在尝试使用存储库和工作单元模式,服务层使用存储库和工作单元。 尝试在特定存储库上执行更新时遇到问题。

我的应用程序架构如下:

我的服务类:

public class MyService
{
   private IRepositoryA _RepositoryA;
   private IRepositoryB _RepositoryB;
   private IUnitOfWork _unitOfWork;

   public MyService(IRepositoryA ARepositoryA, IRepositoryB ARepositoryB, IUnitOfWork AUnitOfWork)
   {
      _unitOfWork = AUnitOfWork;
      _RepositoryA = ARepositoryA;
      _RepositoryB = ARepositoryB;
   }

   public PerformActionOnObject(Guid AID)
   {
      MyObject obj = _RepositoryA.GetRecords()
                                 .WithID(AID);
      obj.SomeProperty = "Changed to new value";
      _RepositoryA.UpdateRecord(obj);  
      _unitOfWork.Save();
   }
}

存储库界面:

public interface IRepositoryA
{ 
   IQueryable<MyObject> GetRecords();
   UpdateRecord(MyObject obj);
}

存储库LINQtoSQL实现:

public class LINQtoSQLRepositoryA : IRepositoryA
{
    private MyDataContext _DBContext;

    public LINQtoSQLRepositoryA(IUnitOfWork AUnitOfWork)        
    {
        _DBConext = AUnitOfWork as MyDataContext;           
    }

    public IQueryable<MyObject> GetRecords()
    {             
        return from records in _DBContext.MyTable                   
               select new MyObject
               {
                  ID = records.ID,
                  SomeProperty = records.SomeProperty
               }
    }


    public bool UpdateRecord(MyObject AObj)
    {
        MyTableRecord record = (from u in _DB.MyTable
                    where u.ID == AObj.ID
                    select u).SingleOrDefault();

        if (record == null)
        {
            return false;
        }           

        record.SomeProperty = AObj.SomePropery;
        return true;
    }
 }

工作单元界面:

public interface IUnitOfWork
{  
    void Save();
}

在数据上下文扩展中实现的工作单元。

public partial class MyDataContext : DataContext, IUnitOfWork
{
   public void Save()
   {
      SubmitChanges();
   }
}

StructureMap注册表:

 public class DataServiceRegistry : Registry
    {
        public DataServiceRegistry()
        {            
            // Unit of work
            For<IUnitOfWork>()               
                .HttpContextScoped()                
                .TheDefault.Is.ConstructedBy(() => new MyDataContext());

            // RepositoryA
            For<IRepositoryA>()
                .Singleton()
                .Use<LINQtoSQLRepositoryA>();    

            // RepositoryB
            For<IRepositoryB>()
                .Singleton()
                .Use<LINQtoSQLRepositoryB>();    
         }
     }

我的问题是,当我在服务对象上调用PerformActionOnObject时,更新永远不会触发任何SQL。我认为这是因为UnitofWork对象中的datacontext与RepositoryA中的数据更改不同。因此,当服务在其IUnitOfWork上调用Save()时,底层datacontext没有任何更新的数据,因此不会触发更新SQL。

StrutureMap注册表设置中是否存在错误?或者设计是否存在更基本的问题?

非常感谢。

1 个答案:

答案 0 :(得分:0)

如果它具有作用域依赖性,那么将某些内容注册为singleton通常不是一个好主意。就像你说的那样,他们很可能会抓住IUnitOfWork的旧实例。

您的存储库是单身的任何特殊原因?我建议将它们作为HttpContext作用域,这样它们就会同步。