簡體   English   中英

使用 DI 和 UoW 模式時是否需要使用 EF 語句

[英]Do i need using statements for EF when utilising DI and UoW patterns

在許多基本示例中,我看到 using 塊環繞着DbContext用法,如下所示:

using (var context = new MyDbContext()) 
{     
    // Perform data access using the context 
}

這是有道理的,因為正在創建一個“新”實例,因此您希望在完成后處理它。

使用 DI

但是,在我正在處理的許多項目中,我看到DbContext被注入到存儲庫和服務層中,如下所示:

public class FileRequestService : IFileRequestService
{
    private readonly MyDbContext _myDbContext;

    public FileRequestService(MyDbContext myDbContext)
    {
        _myDbContext = myDbContext;
    }

    public FileRequest SaveFileRequest(FileRequest fileRequest)
    {
        fileRequest.Status = FileRequestStatus.New;
        //...
        //...
        var fr = _myDbContext.FileRequests.Add(fileRequest);
        _myDbContext.SaveChanges();
        return fr;
    }
}

並在 DI 容器中配置如下:

container.Options.DefaultScopedLifestyle = new WebRequestLifestyle();

container.Register<MyDbContext>(Lifestyle.Singleton);

問題 1

這里沒有使用 using 語句是否可以,因為一旦 Web 請求終止,它可能會被處理掉?

使用 DI/UoW

工作單元模式的類似場景,我看到了這個:

public class RecordController : Controller
{
  private readonly IUnitOfWork _unitOfWork;

  public RecordController(IUnitOfWork unitOfWork)
  {
      _unitOfWork = unitOfWork;
  }

  [HttpPost, ActionName("Index")]
  public PartialViewResult Search(SearchQueryViewModel searchQueryViewModel)
  {    
      var deptId =
      _unitOfWork.DepartmentRepository.Get(x => x.DepartmentCode == searchQueryViewModel.code)
      .Select(s => s.DepartmentId)
      .FirstOrDefault();
       //...                
   }
}

在容器中配置如下:

container.Register<IUnitOfWork, UnitOfWork>(Lifestyle.Scoped);
container.Register<IGenericRepository<Department>, GenericRepository<Department>>(Lifestyle.Scoped);

並且DbContext被注入到 UoW 類的構造函數中。

問題2

同樣,這里沒有使用 using 語句是否可以,或者我應該在 UoW 類上實現IDisposable接口並執行以下操作:

using (_unitOfWork)
{    
  var deptId =
  _unitOfWork.DepartmentRepository.Get(x => x.DepartmentCode == searchQueryViewModel.code)
  .Select(s => s.DepartmentId)
  .FirstOrDefault();
  //...
}

簡單地說,誰創建了一個實例,誰就應該負責調用它的 dispose 方法。

關於問題 1:我個人會避免對 DbContext 使用單例。 谷歌上的快速搜索顯示了許多文章/Stackoverflow 問題,但這是第一個: 單例中的實體框架上下文在您當前的情況下 - 它不會被處理,永遠不會。 它在單例范圍中注冊,這意味着您將擁有一個與容器一樣長的實例。 (簡單的注入器范圍幫助頁面供參考 - http://simpleinjector.readthedocs.io/en/latest/lifetimes.html

關於問題 2:大多數容器一旦離開其作用域,就會調用所有 IDisposable 實例的 dispose 方法。 如果您早些時候調用 dispose 自己,您可能最終會在其他地方處理將作為依賴項提供的實例。 這樣做將導致其他代碼嘗試使用相同的已處理實例...

編輯:如果范圍不受 DI 框架控制,您當然必須自己調用 dispose 。 但這不是我們正在討論的情況

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM