WF 4 のステートマシン ワークフロー


環境 :
Visual Studio 2010 Service Pack 1 (SP1 - 日本語)
.NET Framework 4 Platform Update 1 - Design-time Update for Visual Studio 2010 SP1 (日本語)

.NET 4 Platform Update 1 の WF 新機能

こんにちは。

もう少し経ってしまいましたが、.NET Framework 4 Platform Update 1 (.NET Framework 4 プラットフォーム 更新プログラム 1) がリリースされました。.NET Endpoint Team Blog でも紹介しているように、この .NET Framework 4 Platform Update 1 には WF (Windows Workflow Foundation) にいくつかの Update が行われていますので、それぞれのポイントを見て行きたいと思います。

 

なお、この Platform Update を使って開発をおこなうには、Visual Studio 2010 SP1 に、以下を適用してください。

[ダウンロード センター] .NET Framework 4 プラットフォーム 更新プログラム 1 - Visual Studio 2010 SP1 用デザイン時更新プログラム (KB2495593)
http://www.microsoft.com/downloads/details.aspx?FamilyID=4863f88f-5519-4b66-a195-752746b4389a&displayLang=ja

[ダウンロード センター] .NET Framework 4 プラットフォーム更新プログラム 1 - ランタイム更新プログラム (KB2478063)
http://www.microsoft.com/downloads/details.aspx?FamilyID=e85a2f1b-031c-419c-95b2-0610e90bafd7&displayLang=ja

今回は、ステート マシン ワークフロー (State Machine Workflow) について記載します。

ステート マシン ワークフロー (State Machine Workflow)

以前、こちら の投稿でも記載した通り、.NET 4 の WF (WF 4) では、新たに「フロー チャート」(Flow Chart) というワークフロー テンプレート (ルート ワークフロー) が導入され、かなり柔軟なワークフロー構築が可能となりました。しかし、その一方で、WF 3.5 まで提供されていた「ステート マシン」(State Machine) と呼ばれるイベント ドリブンなワークフロー テンプレートが標準のテンプレートから外され、実は、これまで、WF 4 のステート マシン ワークフローのテンプレートが、別途、ダウンロードで提供されていましたが、今回、Platform Update で標準的に組み込まれました。
では、早速、このワークフロー テンプレートを使って、その概要を簡単に見ていきましょう。

まず、Visual Studio を起動して、[ワークフロー コンソール アプリケーション] を新規作成します。この際、下図の通り、ターゲット プラットフォームとして、[.NET Framework 4 Platform Update 1] を選択 します。

WF 4 の State Machine Workflow では、基本的に、State (状態) と Transition (イベントによる遷移) を結ぶことでワークフローを作成します。

では、今回は、座席予約のサンプルを構築してみましょう !
今回の場合、状態 (State) には、空席あり (Seat Available) と満席 (Seat Full) の 2 つの状態があり、Transition には、シートの予約 (Reserve)、シートのキャンセル (Cancel) の各 Transition があります。

まず、ツールボックスから、StateMachine アクティビティを Workflow1.xaml にドラッグ アンド ドロップします。

あらかじめ、ワークフローで使う変数 (Variables) を作成しておきましょう。今回は、予約可能な座席数 (AvailableSeatCount) と、現在予約されている座席数 (ReservedSeatCount) の 2 つの変数を作成して初期化します。上図の StateMachine をマウスで選択して、下図の通り、変数 (Variables) として、AvailableSeatCount、ReservedSeatCount を作成します。

WF 4 のステートマシン ワークフローでは、必ず開始点 (上図の Start) と、その次の状態 (上図の State1) が存在します。そして、ワークフローにおける初期化の処理は、この State1 (上図) に記述します。

上図の State1 の名前を「Initialize State」という名前に変更して、この State をダブル クリックして、下図の通り、Entry ブロックを使って、上記の変数 (AvailableSeatCount、ReservedSeatCount) に Assign をおこないます。(今回は、予約可能な座席数を 5 とします。)

補足 : この Entry ブロックは、その State になったときに必ず呼び出されるブロックです。一方、State の Exit ブロックは、その State が終了する際に必ず呼ばれるもので、Transition の Condition が評価され、その State が終了することが明確になったタイミングで呼び出されます。

次に、StateMachine のダイアグラム (上図) に戻って、ツールボックスから State と FinalState をドラッグ アンド ドロップして挿入し、それぞれの名前を「SeatAvailable」、「SeatFull」とします。(SeatFull の状態になったら、この StateMachine は終了します。)

上図の SeatAvailable をダブルクリックして、下図の通り、Entry ブロックで、「State : Seat Available」とコンソール出力 (WriteLine) します。

同様に、SeatFull (Final State) の Entry ブロックでは、「State : Seat Full」とコンソール出力します。

StateMachine ダイアグラムの「Initialize State」の隅にマウスを持って行き、クリックして、SeatAvailable までドラッグすると、下図の通り「T1」という名前の Transition が作成されます。

この T1 をダブル クリックして、下図の通り、Condition 欄に、以下の式を入力します。(ReservedSeatCount が AvailableSeatCount より少ない場合は、この State に遷移します。今回の場合、必ず、この State に遷移することになります。)

AvailableSeatCount > ReservedSeatCount

同様に、「Initialize State」から SeatFull に Transition (T2) を作成し、Condition として、以下の式を入力します。

AvailableSeatCount = ReservedSeatCount

つぎに、シートが予約された際の処理を作成します。通常であれば、WF の Bookmark (ブックマーク) や、ワークフロー サービスの ReceiveActivity など、外部からの入力などのトリガー (Trigger) 処理があり、その結果に応じて処理をおこないますが、今回は、1 秒ごとに予約を追加します。(なお、今回は、キャンセルの処理は省略します。)
まず、この「予約追加」の Transition を作成するため、上記同様、SeatAvailable の隅にマウスを持って行き、クリックをおこなって、SeatFull までドラッグをおこないます。(「T3」の Transition が作成されます。)

この T3 をダブルクリックして、下図の通り、T3 の Trigger として、1 秒待ってから (Delay してから)、

ReservedSeatCount + 1

を設定 (Assign) するようにします。また、Condition には、

AvailableSeatCount = ReservedSeatCount

を設定し、予約数が予約可能な座席数と同じになったら、SeatFull に遷移させるようにします。

以上で完成しました。

このワークフローを実行すると、下図の通り、最初は「Seat Available」と表示され、5 秒後に「Seat Full」と表示されます。

上記の通り、Transition はいくつも作成できますが、ステートマシンでは、状態 (State) は、常に、どれか 1 つであり、同時に 2 つの状態になることはありません。そして、FinalState に到達すると、その StateMachine は終了します。

また、上記で、T3 の Trigger 処理を共有し、その結果に応じて別の分岐を作ることもできます。(これは、Shared Transition と呼ばれます。)
上記の T3 の始点にマウスを持って行き、丸いアイコンをマウスでドラッグして、SeatAvailable にドロップすると、下図の通り、T3 から分岐されて T4 が作成されます。

この T4 をダブル クリックすると、下図の通り、T3 と同じ Trigger が表示されます。今回は、Condition として

ReservedSeatCount < AvailableSeatCount

を設定すると、予約数 (ReservedSeatCount) が予約可能な座席数 (AvailableSeatCount) より少ない場合には、毎回、SeatAvailable の状態 (State) に戻ります。

このため、実行結果は、以下の通り変化します。(「Seat Full」になるまでは、毎回、「Seat Available」と表示されます。)

また、State の Entry に StateMachine アクティビティを入れて、状態遷移をネストさせることもできます。(その State の Entry が終了するまで、つぎの Transition の評価はおこなわれません。) 例えば、「日程調整」、「予約受付」、「追加受付」などの各状態 (State) があり、その State 内で上記の「予約可能」、「満席」などの State を持った StateMachine を実行することが可能です。

 

関連ナンバー

 

Comments (0)

Skip to main content