6

我正在使用ASP.Net MVC 4,EF和Unity的DI。也使用UnitOfWork模式。试图找出实现这一点的最佳方式。我有如下的代码。 我遇到的问题是Dispose()在业务和存储库层现在不会被调用,只有在两个析构函数被调用,所以对象似乎永远不会被处置。 请回答下列ASP.NET MVC,Unity和IDisposable

  1. 我真的需要在业务了IDisposable执行和库层(如果统一已经照顾吧))称为

  2. 我应该怎么做才能得到的Dispose( (我应该把它添加到控制器也和处置所有其他对象,或者使用一些特定的生命期管理器)

  3. 我是否应该使用每个的单一实例或处置其在每个请求,因为它是在网络环境中。

的Global.asax.cs:

private static IUnityContainer _unityContainer; 

protected void Application_Start() 
{ 
    _unityContainer = UnityBootstrapper.SetupUnity(); 
    _unityContainer.RegisterType<IController, ProductController>("Product"); 
    DependencyResolver.SetResolver(new Microsoft.Practices.Unity.Mvc.UnityDependencyResolver(_unityContainer)); 
} 

UnityBootstrapper.cs:

public class UnityBootstrapper 
{ 
    public static IUnityContainer SetupUnity() 
    { 
     UnityContainer container = new UnityContainer(); 
     container.RegisterType<IProductDbContext, ProductDbContext>() 
       .RegisterType<IUnitOfWork, UnitofWork>(new InjectionConstructor(new ResolvedParameter(typeof(IProductDbContext)))) 
       .RegisterType<IProductRepository, ProductRepository>() 
       .RegisterType<IProductBusiness, ProductBusiness>(); 
    } 
} 

ProductController.cs:

public class ProductController : ControllerBase 
{ 
    private readonly IProductBusiness _productBusiness;   

    public ProductController(IProductBusiness productBusiness) 
    { 
     _productBusiness = productBusiness; 
    } 

    //No Dispose for this 
} 

ProductBusiness.cs:

public class ProductBusiness : IProductBusiness, IDisposable 
{ 
    private readonly IUnitOfWork _unitOfWork; 
    private readonly IProductRepository _productRepository; 
    public ProductBusiness(IUnitOfWork unitOfWork) 
    { 
     _unitOfWork = unitOfWork; 
     _productRepository = _unitOfWork.ProductRepository; 
    } 

    public override void Dispose() 
    { 
     Dispose(true); 
     GC.SuppressFinalize(this); 
    } 

    protected override void Dispose(bool disposing) 
    { 
     if (!_isDisposed) 
     { 
      if (disposing) 
      { 
       if (_productRepository != null) _productRepository.Dispose(); 
       if (_unitOfWork != null) _unitOfWork.Dispose(); 
      } 

      _isDisposed = true; 
     } 
    } 

    ~ProductBusiness() 
    { 
     Dispose(false); 
    } 
} 

ProductRepository.cs:

public class ProductRepository : IProductRepository, IDisposable 
{ 
    private readonly IProductDbContext _context; 

    public ProductRepository(IProductDbContext context) 
    { 
     if (context == null) 
      throw new ArgumentNullException("context"); 

     _context = context; 
    } 

    public void Dispose() 
    { 
     Dispose(true); 
     GC.SuppressFinalize(this); 
    } 

    protected virtual void Dispose(bool disposing) 
    { 
     if (!_isDisposed) 
     { 
      if (disposing) 
      { 
       if (_context != null) _context.Dispose(); 
      } 

      _isDisposed = true; 
     } 
    } 

    ~ProductRepository() 
    { 
     Dispose(false); 
    } 
} 
+0

谢谢大家对于快速响应 –

+0

SA,欢迎来到StackOverflow。按照这个社区的惯例,你可以通过投票答案来说“谢谢”。然后将最有用的答案标记为已接受的答案。请查看常见问题解答部分,了解有关投票的最新信息:http://stackoverflow.com/help/why-vote – trailmax

回答

1

虽然统一will manage disposing of your registered类型,你还是打电话给你的IOC容器的配置,以便它为他们。

从Application_End开始,它应该没问题。

protected void Application_End() 
    { 
     _unityContainer .Dispose(); 
    } 
1

我相信,如果你设置了正确的LifetimeManager则没有,你并不需要实现IDisposable的团结会处理你的对象的处置。这解释了不同类型的终身管理员http://msdn.microsoft.com/en-us/library/ff660872(v=pandp.20).aspx

就我个人而言,我并没有使用单例,只是让对象被创建,然后在每个请求中处理。

0

因为IDisposable的主要目的是清理非托管资源,所以您不需要在这些类上使用IDisposable。看看这些:

http://msdn.microsoft.com/en-us/library/system.idisposable(v=vs.110).aspx

Proper use of the IDisposable interface

使用您的容器单件模式,如果您使用的容器中,在服务定位的方式可以是有益的。但是,还有其他(可以说是更好的)方式来使用Unity或其他DI/IoC容器。那里有几个bootstrappers。例如:

https://www.nuget.org/packages/Unity.Mvc/

2

你并不真的需要处置的对象,除非你做的处置过程中一些具体的事情。 DI容器为您处理物体寿命。

有时候UoW的实施涉及保存处置的变化。尽量避免这一点。但如果这是不可避免的,你可以实现工厂:

public interface IUnitOfWorkFactory 
{ 
    IUnitOfWork Create(); 
} 

public class UnitOfWorkFactory : IUnitOfWorkFactory 
{ 
    public IUnitOfWork Create() 
    { 
     return new UnitOfWork(); 
    } 
} 

public class UnitOfWork : IUnitOfWork, IDisposable 
{ 
    // other implementation 


    public void Dispose() 
    { 
     context.SaveChanges(); 
    } 
} 

,然后消费者就做这样的事情:大约一次性对象

public MyController(IUnitOfWorkFactory workFactory) 
{ 
    this.workFactory = workFactory; 
} 

public ActionResult DoSomething() 
{ 
    using(var uow = workFactory.Create()) 
    { 
     //do work 
    } 
} 

This DI book chapter会谈。