我也在看powerstone workflow 的源碼,今天竟找到一個工作流牛人的心得。爽!
轉自:http://www.guodanpi.com/zblog/post/20.html
近幾天一直在研究工作流,網上的資料也非常少,大多都是淺嘗則止的要么用OSWorkflow做一個什么都不干的demo要么就是拼命的問shark、jBPM這類老外開發的東東,也都是問多答少,連問的問題都很淺顯,感覺研究起來頗為費力。
工作流提得最多的是“工作流管理聯盟(WfMC)的Workflow參考模型”,沒看這個參考之前我就知道這個咚咚絕對是個超級sb,不然也不會吵吵嚷嚷這么多年都沒個霸主出來。后來找到這個sb咚咚所說到的5大接口,pdf下下來幾百頁,別說本來就不懂,就算懂一點看這個也能研究要頭發白,所以干脆就不管什么規范、什么接口,先看看工作流到底為什么需要,要實現哪些玩意才算能夠交差再說。
中國人喜歡玩定義,所以工作流的定義那可真是五花八門,不知道寫出這些定義的bb有沒有真正開發過一個可用的工作流。看看這個感覺比較有意思http://blog.csdn.net/hongbo781202/archive/2004/09/26/117271.aspx,所以覺得他定義的是不是也能算數:工作流就是為了完成同一目標而相互銜接、自動進行的一系列業務活動或任務。
后來找到一篇介紹工作流的dbms實現的吹牛文章www.ict.ac.cn/xueshu/2001/061.doc,當然多少有點用處,它的組織結構、用戶、角色定義這塊按那幅數據庫設計圖來看還不錯(打算借來改良我們現在的acl系統,呵呵),其他的糟粕不說也罷。
還是先理一理腦子里面的一些概念:(絕對是憑空設想,如果有和××規范或××實現相同的地方純粹巧合)
1. 一個工作流應該由多個狀態構成
既然總說工作流是“基于有限狀態機”的,“有一系列的活動”,那么工作流在“流動”的過程中總要有歇腳的地方,歇下來的時候給當前的狀態拍張照就形成了一個“工作流狀態”。當然,在真實設計的過程中,肯定是人為先定義好這些狀態,由多個狀態(一個開始狀態,多個中間和結束狀態)構成一個工作流定義。工作流對應到數據庫來說除了用個id來記錄外,幾乎沒有任何必須的屬性(當然加個name好認誰也不攔你)。關鍵在于它的兒子(工作流狀態)難定義。
2. 工作流的狀態定義
工作流狀態是一個靜止的概念,說白了可能就是一個字符串“通過”,“審批”等等,但是他要決定如何處理前置狀態流向它的信息。
應該說工作流某一狀態的入口是1…N,它的前置狀態可以有多個(當然開始比較特殊,沒有),前置狀態經過一定的條件后方可到達當前的工作流狀態,問題的核心不在于有多少個前置條件可以到達當前狀態,而是這些前置條件在到達時的規則,這個規則當然是對于前置條件已經滿足,在“匯流”到當前狀態時會有一些處理動作:(由于網上很多介紹都有一些處理的規則,但是我希望能將這些規則具體分配到是流入的動作還是流出的動作)
1)對于前置條件的流入如何處理
a. 順序:當然是對單一的流入口來說的了,沒有什么特別
b. 與匯聚(可能也就是oa里的會簽):詳細來說就是必須滿足所有的前置條件方能到達當前狀態,很好解釋,所有的前置條件都必須處理,所以在數據遺留(后面再說)的處理來說是最容易的。
c. 或匯聚:相對于與匯聚,或匯聚就是只要有一個前置條件通過則可以進入到當前的狀態??梢钥紤]當前的常任理事國的反對機制,只要一個反對,就不能通過。而或匯聚則是只要一個前置條件滿足了,就可以進入當前狀態。
d. 投票:票數達到一定的百分比或數量就算通過。想想人大代表的產生就很容易理解投票機制。可以理解是或匯聚和與匯聚的一個補充。
除了a意外,其他3個都有數據遺留的問題(呵呵,自己發明的概念):當工作流滿足定義的處理規則進入當前狀態后,如何處理那些不滿足條件的前置條件的數據?舉個例子比較容易說明:
項目招標,需要甲、乙、丙的三個平級領導的簽字才能通過,如下:
甲簽字 ----|
乙簽字 ----| ------------------à 通過
丙簽字 ----|
分情況說明:
對于與匯聚:甲通過,乙通過,但是直到丙也通過則進入通過狀態。如果復雜一點,丙退回的情況下,如何處理?此時甲、乙的通過情況應該保持不變,只記錄丙的退回,然后做退回上一狀態的動作。
對于或匯聚:甲通過則全通過,此時需要清理乙、丙的待審批數據,改變該數據的狀態。如果復雜一點:丙退回!那么現在就全亂了套了,所以個人感覺,或匯聚狀態下,只要一個通過則該狀態需要鎖定,其他分支將不能再處理。
對于投票:如果說需要2個人同意方通過,甲同意,乙同意,好說,通過。如果復雜一點:甲通過,乙退回,丙通過!如何處理?又亂了套了,所以也是個人感覺,在投票狀態下,應該處于鎖定狀態,知道滿足通過條件或者不通過條件,方可處理。實際上這種情況非常復雜,可以采取增加優先級的方法處理,也就是說列舉各情況的優先級,然后按優先級最高的處理。
2)對于流出如何處理
a. 條件:需要滿足一定的條件才能流出
b. 時間:在無人處理的情況下,是否采用超時處理
c. 還沒想到,呵呵
3. 工作流的狀態間行為定義
實際上記錄靜態的工作流狀態沒有意義,我們需要考慮的是記錄從哪個狀態到另一狀態的“路程”。所以在這里要定義的是我們常常用到的“箭頭”,也就是一個起點,一個終點的記錄。
唐僧經常被問:施主從哪里來,要到哪里去?工作流狀態就是“大唐”和“西天”,狀態間行為則要回答這個問題,但是比起唐僧千篇一律的回答,狀態間行為自然要復雜得多。
1) 解決從哪里來:
前面已經說明,我們要記錄的是各狀態間的“箭頭”,由于對于這個“箭頭”來說只存在唯一的起點和終點所以在數據庫的設計上,“從哪里來”的信息(定義為FromState)。
2) 解決到哪里去:可以定義為ToState
可以看到狀態與狀態之間是不止一種狀態間行為的。
我們可以大致定義數據庫如下:
class Workflow{
Long id;
}
class State{
Long id;
Workflow workflow;
String fromCondition;
String toCondition;
}
class Route{
Long id;
State fromState;
State toState;
}
先想這么多,明天繼續完善,呵呵(都是瞎扯啊)。