勉強日記

チラ裏

PoEAA ch15 Remote Facade

martinfowler.com


Remote Facade

Provides a coarse-grained facade on fine-grained objects to improve efficiency over a network.

  • OOPにおいて、複雑なロジックを表現するのは、小さなオブジェクトがよい
    • 利点
      • ふるまいの制御・置換がしやすい
      • 名前をつけてアプリケーションを理解しやすくできる
    • オブジェクト間の多くの相互作用がある
      • 大量のメソッド呼び出し
  • しかし、小さなオブジェクトに対して大量のプロセス間コールを行うと、パフォーマンス上の問題が発生する
    • プロセス間コールは高コスト
      • マーシャリング
      • セキュリティチェック
      • ネットワーク
        • 機器の経由
        • 距離
          • 光速よりは速くならない
    • 同一マシン上でさえ、プロセス内コールよりも桁違いに遅い
  • リモートコール回数を削減するために、リモートコール用オブジェクトはcoarse-grainedでなければならない
  • しかし巨大なオブジェクトでビジネスロジックを記述するのはつらい
  • そこでRemote Facade
    • fine-grainedなオブジェクトを、coarse-grainedなFacadeでラップする
    • fine-grainedなオブジェクトはリモートインタフェースをもたない
    • coarse-grainedなRemote Facadeはビジネスロジックをもたない
      • 裏側のfine-grainedなオブジェクトに処理を委譲

How It Works

  • 複雑なビジネスロジックは、単一メモリ空間上のfine-grainedなオブジェクトの相互作用で表現
  • リモートインタフェースとして、別途Remote Facadeを用意する
    • bulk getter/bulk setter
      • getAddressData()で、cityとstateとzipを一度に取得するなど
  • データをどう通信する
    • 通信路の両端に同じfine-grainedなクラスがデプロイされていれば、単にcopyすればよい
    • そうはいかないこともある
      • ロジックを重複させたくない
    • DTOシリアライズする
  • 1つのRemote Facadeは複数のドメインオブジェクトに対応するのがふつう
    • bulk accessorもそれに見合った名前になる
      • 例: 取引履歴 + 顧客情報
        • getPurchasingHistory
        • updateCreditData
  • Remote Facadeの粒度どうするの問題
    • 人々: usecaseごとに小さめのRemote Facade
    • 著者: 少数の大きなRemoteFacade
      • 中程度のアプリケーションなら1つで済ませることも
      • 大規模でも半ダース程度
      • メソッドは多いが、1つ1つが小さいので問題にならない
        • 【補】たんにfine-grainedなオブジェクトに処理を委譲するだけだから
  • リモートコールのクライアントの必要に応じてRemote Facadeを設計する
    • 最もよくあるのが、UI経由で情報を表示・更新するケース
      • この場合、一連の画面に対して1つのRemote Facade
  • 内部では同じことをするのに、異なる名前で複数のメソッドが生える問題
    • 普通だし理にかなっている
      • Facadeとはシステム内部のためではなく、外部の便利ためのものである
      • 内部で同じことをしていても、外部から見て異なるコマンドなら異なるコマンドなのである
  • stateful/stateless
    • statelessだとプールできる
      • B2Cで特に有効
    • stateが必要なケースもある
      • セッション管理
        • Client Session State
        • Database Session State
        • Server Session State
      • Server-は、何千もの同時アクセスがあるとパフォーマンス問題につながるかも
  • さらなる責務の付与
  • Remote Facade自体にビジネスロジックを乗せてしまうのは間違い
    • ローカルではRemote Facadeを使わずにアプリケーション全体が動作できること
      • 【補】「Facade」が必要不可欠なのはFacadeの定義からいっておかしい
    • ワークフローロジックやドメインオブジェクト間の協調などはよそでやる
      • fine-grained objectsやTransaction Scriptなど

Remote Facade and Session Facade

  • Session Facade
    • J2EEコミュニティ発祥
  • Remote Facadeとは似て非なるもの
    • Remote Facade: 薄い
    • Session Facade: 厚い。ロジック含む
      • 特にワークフローロジック
        • 【所感】Service Layerに似てる
      • Transaction Scriptにリモートインタフェースが生えたものととらえられる
        • それ自体は結構なことだが、Remote Facadeとは異なる
  • ビジネスロジックをもつならFacadeと呼ぶべきではない!!
    • 【補】ビジネスロジックをもつということは、アプリケーションに必要不可欠なクラスだということ
      • FacadeはGoFの定義からして「なくてもいい」もの

Service Layer

  • Remote Facadeと似た概念
  • 相違点
    • Service Layerはリモートインタフェースを持たなくてもよい
    • Service Layerはcoarse-grainedなメソッドだけを持つとは限らない
    • coarse-grainedなメソッドを持つことはあるが、意図が異なる
      • わかりやすさのため
      • cf. Remote Facadeはリモートコールを減らしてパフォーマンス問題を解決するため
      • したがってService LayerにDTOは絡まない
  • Service Layerの上にRemote Facadeを乗っけるのはある
  • リモートコールでしか利用されないならばService LayerとRemote Facadeを合併してもよい
    • Service Layerにアプリケーションロジック(ワークフローロジック)があるならば分ける

When to Use It

  • fine-grainedなオブジェクトへのリモートアクセスがあるとき
    • 最もよくある適用例: リモートのPresentationとDomain Model間
  • 同じ筐体でもプロセス間通信でパフォーマンス問題が生じたら適用
  • 同一プロセス上なら不要
    • Presentation - Domain Model間とか
  • Transaction Scriptと併用することも概してない
    • Transaction Script自体がもともとcoarse-grainedだから
  • 「リモートコールは高コスト」等は同期呼び出しが前提にある
    • 非同期のメッセージベースの通信の優位性には目を見張るものがある
    • 本書の守備範囲外