簡體   English   中英

EF5中的UOW和存儲庫模式

[英]UOW and Repository Pattern in EF5

這是關於我從這里找到的一些實體框架材料的一些混淆: https//www.asp.net/

在本頁中,它解釋了如何使用存儲庫包裝dbcontext並使用工作類單元包裝存儲庫: http//www.asp.net/mvc/overview/older-versions/getting-started-with-ef使用-5--MVC-4 /實施最庫和-單元的功圖案-在-AN-ASP-凈-MVC的應用程序

但是,在此頁面上,它指出dbcontext已經是UOW模式和存儲庫模式的組合: https ://msdn.microsoft.com/en-us/library/system.data.entity.dbcontext( v= vs.103)的.aspx

因此,如果dbcontext已經解決了這些模式解決的問題,為什么要用EF5重新實現這些模式呢?

此外,在本教程中,UnitOfWork類似乎沒有顯示UOW應該給出的任何好處。 例如,它聲明:“這樣,當一個工作單元完成后,您可以在該上下文實例上調用SaveChanges方法,並確保所有相關更改都將得到協調。”

但它似乎只是無緣無故地包裝dbcontext。 我想我錯過了什么。 我沒有看到在這個實現中有任何協調......如果出現問題,事情如何“回滾”?

不要使用其他UoW /存儲庫抽象層

正如OP正確指出的那樣,實體框架(類似於NHibernate和其他ORM)已經為您提供了數據庫的抽象,同時具有可供您使用的事務“工作單元”和“存儲庫”。

額外的UoW /存儲庫抽象層是反模式 ,應該不惜一切代價避免。 它有很多問題,其中最重要的是:

  • 它們會阻止您使用底層ORM的全部功能(延遲加載,急切加載,復雜查詢......)
  • 如果他們想要提供除簡單CRUD之外的任何額外好處,它們將會泄漏(即反映基礎ORM中存在的功能)。

但是,但是,但......

我需要通過模擬我的存儲庫來進行單元測試

不,你沒有。 只需使用具有針對您的測試的特定內容的數據庫。 如果您希望更快,請使用內存數據庫(例如SQLite, Effort ,...)。

EF不強制執行未在數據關系中表達的業務邏輯......要強制執行此類邏輯,您必須圍繞EF上下文構建一個OUW / Repository /兩者。

不,你不應該。 基礎架構抽象層(例如工作單元或存儲庫)中實現業務邏輯是完全錯誤的。

  • 有價值的業務邏輯屬於域實體,域服務,域命令或長期運行的業務流程,sagas。
  • 簡單的驗證(即非nullxy之間的值)不會:那些應該在系統接口邊界解決。

還要注意,沒有任何有價值的業務邏輯的簡單CRUD樣式操作不需要經歷所有“層箍”,即避免這種模式:

  1. 數據庫→沒有行為的實體→DTO→查看模型→查看
  2. 編輯字段
  3. 查看→查看模型→DTO→無行為的實體→數據庫

只需從控制器中的ORM直接加載視圖所需的“視圖模型”形狀,然后直接從控制器中保存。

關於抽象

不必要的抽象和諸如此類的層層箍是邪惡的。 它們會混淆您的代碼,綁定您的手,泄漏,增加代碼大小,從而增加代碼中的錯誤數量,而不會提供任何附加值。

當它們為您提供附加價值時使用抽象,例如當您需要它們來解決跨領域問題,捕獲/管理架構中的重復模式時,......

為抽象而創建抽象是浪費時間。

我已經在這里寫了很多文章,但我會總結一下你的利益。 是的,實體框架已經實現了UoW( DbContext )和存儲庫( DbSet )模式。 重新實施它們沒有任何好處。 實際上,由於它大大增加了項目的維護開銷,因此非常不利。

為什么Microsoft在入門教程中包含了這個? 老實說,我不確定,但這是一個困擾無數新MVC開發人員的錯誤,當我剛開始時,我自己也包括在內。

在某種抽象中有好處,這樣您的項目就不依賴於任何一種獲取數據的特定方式。 但是,這種抽象應該返回您的操作所需的特定數據,不多也不少。 由於缺乏一個更好的詞,我將其稱為“服務”,盡管微軟已經通過SOA在該詞上嫁接了不同的含義。 簡單地說,就像您只是為應用程序創建API一樣,就像創建Web API一樣,只是完全基於代碼(不需要實際的HTTP連接)。 然后進入您的項目可以引用的DAL層(類庫或類似)。

關於EF的事情是它暴露的OUW或Repository功能中沒有業務邏輯。 如果您調用SaveChanges,它將很樂意保存所有更改。 但是,有一個要求是,當添加說Widget時,為Widget添加Frobber是必要的,你運氣不好(除非涉及到FK依賴)。 對於未在數據關系中表達的任何業務邏輯,開箱即用的EF不會強制執行。

要強制執行此類邏輯,您必須圍繞EF上下文構建一個OUW / Repository /。 根據我的知識,這是你做這件事的唯一原因。

工作單元和存儲庫模式與實體框架工作無關。 它是設計模式之一。 因此它用於使您的代碼更具可讀性,可重用性和高效性,並且這些模式也用於實現singelton(一次性對象實例化)以及避免控制反轉。

暫無
暫無

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

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