許悅珊
摘要:計(jì)算機(jī)硬件需要中央處理器,而計(jì)算機(jī)軟件則需要中央控制器—工作流引擎。工作流引擎不但可以靈活控制軟件的業(yè)務(wù)邏輯,快速適應(yīng)需求的變化,還可以大大提高軟件的開發(fā)效率,為公司節(jié)省成本提高競爭力。文章介紹了嵌入工作流引擎的設(shè)計(jì)思想與實(shí)現(xiàn)方法。
關(guān)鍵詞:工作流引擎;應(yīng)用開發(fā);Java;Hibemet;Servlet
0引言
在每個(gè)軟件工程項(xiàng)目中,軟件工程師都會面對的一個(gè)問題是:邏輯,即遵循一定規(guī)律的流程。流程可能是業(yè)務(wù)流程,也可能是生產(chǎn)流程。軟件就是為這些流程量身定造的用于提高工作或生產(chǎn)效率的產(chǎn)物。因此在軟件的開發(fā)過程中,程序員都不斷地用重復(fù)的代碼去塑造出這些流程,即業(yè)內(nèi)人士所述的工作流。然而,在軟件的維護(hù)過程中,往往由于業(yè)務(wù)或生產(chǎn)流程的變化,使得軟件必須作出相應(yīng)的修改。于是開發(fā)人員又要面臨修改代碼的任務(wù)。簡單的流程代碼倒不成問題,若碰上比較復(fù)雜的流程,則需花上較長時(shí)間去弄清楚代碼的結(jié)構(gòu)然后才能著手去修改,既費(fèi)勁又容易出錯(cuò)。于是,有人便提出把整個(gè)軟件流程圖形化地表現(xiàn)出來,而且可以自定義。工作流引擎便應(yīng)運(yùn)而生。工作流引擎不僅解決了軟件維護(hù)上的問題,而且它可以靈活地應(yīng)用于不同的項(xiàng)目中,減少代碼的編寫量,從而加速軟件的開發(fā)過程。例如:業(yè)務(wù)流程A->B->C->B,用工作流引擎的方法表示如圖1所示。
顯然用工作流引擎的方法定義流程,既邏輯清晰又形象。倘若業(yè)務(wù)邏輯需要變化,只需在工作流引擎上把流程方向線修改一下便可,免除了改動(dòng)代碼并且重新編譯程序的麻煩。越復(fù)雜的流程越能體現(xiàn)它的優(yōu)點(diǎn)。
工作流引擎既然是為開發(fā)人員而設(shè)計(jì)的,當(dāng)然是嵌入到軟件開發(fā)項(xiàng)目中的,它在整個(gè)軟件中起到了大腦的作用。幾乎所有相關(guān)的外圍程序都由它統(tǒng)一管理與觸發(fā)。例如圖1中的ExcuteA()就是我們所說的外圍程序。在實(shí)際開發(fā)的過程中,程序員只需編寫外圍程序然后把程序掛接到工作流引擎中適當(dāng)?shù)奈恢帽憧?。就像工廠的生產(chǎn)線一樣,不同的階段做不同的加工。程序員只需管各階段怎么加工,而什么時(shí)候做什么加工就交給工作流引擎去做。
1靈動(dòng)的工作流引擎的設(shè)計(jì)思想
工作流引擎要求設(shè)計(jì)靈活,適應(yīng)性強(qiáng),才便于嵌入到各種項(xiàng)目中使用。圖2是一個(gè)輕量級工作流引擎設(shè)計(jì)方案,系統(tǒng)整體架構(gòu)采用三層結(jié)構(gòu)。
第一層是以Java Applet嵌入Web中實(shí)現(xiàn)的客戶端。該客戶端的優(yōu)點(diǎn)在于不需安裝而實(shí)時(shí)下載到IE中使用,在應(yīng)用開發(fā)中免去了由于平臺更新所帶來的客戶端重裝的麻煩。而且Java Applet在圖形界面方面的技術(shù)已經(jīng)日趨成熟,利用Java中的AWT與Swing組件能較好地實(shí)現(xiàn)流程自定義界面的功能。當(dāng)然優(yōu)點(diǎn)的背后常常隱藏著缺點(diǎn),這種做法必須以犧牲客戶端資源為代價(jià)。
第二層是以WebSphere為Web服務(wù)器的中間層。該層內(nèi)部又分為兩層,上層是Java Servlet,下層是Hibemet。JavaServlet負(fù)責(zé)與客戶端的Applet通信;而Hibemet則負(fù)責(zé)Oracle數(shù)據(jù)庫的數(shù)據(jù)存取操作。兩者之間也進(jìn)行著密切的數(shù)據(jù)交流,共同構(gòu)建整個(gè)系統(tǒng)程序的主體。此處采用Hibemet作數(shù)據(jù)庫存取的中間件還有一個(gè)重要的優(yōu)點(diǎn)就是Hibernet能靈活地支持多種數(shù)據(jù)庫類型,以持久化的思想代替數(shù)據(jù)庫存儲的思想。倘若在應(yīng)用開發(fā)中的系統(tǒng)采用的不是Oracle數(shù)據(jù)庫,只需對Hibernet的設(shè)置作少量改動(dòng),工作流引擎便可兼容。
第三層是Oracle數(shù)據(jù)庫,負(fù)責(zé)高效的數(shù)據(jù)存取操作。
2靈動(dòng)的工作流引擎的實(shí)現(xiàn)
2.1界面功能
界面布局分為四個(gè)區(qū):功能按鍵區(qū)、樹型目錄區(qū)、流程元素區(qū)以及流程開發(fā)區(qū),如圖3所示。
功能按鍵區(qū):包括新建、保存、刪除以及退出等功能按鍵。樹型目錄區(qū):其實(shí)就是把多個(gè)已存儲的流程按樹型結(jié)構(gòu)顯示出來。流程元素區(qū):包含開始節(jié)點(diǎn)、結(jié)束節(jié)點(diǎn)、普通節(jié)點(diǎn)以及方向線等流程中的元素。可把流程元素拖到流程開發(fā)區(qū)進(jìn)行流程定義。流程開發(fā)區(qū):進(jìn)行流程定義的地方。在該區(qū)域可以自由地新建和拖動(dòng)流程元素。
2.2流程控制的實(shí)現(xiàn)
在數(shù)據(jù)庫中建立三個(gè)表,分別是:
(1)節(jié)點(diǎn)表:用于存儲流程中的節(jié)點(diǎn)屬性。包括名字、節(jié)點(diǎn)權(quán)限、在定義區(qū)的位置、所屬流程編號等。
(2)流向表:用于存儲流程的方向線。包括出發(fā)節(jié)點(diǎn)、指向節(jié)點(diǎn)、所屬流程編號、以及下面講述到的觸發(fā)函數(shù)和代謝函數(shù)。
(3)流程控制表:此表是流程控制的中心表。包括每個(gè)具體業(yè)務(wù)記錄的編號、當(dāng)前所在節(jié)點(diǎn)編號(與節(jié)點(diǎn)表關(guān)聯(lián))、所屬流程編號。每個(gè)新業(yè)務(wù)的辦理都必須先往該表插入一條新記錄。通過該表的信息可以查詢出當(dāng)前用戶所屬節(jié)點(diǎn)有哪些待辦的業(yè)務(wù)。當(dāng)用戶點(diǎn)擊按鈕把業(yè)務(wù)推向下一節(jié)點(diǎn)時(shí),聯(lián)合流程控制表與流向表便可知道下一個(gè)節(jié)點(diǎn)是什么。只需在程序中把流程控制表中的“當(dāng)前所在節(jié)點(diǎn)編號”字段修改為下一個(gè)節(jié)點(diǎn)編號,便可實(shí)現(xiàn)業(yè)務(wù)跟隨所定義的流程流轉(zhuǎn)從而到達(dá)流程控制的目的。
2.3節(jié)點(diǎn)的權(quán)限
在圖3所示的流程處理中,需要提供一個(gè)對節(jié)點(diǎn)權(quán)限設(shè)置的功能,如圖4所示。
在每個(gè)節(jié)點(diǎn)的屬性中可以設(shè)置可讀寫用戶和只讀用戶權(quán)限。輸入框中填入應(yīng)用系統(tǒng)的用戶登錄名用“,”隔開。在開發(fā)過程中用SQL查詢流程控制表和節(jié)點(diǎn)表便可得到當(dāng)前登錄用戶在哪些節(jié)點(diǎn),有哪些待辦任務(wù),從而形成待辦業(yè)務(wù)列表提醒用戶辦理。
2.4外圍程序調(diào)用
工作流引擎只承擔(dān)軟件中的大腦的作用,不實(shí)現(xiàn)任何的具體業(yè)務(wù)程序。為了實(shí)現(xiàn)工作流引擎對這些外圍的業(yè)務(wù)邏輯程序的調(diào)用,需要在節(jié)點(diǎn)屬性中添加兩個(gè)屬性觸發(fā)函數(shù)與代謝函數(shù)。
觸發(fā)函數(shù)是在用戶辦理業(yè)務(wù)時(shí)觸發(fā)的業(yè)務(wù)程序。例如觸發(fā)函數(shù)可以是一個(gè)彈出信息填寫界面的程序方法,在不同節(jié)點(diǎn)可以調(diào)用不同的觸發(fā)函數(shù)來實(shí)現(xiàn)該節(jié)點(diǎn)的業(yè)務(wù)辦理。代謝函數(shù)則在用戶辦理完該節(jié)點(diǎn)的業(yè)務(wù)后,點(diǎn)擊按鈕把業(yè)務(wù)推向下一節(jié)點(diǎn)時(shí)執(zhí)行。它可以用于例如信息的補(bǔ)全或其他由程序自動(dòng)完成的業(yè)務(wù)邏輯。
外圍程序的調(diào)用運(yùn)用了Java中的接口實(shí)現(xiàn)方式。在工作流引擎中定義有觸發(fā)函數(shù)接口和代謝函數(shù)接口(類的其中一種)。接口中分別定義一個(gè)主方法mainFunction()。所有觸發(fā)函數(shù)類和代謝函數(shù)類分別實(shí)現(xiàn)這兩個(gè)接口。類的名稱填寫在節(jié)點(diǎn)屬性中的觸發(fā)函數(shù)和代謝函數(shù)輸入框,如圖5所示。
利用Java的反射機(jī)制,工作流引擎可以自動(dòng)用所填寫的類名稱來實(shí)例化所對應(yīng)的接口,然后統(tǒng)一調(diào)用主方法mainFunc-tion(),從而達(dá)到觸發(fā)該節(jié)點(diǎn)所對應(yīng)的外圍業(yè)務(wù)程序的目的。代碼實(shí)現(xiàn)片斷如下:
觸發(fā)函數(shù)接口:
public interface TrigerFunctionInterface{
boolean mainFunction();
//定義主方法,用于觸發(fā)函數(shù)與代謝函數(shù)實(shí)現(xiàn)
}
觸發(fā)函數(shù)類:
public class BussinessLogic implements
TrigerFunctionInterface{
public boolean mainFunction(){
try{
…//業(yè)務(wù)邏輯代碼
return true;
}catch(Exception e){
e printStackTrace();
return false;
}
}
}
工作流引擎中運(yùn)用Java反射機(jī)制調(diào)用觸發(fā)函數(shù)類方式:
public class Trigger{
try {
//加載觸發(fā)函數(shù)類BussinessLogic
Class bussinessClass=Class.forName(“BussinessLogic”):
//實(shí)例化觸發(fā)函數(shù)類BussinessLogic
Object bussinessObject=bussinessClass.newlnstance();
Ctassl]classPara=new Class[1];
classPara[0]=String.classi
//加載主方法mainFunction
java lang.reflect.Method mainFunction=bussinessClass
.getMethod(“mainFunction”,null):
//調(diào)用主方法mainFunction
mainFunction.invoke(bussinessObject,null);
}catch(Exception e){
e printStackTrace():
}
}
2.5并聯(lián)流程
有時(shí)候業(yè)務(wù)流程并不是單線而是并聯(lián)進(jìn)行的。如圖3所示,業(yè)務(wù)同時(shí)經(jīng)過部門B、部門c和部門D審批,他們之間沒有先后順序。此時(shí)流程控制表需要插入三條記錄分別對應(yīng)于不同部門節(jié)點(diǎn)。所以為了兼容這并聯(lián)的案例,當(dāng)業(yè)務(wù)被推向下一節(jié)點(diǎn)時(shí),應(yīng)該把流程控制表中的原記錄刪除,重新插入新記錄,而不只是像2.2所述的修改“當(dāng)前所在節(jié)點(diǎn)編號”來實(shí)現(xiàn)。
經(jīng)過三個(gè)部門同時(shí)審批后業(yè)務(wù)匯合到部門E。這里會出現(xiàn)兩種情況:一、需要經(jīng)過三個(gè)部門的審批部門E才可辦理;二、只需經(jīng)其中一個(gè)部門審批部門E便可辦理。為了實(shí)現(xiàn)這兩種需求,需要在節(jié)點(diǎn)中添加一個(gè)屬性“匯合”類型,可選值“與合”和“或合”。當(dāng)選擇“與合”時(shí),并聯(lián)的部門之間的關(guān)系便是“與”的關(guān)系,即實(shí)現(xiàn)情況一的需求。當(dāng)選擇“或合”時(shí),并聯(lián)的部門之間的關(guān)系便是“或”的關(guān)系,即實(shí)現(xiàn)情況二的需求。
2.6子流程
對于復(fù)雜的流程,由于節(jié)點(diǎn)太多??雌饋礤e(cuò)綜復(fù)雜,所以把流程分為主流程和若干個(gè)子流程是很必要的。假設(shè)部門E在辦理時(shí)候也需要經(jīng)部門內(nèi)部幾個(gè)職員才能把業(yè)務(wù)辦理完。則需要在部門E的節(jié)點(diǎn)內(nèi)定義子流程。子流程與主流程的隸屬關(guān)系可以在圖3中的樹型目錄區(qū)表現(xiàn)出來。
3結(jié)束語
隨著國內(nèi)軟件業(yè)的逢勃發(fā)展,競爭越來越激烈,誰能開拓更高效率、更高質(zhì)量的軟件開發(fā)理念,誰就有條件在競爭中立于不敗之地。而工作流引擎正是競爭者具備這種條件的重要武器。相信工作流引擎將會發(fā)展成今后的開發(fā)平臺,在開發(fā)平臺上擁有自己的編程語言并可靈活地調(diào)用來自不同系統(tǒng)的程序接口,必將把軟件開發(fā)效率提升到新的高度。