📄
概念 📚 software-design-concepts

アーキテクチャスタイル

モノリス・マイクロサービス・サーバーレスなど主要なアーキテクチャスタイルの特徴とトレードオフ

アーキテクチャスタイルとは、システム全体の構造を決定する設計上の判断の集合体である。どのスタイルを選ぶかは、チームの規模・ドメインの複雑さ・スケール要件・デプロイ頻度など複数の文脈に依存する。正解は一つではなく、常にトレードオフの選択となる。

代表的なスタイルとして、レイヤードアーキテクチャ(Presentation → Application → Domain → Infrastructure)は理解しやすく多くのフレームワークに採用されているが、依存が一方向に流れるよう設計しないと上位層が下位層に強く結合してしまう。クリーンアーキテクチャやヘキサゴナルアーキテクチャは、依存性逆転原則(DIP)を徹底してドメインをインフラから保護する。いずれもポートとアダプターの考え方でテスタビリティを高める。

マイクロサービスは各サービスが独立してデプロイ・スケールできる反面、分散システムの複雑さ(ネットワーク遅延・障害伝播・分散トレーシング)を引き受ける必要がある。モノリスは単純さと一貫性のトランザクションを強みとするが、コードベースが肥大化するとデプロイリスクが増大する。サーバーレスはイベント単位の課金とスケールゼロが魅力だが、コールドスタートや実行時間制限が設計制約になる。CAP定理(一貫性・可用性・分断耐性のうち2つしか保証できない)は、分散スタイルを採用する際に常に念頭に置くべき根本的な制約である。

コードレビューで着目するポイント

  • レイヤー間の依存方向が定義した設計と一致しているか(上位層が下位層の具象に依存していないか)
  • ドメインロジックがインフラ層(DB・HTTP・外部API)の詳細に汚染されていないか
  • マイクロサービス間の通信がサービス境界を正しく尊重しているか(他サービスのDBに直接アクセスしていないか)
  • 同期通信と非同期通信の使い分けが適切か(強い一貫性が必要な箇所に非同期を使っていないか)
  • スタイルの変更(モノリスからマイクロサービスへの移行など)が段階的に行われているか
  • 凝集度の高い単位でモジュールが分割されているか(無関係な責務が一つのサービスに詰め込まれていないか)
  • 共有ライブラリや共有DBによる暗黙的な結合が生じていないか

典型的なアンチパターン

分散モノリス(Distributed Monolith): マイクロサービスに分割したはずが、サービス間で同期的なAPIコールが連鎖し、一箇所の変更が全サービスの同時デプロイを必要とする状態。物理的に分離されているだけでロジック上は密結合のまま。

レイヤー越え(Layer Bypass): Controller がリポジトリを直接呼び出したり、インフラ層のコードがドメインオブジェクトを生成したりして、レイヤーの意図する保護が機能しなくなる状態。

過早なマイクロサービス化: ドメイン境界が未成熟な段階でサービス分割を行い、後から境界の再定義が必要になって大量のAPIリファクタリングが発生するケース。

参考リソース