ワークフローの入力
from Modeling Workflows as Pipelines
入力としてのコマンド
ワークフロー の真の入力は コマンド である
単なる ドメインオブジェクト ではない radish-miyazaki.icon
https://scrapbox.io/files/668383067a07ad001c6621b5.png
DTO から デシリアライズ 済み
e.g. 注文確定ワークフロー(ドメインの文書化)
コマンドは、PlaceOrder(注文を確定する)とする
このコマンドは、ワークフローがリクエストを処理するために必要な情報をすべて内包している必要がある
ドメインオブジェクト
UnvalidatedOrder
code:fsharp
type UnvalidatedOrder =
{ OrderId: string
CustomerInfo: UnvalidateCustomerInfo
ShippingAddress: UnvalidatedAddress }
また、今回はメタデータを記録・監査のために追跡したいので、以下のように型を定義する
メタデータ
誰がコマンドを作成したか
タイムスタンプ
もちろんこれらは仕様による(必須ではない) radish-miyazaki.icon
code:fsharp
type PlaceOrder =
{ OrderForm: UnvalidatedOrder
TimeStamp: DateTime
UserId: string }
ジェネリクスによる共通構造の共有
各 コマンド は共通するフィールドを持つ
e.g.
タイムスタンプ
ユーザ ID
OOP の場合
共有のフィールドを含む 基底クラス を定義し、各コマンドはそれを継承することで解決できる
FP の場合
ジェネリクス を使うことで解決できる
code:fsharp
type Command<'data> = {
Data: 'data
TimeStamp: DateTime
UserId: string
}
type PlacedOrderCommand = Command<UnvalidatedOrder>
複数のコマンドを 1 つの型にまとめる
場合によっては、境界づけられたコンテキスト のすべてのコマンドが同じ入力チャネル(メッセージキュー)で送信されることもある
https://scrapbox.io/files/669d03b8609fd8001c2fafbc.png
この場合、これらをシリアライズする 1 つのデータ構造に統一する必要がある
複数のコマンドから 1 つを選択するため、選択型 を用いる
code:fsharp
type OrderTakingCommand =
| Place of PlaceOrder
| Change of ChangeOrder
| Cancel of CancelOrder
この選択型は、DTO にマッピングされ、入力チャネル上で シリアライズ・デシリアライズ が行われる
https://scrapbox.io/files/669d04b38021a1001d2f9a16.png
オニオンアーキテクチャ の インフラストラクチャ層 に新しい ルーティング または ディスパッチ の入力ステージを追加する