커맨드 패턴

강한친구·2022년 4월 11일
0

OOP Desing Pattern

목록 보기
9/15

정의

실행될 기능을 캡슐화 해서 재사용성을 높이는 패턴이다.
커맨드패턴을 이용하면 요구사항대로 객체를 캡슐화 할 수 있으며, 매게변수를 써서 여러가지 다른 요구사항을 집어넣을 수 있다.

커맨드패턴은
명령을 주는 클라이언트
이를 받는 커맨드
이를 세팅하는 인보커
최종적으로 메소드를 호출하는 리시버

로 구성되어 있다.

리시버를 캡슐화할 수 있고, undo를 통해 복구하거나 로그를 남겨 작업을 다시 시도하기가 쉽다.

코드로 보기

출처

클라이언트

package command;

public class RemoteControlTest {
    public static void main(String[] args) {
        SimpleRemoteControl remote = new SimpleRemoteControl();
        Light light = new Light();
        GarageDoor garageDoor = new GarageDoor();
        LightOnCommand lightOn = new LightOnCommand(light);
        GarageDoorOpenCommand garageDoorOpenCommand = new GarageDoorOpenCommand(garageDoor);

        remote.setCommand(lightOn);
        remote.buttonWasPressed();
        remote.setCommand(garageDoorOpenCommand);
        remote.buttonWasPressed();
    }
}

인터페이스

package command;

public interface Command {
    public void execute();
}

인보커

package command;

public class SimpleRemoteControl {
    Command slot;
    public SimpleRemoteControl() {}

    public void setCommand(Command command) {
        slot = command;
    }

    public void buttonWasPressed() {
        slot.execute();
    }
}

커맨드 구현

package command;

public class LightOnCommand implements Command{
    Light light;
    public LightOnCommand(Light light) {
        this.light = light;
    }

    @Override
    public void execute() {
        light.on();
    }
}

리시버

package command;

public class Light {
    void on() {
        System.out.println("Light ON");
    }

    void off() {
        System.out.println("Light OFF");
    }
}

이러한 구성으로 이루어져있다.

클라이언트에서 인보커 LightOnCommand에 lighton을 set하고 이를 실행하면 reciever light클래스의 on메서드가 실행되는 방식이다.

리모컨 통합 API

package command;

import java.util.Arrays;

public class RemoteControl {
    Command[] onCommands;
    Command[] offCommands;

    public RemoteControl() {
        onCommands = new Command[7];
        offCommands = new Command[7];

        Command noCommand = new NoCommand();
        for (int i  = 0; i < 7; i++) {
            onCommands[i] = noCommand;
            offCommands[i] = noCommand;
        }
    }
    public void setCommand(int slot, Command onCommand, Command offCommand) {
        onCommands[slot] = onCommand;
        offCommands[slot] = onCommand;
    }

    public void onButtonWasPushed(int slot) {
        onCommands[slot].execute();
    }
    public void offButtonWasPushed(int slot) {
        offCommands[slot].execute();
    }

    @Override
    public String toString() {
        return "RemoteControl{" +
                "onCommands=" + Arrays.toString(onCommands) +
                ", offCommands=" + Arrays.toString(offCommands) +
                '}';
    }
}

버튼이 7개 있는 오토메이션 기기에 각 버튼마다 command를 지정해주고, 버튼이 눌리면 해당 버튼에 지정된 command의 execute를 실행하는 방식이다.

noCommand
노커맨드는 아무것도 실행하지 않는 커맨드이다.
모든 버튼에 커맨드가 매핑되어야하기에 이러한 커맨드를 사용해서 모든 버튼에 커맨드를 매핑할 수 있다.

커맨드 패턴 활용

요청을 큐에 저장

클라이언트가 생성한 커맨드들을 전부 큐에 저장해놨다가 한참 후에 호출 하는 작업이 가능해진다.
이런 식으로 효율적으로 처리가 가능해진다.

로그 기록

클라이언트의 요청을 로그에 기록해놨다가 장애 발생시 그 로그를 복구해서 장애를 회복할 수 있다.

0개의 댓글