詳解51種企業(yè)應(yīng)用架構(gòu)模式
1.什么是企業(yè)應(yīng)用
我的職業(yè)生涯專注于企業(yè)應(yīng)用,因此,這里所談及的模式也都是關(guān)于企業(yè)應(yīng)用的。(企業(yè)應(yīng)用還有一些其他的說(shuō)法,如“信息系統(tǒng)”或更早期的“數(shù)據(jù)處理”。)那么,這里的“企業(yè)應(yīng)用”具體指的是什么呢?我無(wú)法給出一個(gè)精確的定義,但是我可以羅列一些個(gè)人的理解。
先舉幾個(gè)例子。企業(yè)應(yīng)用包括工資單、患者記錄、發(fā)貨跟蹤、成本分析、信用評(píng)分、保險(xiǎn)、供應(yīng)鏈、會(huì)計(jì)、客戶服務(wù)以及外匯交易等。企業(yè)應(yīng)用不包括汽車燃油噴射、文字處理、電梯控制、化工廠控制器、電話交換機(jī)、操作系統(tǒng)、編譯器以及電子游戲等。
企業(yè)應(yīng)用一般都涉及持久化數(shù)據(jù)。數(shù)據(jù)必須持久化是因?yàn)槌绦虻亩啻芜\(yùn)行都需要用到它們——實(shí)際上,有些數(shù)據(jù)需要持久化若干年。在此期間,操作這些數(shù)據(jù)的程序往往會(huì)有很多變化。這些數(shù)據(jù)的生命周期往往比最初生成它們的那些硬件、操作系統(tǒng)和編譯器還要長(zhǎng)。在此期間,為了存儲(chǔ)新的信息而不干擾舊的信息,數(shù)據(jù)的結(jié)構(gòu)經(jīng)常會(huì)發(fā)生許多變化。即使是有根本性的變化發(fā)生,或公司安裝了一套全新的軟件來(lái)處理某項(xiàng)任務(wù),這些數(shù)據(jù)也必須被“遷移”到新的應(yīng)用上。
企業(yè)應(yīng)用一般都涉及大量數(shù)據(jù)——一個(gè)中等規(guī)模的系統(tǒng)往往都包含1GB以上的數(shù)據(jù),這些數(shù)據(jù)是以數(shù)千萬(wàn)條記錄的方式存在的。巨大的數(shù)據(jù)量導(dǎo)致數(shù)據(jù)的管理成為系統(tǒng)的主要工作。早期的系統(tǒng)使用的是索引文件結(jié)構(gòu),如IBM的VSAM和ISAM。現(xiàn)代的系統(tǒng)往往采用數(shù)據(jù)庫(kù),絕大多數(shù)是關(guān)系型數(shù)據(jù)庫(kù)。設(shè)計(jì)和填充這些數(shù)據(jù)庫(kù)已經(jīng)成為一個(gè)獨(dú)立的專業(yè)領(lǐng)域。
企業(yè)應(yīng)用一般還涉及很多人并發(fā)訪問(wèn)數(shù)據(jù)。對(duì)于很多系統(tǒng)來(lái)說(shuō),人數(shù)可能在100人以下,但是對(duì)于一些通過(guò)互聯(lián)網(wǎng)進(jìn)行通信的基于Web的系統(tǒng),人數(shù)則會(huì)呈指數(shù)級(jí)增長(zhǎng)。要確保這些人都能夠正確地訪問(wèn)數(shù)據(jù),就一定會(huì)存在這樣或那樣的問(wèn)題。即使人數(shù)沒(méi)有那么多,要確保兩個(gè)人在同時(shí)操作同一數(shù)據(jù)項(xiàng)時(shí)不出現(xiàn)錯(cuò)誤,也是存在問(wèn)題的。事務(wù)管理工具可以處理其中的一些負(fù)擔(dān),但是它通常無(wú)法做到對(duì)應(yīng)用開(kāi)發(fā)者隱藏。
企業(yè)應(yīng)用還涉及大量操作數(shù)據(jù)的用戶界面屏幕。有幾百個(gè)用戶界面屏幕是不足為奇的。企業(yè)應(yīng)用的用戶從偶爾使用到定期使用都有,他們也經(jīng)常沒(méi)什么技術(shù)背景。因此,出于不同的使用目的,數(shù)據(jù)需要很多種表現(xiàn)形式。系統(tǒng)一般都有很多批處理過(guò)程,但當(dāng)專注于強(qiáng)調(diào)用戶交互的用例時(shí),這些批處理過(guò)程很容易被忽視。
企業(yè)應(yīng)用很少獨(dú)立存在,通常需要與散布在企業(yè)周圍的其他企業(yè)應(yīng)用集成。這些各式各樣的系統(tǒng)是在不同時(shí)期采用不同技術(shù)構(gòu)建的,甚至連協(xié)作機(jī)制都不同:COBOL數(shù)據(jù)文件、CORBA系統(tǒng)或是消息系統(tǒng)。企業(yè)經(jīng)常希望能用一種統(tǒng)一的通信技術(shù)來(lái)集成所有系統(tǒng)。當(dāng)然,每次這樣的集成工作幾乎都很難真正實(shí)現(xiàn),所以會(huì)有幾個(gè)不同的統(tǒng)一集成方案同時(shí)存在。當(dāng)業(yè)務(wù)組織需要同其業(yè)務(wù)伙伴進(jìn)行應(yīng)用集成時(shí),情況就更糟糕。
即使是某家公司統(tǒng)一了集成技術(shù),它們也還是會(huì)遇到業(yè)務(wù)流程中的差異以及數(shù)據(jù)中概念的不一致性。一個(gè)部門可能認(rèn)為客戶是當(dāng)前簽有協(xié)議的人,而另外一個(gè)部門可能還要將那些以前有合同但現(xiàn)在已經(jīng)沒(méi)有了的人計(jì)算在內(nèi)。再有,一個(gè)部門可能只關(guān)心產(chǎn)品銷售而不關(guān)心服務(wù)銷售。粗看起來(lái),這些問(wèn)題似乎容易解決,但是,一旦幾百條記錄中的每個(gè)字段都有可能存在著細(xì)微差別,問(wèn)題的規(guī)模就會(huì)形成不小的挑戰(zhàn)——就算唯一知道這些字段真正含義的員工還在公司任職(當(dāng)然,所有這些都會(huì)毫無(wú)預(yù)警地發(fā)生變化)。這樣,數(shù)據(jù)就必須被不停地以各種不同的語(yǔ)法和語(yǔ)義格式讀取、轉(zhuǎn)換和寫入。
再接下來(lái)的問(wèn)題是由“業(yè)務(wù)邏輯”帶來(lái)的。我認(rèn)為“業(yè)務(wù)邏輯”這個(gè)詞很滑稽,因?yàn)楹茈y再找出什么東西比“業(yè)務(wù)邏輯”更加沒(méi)有邏輯。當(dāng)我們構(gòu)建一個(gè)操作系統(tǒng)時(shí),總是盡可能地使得系統(tǒng)中的各種事物符合邏輯。而業(yè)務(wù)規(guī)則是人家給你的,沒(méi)有相當(dāng)?shù)男姓Γ灰敫淖兯?dāng)然,它們都有自己的理由。你必須面對(duì)很多奇怪的條件,而且這些條件相互作用的方式也非常怪異。比如,某個(gè)銷售人員為了簽下其客戶幾百萬(wàn)美元的一張單,可能會(huì)在商務(wù)談判中與對(duì)方達(dá)成協(xié)議,將該項(xiàng)目的年度到賬時(shí)間推遲兩天,因?yàn)檫@樣才能夠與該客戶的賬務(wù)周期相吻合。成千上萬(wàn)的這類“一次性特殊情況”最終導(dǎo)致了復(fù)雜的業(yè)務(wù)“無(wú)邏輯”,使得商業(yè)軟件開(kāi)發(fā)那么困難。在這種情況下,必須盡量將這些業(yè)務(wù)邏輯組織成有效的方式,因?yàn)槲覀兛梢源_定的是,這些“邏輯”一定會(huì)隨著時(shí)間不斷變化。
對(duì)不同的領(lǐng)域邏輯組織方式,領(lǐng)域邏輯的復(fù)雜度和工作量之間的關(guān)系示意
對(duì)于一些人來(lái)說(shuō),“企業(yè)應(yīng)用”這個(gè)術(shù)語(yǔ)指的是大型系統(tǒng)。但是記住這一點(diǎn)很重要:并不是所有的企業(yè)應(yīng)用都是大型的,盡管它們可能都為企業(yè)提供巨大的價(jià)值。很多人認(rèn)為,由于小型系統(tǒng)的規(guī)模不大,所以不值得為之操心,在某種程度上,這是合理的。如果一個(gè)小型系統(tǒng)失敗了,它通常不會(huì)像大型系統(tǒng)那樣引起廣泛關(guān)注。但是,我認(rèn)為這種思想沒(méi)有對(duì)小型項(xiàng)目的累積效應(yīng)給予足夠的重視。試想,如果在小型項(xiàng)目上能夠進(jìn)行某些改善措施,那么這種累積效應(yīng)對(duì)企業(yè)的影響是非常顯著的,特別是因?yàn)樾⌒晚?xiàng)目通常具有不成比例的價(jià)值。實(shí)際上,你可以做的最好的事情之一是通過(guò)簡(jiǎn)化架構(gòu)和過(guò)程,將一個(gè)大型項(xiàng)目變成小型項(xiàng)目。
2.企業(yè)應(yīng)用的種類
在我們討論如何設(shè)計(jì)企業(yè)應(yīng)用以及使用哪些模式之前,認(rèn)識(shí)到這一點(diǎn)很重要:企業(yè)應(yīng)用是多種多樣的,不同的問(wèn)題將導(dǎo)致不同的處理方法。如果有人說(shuō),“總是這樣做”的時(shí)候,就應(yīng)當(dāng)敲響警鐘了。我認(rèn)為,設(shè)計(jì)中最具挑戰(zhàn)性(也是我最感興趣)的地方就是了解有哪些候選的設(shè)計(jì)方案以及各種不同設(shè)計(jì)方案之間的優(yōu)劣比較。進(jìn)行選擇的空間很大,但我在這里只選三個(gè)方面。
考慮一個(gè)B2C(Business to Customer)的在線零售商:人們?yōu)g覽和——運(yùn)氣好,還有購(gòu)物車——購(gòu)買。這樣一個(gè)系統(tǒng)必須能夠應(yīng)付大量的用戶,因此,其解決方案不但要考慮到資源利用的高效,還要考慮到系統(tǒng)的可伸縮性,以便在用戶規(guī)模增大時(shí)能夠通過(guò)增加硬件的辦法加以解決。這樣的應(yīng)用的領(lǐng)域邏輯可能非常直接:獲取訂單,進(jìn)行簡(jiǎn)單的價(jià)格計(jì)算和發(fā)貨計(jì)算,給出發(fā)貨通知。我們希望任何人都能夠輕松訪問(wèn)該系統(tǒng),因此用戶界面可以選用通用的Web表現(xiàn)方式,以支持各種不同的瀏覽器。數(shù)據(jù)源包括用來(lái)存放訂單的數(shù)據(jù)庫(kù),還可能包括某種與庫(kù)存系統(tǒng)的通信交流,以便獲得商品的可用性信息和發(fā)貨信息。
再考慮一個(gè)租約自動(dòng)處理系統(tǒng)。在某些方面,這樣的系統(tǒng)比起前面介紹的B2C零售商系統(tǒng)要簡(jiǎn)單得多,因?yàn)樗挠脩魯?shù)很少(在特定時(shí)間內(nèi)不會(huì)超過(guò)100個(gè)),但是它的業(yè)務(wù)邏輯卻比較復(fù)雜。計(jì)算每個(gè)租約的月供,處理諸如提早解約和逾期付款這樣的事件,簽訂合同時(shí)驗(yàn)證各種數(shù)據(jù),這些都是復(fù)雜的任務(wù),因?yàn)樽饧s行業(yè)的許多競(jìng)爭(zhēng)都是以過(guò)去的交易為基礎(chǔ)稍加變化而出現(xiàn)的。正是因?yàn)橐?guī)則的隨意性很大,才使得像這樣一個(gè)復(fù)雜的業(yè)務(wù)領(lǐng)域具有挑戰(zhàn)性。
這樣的系統(tǒng)在用戶界面(UI)上也更加復(fù)雜。這就要求HTML界面要能提供更豐富的功能和更復(fù)雜的屏幕,而這些要求往往是HTML前端目前無(wú)法達(dá)到的,需要更傳統(tǒng)的富客戶界面。用戶交互的復(fù)雜性還會(huì)帶來(lái)事務(wù)行為的復(fù)雜性:簽訂租約可能要耗時(shí)1~2小時(shí),這期間用戶要處于一個(gè)邏輯事務(wù)中。一個(gè)復(fù)雜的數(shù)據(jù)庫(kù)設(shè)計(jì)方案中可能也會(huì)涉及200多個(gè)表以及一些有關(guān)資產(chǎn)評(píng)估和計(jì)價(jià)的軟件包。
第三個(gè)例子是一家小型公司使用的簡(jiǎn)單的“開(kāi)支跟蹤系統(tǒng)”。這個(gè)系統(tǒng)的用戶很少,邏輯簡(jiǎn)單,并且可以通過(guò)HTML表示輕松地在整個(gè)公司訪問(wèn),唯一的數(shù)據(jù)源是數(shù)據(jù)庫(kù)中的幾個(gè)表。盡管如此,開(kāi)發(fā)這樣的系統(tǒng)也不是沒(méi)有挑戰(zhàn)。一方面你必須快速地開(kāi)發(fā)出它,另一方面你又必須為它以后可能的發(fā)展考慮:也許以后會(huì)為它增加計(jì)算報(bào)銷支票的功能,也許它會(huì)被集成到工資系統(tǒng)中,也許還要增加關(guān)于稅務(wù)的功能,也許要為公司的CFO生成匯總報(bào)表,也許會(huì)被集成到一個(gè)航空訂票Web Service中,等等。如果在這個(gè)系統(tǒng)的開(kāi)發(fā)中,也試圖使用前面兩個(gè)例子中的一些架構(gòu),可能會(huì)影響開(kāi)發(fā)進(jìn)度。如果一個(gè)系統(tǒng)會(huì)帶來(lái)業(yè)務(wù)效益(如所有的企業(yè)應(yīng)用應(yīng)該的那樣),則系統(tǒng)進(jìn)度延誤同樣也是開(kāi)銷。你不希望現(xiàn)在做出的決策會(huì)阻礙未來(lái)的發(fā)展。但是,如果現(xiàn)在就考慮了這些靈活性但是考慮不得當(dāng),額外的復(fù)雜性又可能會(huì)讓系統(tǒng)在未來(lái)變得更難演化,進(jìn)一步延誤系統(tǒng)部署,減少系統(tǒng)的效益。雖然這類系統(tǒng)很小,但是一個(gè)企業(yè)中往往有很多這樣的系統(tǒng),這些系統(tǒng)的架構(gòu)不良性累積起來(lái),后果將會(huì)非常可怕。
這三個(gè)企業(yè)應(yīng)用的例子都有難點(diǎn),而且難點(diǎn)各不相同。當(dāng)然,也不可能有一個(gè)適合于三者的通用架構(gòu)。選擇架構(gòu)時(shí),必須很清楚地理解系統(tǒng)的特定問(wèn)題,在理解的基礎(chǔ)上再來(lái)選擇合適的設(shè)計(jì)。
3.企業(yè)架構(gòu)模式
模式的概念早就有了。我在這里不想把這段歷史重新演繹一遍。只是想簡(jiǎn)單談?wù)勎覍?duì)模式和它們?yōu)槭裁词敲枋鲈O(shè)計(jì)的重要手段的一些看法。
模式?jīng)]有統(tǒng)一的定義,可能最好的起點(diǎn)是Christopher Alexander給出的定義(這也是許多模式狂熱者的靈感來(lái)源):
“每一個(gè)模式描述了一個(gè)在我們周圍不斷重復(fù)發(fā)生的問(wèn)題以及該問(wèn)題解決方案的核心。這樣,你就能一次又一次地使用該方案而不必做重復(fù)勞動(dòng)”[Alexander et al.]。
盡管Alexander是建筑家,他談?wù)摰氖墙ㄖJ剑涠x也能很好地適用于軟件業(yè)。模式的核心就是特定的解決方案,它有效而且有足夠的通用性,能解決重復(fù)出現(xiàn)的問(wèn)題。模式的另一種視角是把它看成一組建議,而創(chuàng)造模式的藝術(shù)則是將很多建議分解開(kāi)來(lái),形成相互獨(dú)立的組,在此基礎(chǔ)上可以相對(duì)獨(dú)立地討論它們。
模式的關(guān)鍵點(diǎn)是它們?cè)从趯?shí)踐。必須觀察人們的工作過(guò)程,發(fā)現(xiàn)其中好的設(shè)計(jì),并找出“這些解決方案的核心”。這并不是一個(gè)簡(jiǎn)單的過(guò)程,但是一旦發(fā)現(xiàn)了某個(gè)模式,它將是非常有價(jià)值的。
一旦需要使用模式,就必須知道如何將它運(yùn)用于當(dāng)前的問(wèn)題。使用模式的關(guān)鍵之一是不能盲目使用,這也是模式工具為什么都那么慘。我認(rèn)為模式是一種“半生不熟品”,為了用好它,還必須在自己的項(xiàng)目中把剩下的那一半“火候”補(bǔ)上。我本人每次在使用模式時(shí),都會(huì)東改一點(diǎn)西改一點(diǎn)。因此你會(huì)多次看到同一個(gè)解決方案,但沒(méi)有一次是完全相同的。
每個(gè)模式相對(duì)獨(dú)立,但又不彼此孤立。有時(shí)候它們相互影響,如影隨形。































