Exception design
ドメイン例外の設計・分類・階層構造を支援する。 次のような依頼があったときに使う:「ドメイン例外を設計する」「例外クラスを作る」 「エラーハンドリングを設計する」「例外の分類を整理する」「ビジネスエラーを定義する」 「例外戦略を決める」「例外設計をレビューする」「エラーハンドリングを改善する」。 または、ドメイン例外、ビジネスエラー、例外設計、エラーハンドリング、例外の分類に言及する場合にも使う。From its SKILL.md
npx -y skills add dskst/ddd-skills --skill exception-designAssembled from the repository path, not quoted from the project. Check it against their README if it does not work.
One thing to look at
- 1 stars1 stars. Stars are a popularity signal and not a quality one, but at this level it is likely that nobody has read this closely except its author, and you would be relying on your own review.
SKILL.md
6.4 KB, as published. Nobody here has run it
例外設計
DDD におけるドメイン例外の設計・分類・階層構造の構築を支援する。
ドメイン例外とは
ビジネスルールの違反を表現する例外である。技術的なエラー(DB接続エラー等)とは明確に分離する。
原則:
- ドメイン例外はドメイン層に定義する
- 例外名はドメイン用語で命名する(技術用語を使わない)
- 例外はビジネスルール違反の「何が」「なぜ」起きたかを伝える
- 例外の捕捉・変換はアプリケーション層またはインフラ層で行う
例外の分類体系
層別の例外分類
例外の種類
├── ドメイン例外(ドメイン層)
│ ├── 不変条件違反: ビジネスルールに反する操作
│ ├── 存在条件違反: 必要なオブジェクトが見つからない
│ └── 状態遷移違反: 許可されない状態遷移
│
├── アプリケーション例外(アプリケーション層)
│ ├── 認証エラー: 認証に失敗
│ ├── 認可エラー: 権限がない操作
│ └── ユースケースエラー: ユースケース前提条件の不成立
│
└── インフラ例外(インフラ層)
├── 永続化エラー: DB操作の失敗
├── 通信エラー: 外部サービスとの通信失敗
└── 設定エラー: 構成の不備
ドメイン例外の詳細分類
| 分類 | 説明 | 例 |
|---|---|---|
| 不変条件違反 | ビジネスルールに反する | 在庫不足、残高不足、上限超過 |
| 存在条件違反 | 必要なものが見つからない | 商品が存在しない、顧客が見つからない |
| 状態遷移違反 | 許可されない状態変更 | キャンセル済み注文の確定、配送済みの取消 |
| 整合性違反 | データ間の不整合 | 合計金額の不一致、重複登録 |
例外の命名規則
ドメイン用語で、何が問題かを明確に伝える。
推奨:
InsufficientStockException — 在庫不足
OrderAlreadyCancelledException — 注文は既にキャンセル済み
InvalidOrderAmountException — 注文金額が不正
CustomerNotFoundException — 顧客が見つからない
非推奨:
BusinessException — 抽象的すぎる
ValidationError — 何の検証か不明
IllegalStateException — 技術用語
Error001 — 意味が不明
例外階層の設計
DomainException(基底)
├── InvariantViolationException(不変条件違反の基底)
│ ├── InsufficientStockException
│ ├── InsufficientBalanceException
│ └── OrderLimitExceededException
├── EntityNotFoundException(存在条件違反の基底)
│ ├── CustomerNotFoundException
│ ├── ProductNotFoundException
│ └── OrderNotFoundException
└── InvalidStateTransitionException(状態遷移違反の基底)
├── OrderAlreadyCancelledException
├── OrderAlreadyShippedException
└── PaymentAlreadyCompletedException
例外に含める情報
ドメイン例外:
├── メッセージ: ビジネス用語での説明
├── エラーコード: 一意の識別コード(APIレスポンス用)
├── 関連データ: 問題の特定に必要な情報
└── 原因: 根本原因の例外(ある場合)
エラーコードの体系例:
| プレフィックス | 分類 | 例 |
|---|---|---|
ORD- | 注文ドメイン | ORD-001: 在庫不足 |
PAY- | 決済ドメイン | PAY-001: 残高不足 |
USR- | ユーザードメイン | USR-001: 重複登録 |
例外の発生場所
| 場所 | 例外の種類 | 例 |
|---|---|---|
| Value Object コンストラクタ | 不変条件違反 | InvalidEmailFormatException |
| エンティティのメソッド | 状態遷移違反、不変条件違反 | OrderAlreadyCancelledException |
| ドメインサービス | ビジネスルール違反 | InsufficientStockException |
| ファクトリ | 生成条件違反 | InvalidOrderException |
例外の変換戦略
ドメイン例外をアプリケーション層・プレゼンテーション層で適切に変換する。
変換フロー:
ドメイン例外
→ アプリケーション層: ログ出力、イベント発行
→ プレゼンテーション層: HTTPステータスコード + エラーレスポンスに変換
| ドメイン例外 | HTTPステータス | 理由 |
|---|---|---|
| 不変条件違反 | 422 Unprocessable Entity | ビジネスルール違反 |
| 存在条件違反 | 404 Not Found | リソースが存在しない |
| 状態遷移違反 | 409 Conflict | 現在の状態と矛盾 |
| 認可エラー | 403 Forbidden | 権限がない |
アンチパターン
| アンチパターン | 問題 | 対処 |
|---|---|---|
| 汎用例外の多用 | throw new Exception("error") | ドメイン固有の例外を定義する |
| 例外による制御フロー | 正常フローを例外で制御 | 例外は異常系のみに使う |
| 例外の握りつぶし | catch して何もしない | 適切に処理またはリスローする |
| 技術例外の漏洩 | SQLExceptionがドメインまで到達 | インフラ層で変換する |
| 過度な例外階層 | 5段以上のネスト | 2〜3段に抑える |
擬似コード例
examples/ ディレクトリに具体例がある:
examples/exception-hierarchy.pseudo— 例外階層の設計例