0
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Pythonで実装するMediatorパターン:オブジェクト間通信を中央集約する調停者設計

Posted at

概要

Mediator(メディエーター)パターンは、
多くのオブジェクトが相互に複雑に通信する構造を、調停者(Mediator)を介して整理・集約する設計パターンである。

各オブジェクトはMediatorを通じて他者と連携し、直接の依存を持たない疎結合な設計を実現
イベントのハブ、GUIコンポーネント、チャット、フォームバリデーションなどに活用される。


1. なぜMediatorが必要か?

❌ 各コンポーネントが互いに直接参照しあうと、依存関係がスパゲッティ化

class Button:
    def on_click(self):
        textbox.clear()
        dialog.hide()

関係が密結合になり、変更が波及・再利用が困難


✅ Mediatorにイベント制御を集中させることで、各コンポーネントは単純化

class Button:
    def on_click(self):
        mediator.notify(self, "click")

各オブジェクトはMediatorだけを知り、連携はMediatorが制御


2. 基本構造

✅ Mediatorインターフェース

class Mediator:
    def notify(self, sender, event):
        raise NotImplementedError

✅ Colleague(参加者の共通ベース)

class Component:
    def __init__(self, mediator: Mediator):
        self.mediator = mediator

✅ 各コンポーネント(Colleague)

class Button(Component):
    def click(self):
        print("[Button] クリックされました")
        self.mediator.notify(self, "click")

class TextBox(Component):
    def clear(self):
        print("[TextBox] テキストをクリア")

class Dialog(Component):
    def hide(self):
        print("[Dialog] 非表示にしました")

✅ ConcreteMediator(調停ロジック)

class UIControlMediator(Mediator):
    def __init__(self):
        self.button = None
        self.textbox = None
        self.dialog = None

    def notify(self, sender, event):
        if sender == self.button and event == "click":
            self.textbox.clear()
            self.dialog.hide()

✅ 使用例

mediator = UIControlMediator()

btn = Button(mediator)
txt = TextBox(mediator)
dlg = Dialog(mediator)

mediator.button = btn
mediator.textbox = txt
mediator.dialog = dlg

btn.click()

出力:

[Button] クリックされました  
[TextBox] テキストをクリア  
[Dialog] 非表示にしました

3. Python的応用:イベントルータとしての汎用Mediator

class EventMediator:
    def __init__(self):
        self.handlers = {}

    def register(self, event, handler):
        self.handlers[event] = handler

    def emit(self, event, *args):
        if event in self.handlers:
            self.handlers[event](*args)

# 使用例
em = EventMediator()
em.register("save", lambda: print("保存処理"))
em.register("cancel", lambda: print("キャンセル処理"))

em.emit("save")    # 保存処理
em.emit("cancel")  # キャンセル処理

Pythonの柔軟さを活かした、軽量なMediator実装も可能


4. 実務ユースケース

✅ GUIフォームの部品連携制御

入力変更に応じて他部品の状態を動的に制御


✅ チャットシステムの中央集約ハブ

ユーザー間の通信を一元管理


✅ IoTセンサとコントローラのイベント連携

センシングとアクションの分離設計を実現


✅ サーバ・クライアント間のメッセージルーティング

役割別の通知・命令を中央で制御


5. よくある誤用と対策

❌ Mediatorが巨大化し、神クラスになる

→ ✅ 機能ごとにMediatorを分割、責任を明確化する


❌ Mediatorを使ってもColleagueが他者に依存してしまう

→ ✅ 全ての連携はMediator経由とし、直接参照は避ける


❌ Mediatorの存在がUIやロジックに露出しすぎる

→ ✅ 依存性注入や隠蔽でMediatorを内部ロジックに閉じ込める


結語

Mediatorパターンとは、“複数オブジェクトの関係性を中央に集約し、構造を制御する調停者設計”である。

  • オブジェクト間通信を疎結合に変換し、構造の柔軟性と拡張性を保つ
  • GUI・ネットワーク・リアクティブシステムなどにおいて、中心的なイベント管理が可能
  • Pythonでは動的なイベント分配や軽量ルータ構造で、Mediatorの力を最大限に活かせる

Pythonicとは、“対話は直接せず、調停者を通して統制すること”。
Mediatorパターンはその関係性の知性を、設計の集約性として表現する技法である。

0
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?