[swift] Command 디자인 패턴으로 실행할 작업과 수행 주체 분리

Command 디자인 패턴은 객체 지향 소프트웨어 개발에서 커맨드를 요청하는 측과 실제로 작업을 수행하는 객체를 분리하는 데 사용됩니다. 이 패턴은 실행할 작업을 캡슐화하여 실행하고자 하는 대상, 인수 또는 기타 필요한 정보를 캡슐화할 수 있도록 합니다. 또한, Command를 취소하거나 다시 실행하거나 로깅할 수 있게끔 지원하는 기능을 제공합니다.

Command 패턴의 구성 요소

1. Command

실제 작업을 수행하는 객체를 위한 인터페이스를 정의합니다. 이 인터페이스에는 실행 메서드가 포함되어 있습니다.

protocol Command {
    func execute()
}

2. Concrete Command

위에서 정의한 Command 인터페이스를 구현하는 객체입니다. 이 객체는 실제 작업을 실행하는 로직을 포함하고 있습니다.

class ConcreteCommand: Command {
    private let receiver: Receiver
    
    init(receiver: Receiver) {
        self.receiver = receiver
    }
    
    func execute() {
        receiver.performAction()
    }
}

3. Receiver

실제로 작업을 수행하는 객체입니다. Concrete Command가 요청을 수신한 후, Receiver는 해당 작업을 수행합니다.

class Receiver {
    func performAction() {
        // 작업 실행 로직
    }
}

4. Invoker

Command 객체를 보관하고, 요청을 수신하고, 요청에 맞는 Command를 실행합니다.

class Invoker {
    private var commands: [Command] = []
    
    func addCommand(command: Command) {
        commands.append(command)
    }
    
    func executeCommands() {
        for command in commands {
            command.execute()
        }
    }
}

Command 패턴의 활용 예시

Command 패턴은 사용자가 특정 명령을 입력하거나 사용자 인터페이스를 통해 명령을 내릴 때 특히 유용합니다. 또한, 작업을 로깅하거나 취소 및 다시 실행해야 하는 경우에도 Command 패턴을 활용할 수 있습니다.

이런 디자인 패턴을 활용하면 실행할 작업과 수행 주체를 분리함으로써 유연성을 확보할 수 있습니다. 또한, 새로운 명령을 추가하거나 기존 명령을 수정할 때, 기존 코드에 영향을 최소화하는 장점을 얻을 수 있습니다.

참고 문헌: Sourcemaking - Command Pattern


위와 같이 command 디자인 패턴을 활용하면, 코드의 유연함과 유지보수성이 높아지면서 하나의 기능을 여러 곳에서 활용할 수 있습니다. Command 패턴은 객체 간의 결합도를 낮추고, 시스템을 보다 유연하게 만들어주는 강력한 디자인 패턴 중 하나입니다.