Mediator Design Pattern

In Complex Systems, objects communicate with each other directly or notify all. one way is to create individual relations for each object with another which will make the code tightly coupled, another way is to create a layer between objects which will act as a mediator, all the communication will pass through it to the intended receiver.
Mediator Design Pattern promotes loose coupling, now all the different parts communicate with each other but are not dependent.

Mediator Design Pattern provides a loosely coupled mechanism where different objects independently interact and communicate with one another.

Mediator Design Pattern reduces communication complexity between individual components and maintains centralized control. it acts like a many-to-one relationship network.
Some real-world examples of Mediator Design Pattern are

  • Electronic systems have Central Processing Unit, which decides the operation based on buttons pressed or instructions. each component is communicating via Central Processing Unit and sends or receives instructions from it.
  • Traffic police managing traffic in the middle of an intersection work as a mediator and each vehicle instead of talking to each other talks to traffic police, and then the instruction is communicated to others.
  • Pilots flying helicopters, airplanes, or jets require airstrips to land and take off. each pilot doesn't talk to another pilot instead an Air Trafic Control acts as a mediator, each pilot will be talking to ATC and ATC will manage the execution. the same logic applies to train stations as well.
  • All chat systems, have a Centralized Message Processing system, which controls and manages the communication flow, receives messages, passes them to the receiver, and broadcasts them to a group.
package org.wesome.design.patterns;

public interface Restaurant {
    void directMessage(String message, KitchenStaff sender, KitchenStaff receiver);

    void groupMessage(String message, KitchenStaff sender);

    void addKitchenStaff(KitchenStaff kitchenStaff);
}
package org.wesome.design.patterns;

import java.util.ArrayList;
import java.util.List;

public class RestaurantImpl implements Restaurant {
    private final List<KitchenStaff> kitchenStaffs;

    public RestaurantImpl() {
        this.kitchenStaffs = new ArrayList<>();
    }

    @Override
    public void addKitchenStaff(KitchenStaff kitchenStaff) {
        this.kitchenStaffs.add(kitchenStaff);
    }

    @Override
    public void directMessage(String message, KitchenStaff sender, KitchenStaff receiver) {
        receiver.receiveMessage(message);
    }

    @Override
    public void groupMessage(String message, KitchenStaff sender) {
        /*  make sure the sender should not receive the same message   */
        kitchenStaffs.stream().filter(kitchenStaff -> kitchenStaff != sender).forEach(kitchenStaff -> kitchenStaff.receiveMessage(message));
    }
}
package org.wesome.design.patterns;

public abstract class KitchenStaff {
    protected Restaurant restaurantMediator;
    protected String staffName;

    public KitchenStaff(Restaurant restaurantMediator, String staffName) {
        this.restaurantMediator = restaurantMediator;
        this.staffName = staffName;
    }

    public abstract void directMessage(String message, KitchenStaff receiver);

    public abstract void groupMessage(String message);

    public abstract void receiveMessage(String message);
}
package org.wesome.design.patterns;

public class KitchenStaffImpl extends KitchenStaff {
    public KitchenStaffImpl(Restaurant med, String name) {
        super(med, name);
    }

    @Override
    public void directMessage(String message, KitchenStaff receiver) {
        System.out.println(System.lineSeparator() + this.staffName + " to " + receiver.staffName + " -> " + message);
        restaurantMediator.directMessage(message, this, receiver);
    }

    @Override
    public void groupMessage(String message) {
        System.out.println(System.lineSeparator() + this.staffName + " to all -> " + message);
        restaurantMediator.groupMessage(message, this);
    }

    @Override
    public void receiveMessage(String message) {
        System.out.println(this.staffName + " received <- " + message);
    }
}
package org.wesome.design.patterns;

public class Mediator {

    public static void main(String[] args) {
        Restaurant mediator = new RestaurantImpl();
        KitchenStaff restaurantOwner = new KitchenStaffImpl(mediator, "James");
        KitchenStaff liam = new KitchenStaffImpl(mediator, "Liam");
        KitchenStaff oliver = new KitchenStaffImpl(mediator, "Oliver");
        mediator.addKitchenStaff(restaurantOwner);
        mediator.addKitchenStaff(liam);
        mediator.addKitchenStaff(oliver);

        restaurantOwner.groupMessage("Hi All, All the guest have arrived, we have multiple orders");

        restaurantOwner.directMessage("Hi Liam, you will be preparing Apple Crumble", liam);
        liam.directMessage("sure James", restaurantOwner);

        restaurantOwner.directMessage("Hi Oliver, you will be preparing Apple Pie", oliver);
        oliver.directMessage("ok  James", restaurantOwner);
    }
}
plugins {
    id 'java'
    id "io.freefair.lombok" version "6.2.0"
}

group = 'org.wesome'
version = '0.0.1-SNAPSHOT'
sourceCompatibility = JavaVersion.VERSION_1_8

configurations {
    compileOnly {
        extendsFrom annotationProcessor
    }
}
repositories {
    mavenCentral()
}

dependencies {
    implementation 'org.junit.jupiter:junit-jupiter:5.6.2'
}

test {
    useJUnitPlatform()
}

 

follow us on