๐ง What Is the Mediator Pattern?
The Mediator Pattern is a behavioral design pattern that promotes loose coupling by centralizing complex communication between objects into a single mediator. Instead of having components refer to each other directly, they interact through a mediator, making the system easier to manage and extend.
๐ When to Use It
Use the Mediator Pattern when:
Multiple objects interact in complex ways
You want to avoid tightly coupled code with lots of interdependencies
Adding or modifying interactions between classes is becoming error-prone
You need better control over how objects communicate
Common scenarios:
UI components (buttons, text boxes, dialogs)
Chat applications
Workflow engines or pipelines
Microservices communication management
๐ ๏ธ How It Works
The Mediator Pattern includes:
A Mediator Interface that defines communication methods
A ConcreteMediator that implements coordination logic
Colleague Classes that interact via the mediator
C# Example: Chat Room Mediator
// Mediator interface
public interface IChatRoomMediator
{
void SendMessage(string message, User sender);
}
// Concrete Mediator
public class ChatRoom : IChatRoomMediator
{
private List<User> _users = new List<User>();
public void Register(User user)
{
_users.Add(user);
user.SetChatRoom(this);
}
public void SendMessage(string message, User sender)
{
foreach (var user in _users)
{
if (user != sender)
{
user.Receive(message, sender.Name);
}
}
}
}
// Colleague
public class User
{
public string Name { get; }
private IChatRoomMediator _chatRoom;
public User(string name)
{
Name = name;
}
public void SetChatRoom(IChatRoomMediator chatRoom)
{
_chatRoom = chatRoom;
}
public void Send(string message)
{
_chatRoom.SendMessage(message, this);
}
public void Receive(string message, string sender)
{
Console.WriteLine($"{Name} received from {sender}: {message}");
}
}
Usage
var chatRoom = new ChatRoom();
var alice = new User("Alice");
var bob = new User("Bob");
var charlie = new User("Charlie");
chatRoom.Register(alice);
chatRoom.Register(bob);
chatRoom.Register(charlie);
alice.Send("Hello, everyone!");
โ๏ธ Pros and Cons
โ Pros
Centralizes control over communication logic
Promotes loose coupling between components
Makes components easier to reuse and maintain
Simplifies complex interaction networks
โ Cons
Mediator can become a monolithic god object if overused
Increases the number of classes
May require careful planning to keep the mediator lightweight
๐งช Testing Benefits
You can test the mediator independently from the colleagues
Each component can be tested in isolation
Easy to mock or replace the mediator for unit tests
Test communication rules in a single place
๐ Real-World Use Cases
UI Frameworks: Dialogs managing buttons, input fields and menus
Air Traffic Control Systems: All planes report to a central controller, not to each other
Chat Applications: Central chatroom or server distributes messages to users
Workflow Engines: Steps of a process communicate through a central coordinator
๐ Related Patterns
Observer: Allows broadcast-style communication to multiple listeners but without coordination
Command: Encapsulates requests but does not handle interaction between components
Facade: Simplifies access to a complex subsystem but does not coordinate interaction like a mediator
๐ Final Thoughts
The Mediator Pattern is your go-to solution when your system is turning into a spaghetti mess of interconnected objects. It provides a clean way to control communication, reduce dependencies and promote maintainability. When used properly, the mediator becomes the hub that keeps your components both simple and powerful.