# Haskell をドメイン記述言語として使う
(検証可能な疑似コードとして使う)
| **観点** | **疑似コードの課題** | **Haskellの利点** |
| ------------------------------ | ---------------------------- | --------------------------------------- |
| **曖昧さの排除** | 書き手によって表現がブレる | 型と構文が正確性を保証 |
| **ルールの明示** | ロジックや制約が省略されがち | ガード・パターンマッチで明示できる |
| **ドキュメントとしての持続性** | 書いたら放置されがち | コンパイルが通る限りメンテナンスが可能 |
| **実装とのギャップ** | 擬似表現と実装がズレやすい | Haskellなら**半実装**として再利用できる |
|**ユビキタス言語との対応**|業務用語との整合が曖昧|明確な型や関数名で**業務語をプログラムに反映**できる|
```haskell
data EvaluationStatus = Draft | Submitted | Approved | Rejected
deriving (Show, Eq)
data Command
= Submit UserId EvaluationData
| Approve UserId EvaluationId
| Reject UserId EvaluationId Reason
data Event
= EvaluationSubmitted UserId EvaluationId
| EvaluationApproved UserId EvaluationId
| EvaluationRejected UserId EvaluationId Reason
applyCommand :: EvaluationStatus -> Command -> Either String (EvaluationStatus, Event)
applyCommand Draft (Submit uid data_) =
Right (Submitted, EvaluationSubmitted uid (generateId data_))
applyCommand Submitted (Approve uid eid) =
Right (Approved, EvaluationApproved uid eid)
applyCommand Submitted (Reject uid eid reason) =
Right (Rejected, EvaluationRejected uid eid reason)
applyCommand _ _ = Left "Invalid transition"
```
👉 [[関数型ドメインモデリング#Code]]