.Net企業級應用架構設計之業務層設計

來源:互聯網
上載者:User

業務層剖析

任何複雜的任何軟體都可以通過層來組織,每一層表示系統中的一個邏輯部分,一般來說,商務邏輯層中的模組包含了系統所需要的所有功能上的演算法和計算過程,並於資料層和表現層互動。抽象的說,商務邏輯層是軟體中專門處理業務相關任務效能的部分。

商務邏輯層表示了系統的邏輯,此處的代碼將要進行必要的決斷並執行操作。前面談到過安全性,在商務邏輯層的安全性意味著使用基於角色的安全原則,僅允許認證使用者訪問特定的業務對象。從外界看,商務邏輯層可以看作是一個操作業務對象的機制,一般來說,業務對象不過是某個領域實體的實現,或者是某類輔助類型,用來執行一些計算。商務邏輯層處於分層系統的中間位置,商務邏輯層的輸入和輸出不一定是業務對象,很多時候,架構師更傾向於使用資料移轉對象在層之間交換資料。

資料移轉對象和業務對象之間的取捨一直是團隊中爭議的話題。建議使用資料移轉對象的理論認為,資料移轉對象能減少層之間的耦合,使系統更加整潔乾淨。不過在現實中,人們都會說複雜性已經很高,因此應該避免增加任何不必要的對象。一條實用的原則是,當已經有了數百個業務對象時,或許並不應該僅僅為了設計的乾淨而讓這個數字加倍,在這種情況下,資料移轉對象通常就是業務對象。業務對象同時包含了資料和行為,是一個可以參與到領域邏輯的完整對象。而資料移轉對象更像是一種值,即一系列資料的容器而沒有相關的行為。為了序列化,業務對象中的資料會複製到資料移轉對象中。除了get/set訪問器之外,資料移轉對象沒有邏輯行為。資料移轉對象並不僅僅是領域對象去掉了行為,它表示了特定領域對象的一個子集,用於專門的上下文中。一般來說領域對象是一個對象圖,而資料移轉對象僅僅是所需要部分資料的投影而已。

每個真實的世界組織都是基於一系列商務規則啟動並執行。或許很多人沒有認識到組織中存在的這些規則,但不能否認這些規則的存在。每個組織都有自己要實現的戰略,而商務規則是保證實現這些戰略的主要手段。戰略決定了組織的發展方向,而業務給出了實現戰略的具體做法。

業務對象的屬性來自於其映射的實體的屬性,業務對象的方法來自於其自身的職責以及應用到該實體上的部分商務規則。商務規則在很多程度上是對資料的驗證。換句話說,很多商務規則說到底就是驗證某個業務對象的當前內容。按照這樣的理解,若有專門的驗證層,並讓業務對象可選擇的支援,這個設計將會非常不錯。

商務邏輯層不應該看作是一個整體的組件,或者一些不相關模組的組合。多年的實際經驗告訴我們,商務邏輯層在其他層(經典三層)中適當的重複是可以接受的,也是很多程式的做法。不過這種做法有一定的限度,且不應該受到鼓勵。

業務層和其他層

假設我們有一個經典的分層系統,分為表現層、業務層和資料訪問層,那麼商務邏輯分布在各個層中的百分比應該是多少?最權威的答案是0 - 100 - 0 。這個數字顯然不現實,通常你應該嘗試把所有的事情放在商務邏輯層完成,除了CRDU操作以及使用者介面的調整。分散在表現層和資料訪問層中的邏輯有可能只是處於效能方面的考慮才進行的重複。這些重複由一些系統總體功能的灰色地帶導致,有時候我們都不知道該把他們放在何處,下面介紹幾個常見的灰色地帶。

1、資料格式化。若在用戶端進行可視化,那麼表現層必須瞭解很多上下文以及系統的邏輯。若將格式化放在商務邏輯層,那麼商務邏輯層就必須提供合適的方法,供用戶端調用並擷取可以直接顯示的字串。我們會有幾個選擇,第一是存放兩個資料,未經處理資料和格式化之後的資料。第二是存放未經處理資料,需要時格式化。第三是按照輸入時的格式直接存放。我們當然會選擇第二種。

2、CRUD操作。資料訪問層應該僅僅用來處理資料庫相關的操作,而商務邏輯判斷又必須調用資料。

3、預存程序。原因類同與CRUD訪問。在涉及到資料庫流量的問題時,基本可以通過添加硬體或更換更好的硬體來解決,此外,在商務邏輯層中可以進行適當的緩衝。

業務層的模式區分

在業務層的模式上有幾種選擇。首先是過程式模式,在物件導向開發興起之前,商務邏輯只不過是一系列過程的集合,每個集合都用來處理來自於表現層的一個請求。因此好的設計都在於更好的去組織這些過程,減少代碼和流程的冗餘。基於對象的模式抽象程度越高,與資料模型的差距也會越大,因此若想建立一個領域驅動的物件模型,一般應該從領域著眼,而不是從資料庫結構開始。領域驅動的設計一定會使資料庫模型和領域模型之間存在不小差異。這個模式通常叫做領域模型。

基於對象的模式在開始時代價較高,但隨著複雜性增長,其代價基本上也線性增加。換句話說,一旦你對領域模型有足夠的瞭解,無論系統的複雜性如何,你都可以使用領域模型模式。在複雜性度量上,複雜性分為兩方面,第一種是天生的,不可避免,無法協調需求本身,這類複雜性可以通過一些方法或多或少降低,不過不可能完全抹除,必須直接面對。第二種是來自於引入的複雜,這個來自於不同項目干係人意見的不協調,負面效果就是將團隊引向錯誤的方向,錯誤的方向則會讓抽象設計包含不必要或非功能性的功能,將軟體逼上絕路。

需求的數量可以用來粗略判斷系統的複雜性,認識到複雜性比解釋如何找到複雜性更加簡單。

事務指令碼模式

事務指令碼模式可能是商務邏輯層中最簡單的模式了,它是一個純粹的過程式模式。事務指令碼模式鼓勵你放棄所有的物件導向設計,將業務直接映射到需要的使用者操作上,該模式的關注點在於使用者通過表現層所能執行的操作,並為每個操作編寫一個專門的方法。事務指令碼模式易於理解和解釋,每個必須的使用者操作都在一個物理事務中開始。直至結束,不過資料訪問通常被封裝在另一些組件中,並不屬於指令碼。事務指令碼適合應用於那些商務邏輯非常簡單,且最好不大可能改變的簡單情境中。在這個簡易度和複雜性的概念上權衡非常艱難,更為重要的是,對簡單和複雜的認知還依賴與一個人的態度和能力。你懂的!

簡單是事務指令碼模式最值得一提的優勢,但是事務指令碼有造成代碼重複的潛質。所有實現了事務指令碼的類型都可以看做是業務組件。每個業務組件都可以有一個或多個事務。比較流行的設計方式是將各個事務指令碼分組,然後讓每一組成為一個業務組件,這樣每一組中的事務指令碼在邏輯上都是相關的。另一種做法是將每個事務指令碼用單獨的類封裝起來,這樣每個業務組件都僅包含一個方法,換句話說,這裡的業務組件就變成了一堆命令對象。若想將事務指令碼的業務組件設計成命令對象,可以釋放出一個介面,並將所有需要的參數以類型公有屬性的形式暴露出來。

表模組模式

與事務指令碼相比,表模組更有結構,表模組作為一個容器,將資料和行為組合在一起。商務邏輯被拆分為粗粒度的、表示整個資料表的組件。表模組的粒度不會下降到資料行的程度,即表模組類無法區分每一行資料。表模組模式應用中,使用基於記錄集的資料結構是最常見的方式。例如Dataset、Datatable等。

對那些不需要太多抽象,且資料模型和物件模型之間沒有太大差異的情境,表模組是個非常不錯的折衷方案。與事務指令碼相比,表模組基於一個概念性模型。而不是一大批方法的鬆散集合。若系統中的表現層和資料訪問層都是基於表狀資料結構,那麼表模組將是非常好的選擇,這時,業務層即可為表現層提供直接可用的資料,有時甚至可以直接通過資料繫結實現。

表模組並沒有比事務指令碼複雜很多,不過若完全需要手工構造,那麼花費的時間可能比簡單的事務指令碼多出很多。模式在提供了更多指導的同時,也意味著我們需要考慮更多規則,也就是編寫更多代碼。

內嵌的Dataset設計器提供Fill和GetData方法來基於整個資料表進行查詢。從概念角度講,表模組的另一個優勢在於,無論底層資料來源是什麼,對於同一些功能都會得到同樣的表模組類。表模組基於對象,但完全由資料庫驅動。表模組並不適合表述複雜的眾多實體。特別是物件模型和資料模型之間有顯著差距的時候。表模組的優勢是VS提供了強大的支援,實現起來簡單,不過考慮到這些產生的程式碼類似於一個黑箱,優勢也就成了劣勢。當然,表模組這個結構模型不一定需要和VS緊密耦合。

活動記錄模式

事務指令碼和表模組都是過程式模式。但是表模組基於對象,不是一個對於基於對象商務邏輯建模模式。最終走向物件導向設計關鍵的一步是你認識到系統中的目標對象,商務邏輯和領域邏輯才是系統的核心,它是由實體之間必須的互動組成的。

活動記錄是一種應用於相對簡單的領域模型,但仍基於對象模式。另一種更加容易理解的說法是,活動記錄基於資料表中的行,而不是表模組那樣基於資料表。也就是說,活動記錄對資料有行層級的粒度,而表模組關注的是整張表。活動記錄模式歸為資料來源設計模式,而不是商務邏輯模式。活動記錄模式就是指一個封裝了資料表或視圖的一行的對象,對象中可以同時包含資料和行為,活動記錄對象的結構應該儘可能地接近於相關聯的資料表結構。

在那些沒有服務層的應用程式中,活動記錄模式可以和事務指令碼結合使用。

活動記錄模式的成功依賴於兩個因素:簡單和架構。這兩個因素緊密相關。我們最常見和熟悉的是LINQ- to - SQL。相對於簡單的邏輯來說,活動記錄非常合適。活動記錄的另一個問題是對象和資料庫表設計之間的綁定。若你不得不修改資料庫,那麼同時也要修改活動記錄物件模型以及所有相關代碼,從這個角度看,活動記錄站在了領域驅動的對立面。

領域驅動模式

在設計領域邏輯時,若選用了過程式方法或活動記錄模式,那麼實際上採取的是以資料為核心的做法。驅動業務模型設計的並不是業務本身,而是業務中使用到的資料。

從長遠看,以資料為中心的方法並不能很好的適應規模的增加。因為當系統的複雜性達到某個極限之後,哪怕是再添加一些新的需求,都會成為難處理的問題。領域模型關注於系統的期待行為以及系統正常工作所需要的資料。領域驅動設計力求將複雜性控制在一個可控(雖然仍舊很高)範圍內,選用領域驅動設計並不一定需要使用領域模型模式,不過領域模型模式是最自然的選擇。

領域模型描述了系統中涉及的實體,捕獲了實體之間的關係以及資料在其中交換的過程。領域模型此刻還並不是一個軟體,也不涉及任何軟體或實現上的概念或原則。領域模型只是一個正式的模型,用來讓技術團隊和業務團隊彼此理解並能良好交流。領域模型可以看作是活動記錄的“大哥”,領域模型完全和資料庫獨立,是一個儘可能貼近真實流程的模型。領域模型模式使系統建模非常自由靈活,無需考慮平台和資料庫的約束。此外,領域驅動設計是一種看待設計的方式,因此技能和態度起到了重要的作用。

在領域模型中,概念是用來建模的,這種做法充分利用了物件導向設計的優勢,你可以使用到物件導向的所有特性,包括封裝和繼承,而同時又無需受到資料庫結構的限制,這就意味著實體並不會察覺到絲毫有關底層使用的持久化機制。領域模型是由需求驅動的,且僅需要你理解問題領域,並用類對於邏輯建模。實現領域模型主要的障礙是對象和關係型資料庫之間的不匹配,領域模型是一個物件導向的設計,和資料庫或其他應用程式的約束完全無關,而今受限於其建模的商務程序,這意味著同樣的領域模型可以重用於其他需要同樣邏輯的任意情境。模型是和業務相關的,且僅和業務相關。

若沒有任何O/R映射工具,例如NHibernate,那麼很難實現領域模型模式。

小結

商務邏輯是系統的核心,不過並不是整個系統。商務邏輯設計上的選擇將會影響到其他層,特別是持久化和資料訪問層,這兩個層加起來,就會項目的成敗產生決定的影響。

相關部落格:

  • .Net企業級應用架構設計之當代的架構師和架構
  • .Net企業級應用架構設計之UML
  • .Net企業級應用架構設計之設計原則和模式
  • .Net企業級應用架構設計之業務層設計
  • .Net企業級應用架構設計之服務層設計
  • .Net企業級應用架構設計之資料訪問層
  • .Net企業級應用架構設計之表現層設計

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.