The Command Design Pattern is a behavioral design pattern that turns a request into a stand-alone object. This object contains all the information about the request, allowing for easier parameterization of clients with different requests, queuing of requests, and logging of the requests. It also supports the undoable operations.
Concept:
-
Command: Represents a request and contains all the necessary information to execute that request. It typically includes an interface with an
execute
method. -
ConcreteCommand: Implements the
Command
interface and binds together a specific command with its corresponding action. - Invoker: Asks the command to execute the request.
- Receiver: Knows how to perform the operation associated with the command.
- Client: Creates a concrete command and associates it with a receiver.
Example:
Let's consider a simple example where we have a light and want to control it using a remote control. We'll implement the Command Pattern to achieve this.
Command Interface:
# Command Interface
class Command
def execute
raise NotImplementedError, 'Subclasses must implement the execute method'
end
end
Concrete Commands:
# Concrete Command: TurnOnCommand
class TurnOnCommand < Command
def initialize(light)
@light = light
end
def execute
@light.turn_on
end
end
# Concrete Command: TurnOffCommand
class TurnOffCommand < Command
def initialize(light)
@light = light
end
def execute
@light.turn_off
end
end
Receiver:
# Receiver: Light
class Light
def turn_on
puts 'Light is ON'
end
def turn_off
puts 'Light is OFF'
end
end
Invoker:
# Invoker: RemoteControl
class RemoteControl
def initialize
@command = nil
end
def set_command(command)
@command = command
end
def press_button
@command.execute if @command
end
end
Client Code:
# Client code using the Command Pattern
light = Light.new
turn_on_command = TurnOnCommand.new(light)
turn_off_command = TurnOffCommand.new(light)
remote = RemoteControl.new
remote.set_command(turn_on_command)
remote.press_button # Outputs: Light is ON
remote.set_command(turn_off_command)
remote.press_button # Outputs: Light is OFF
In this example:
-
Command
is the command interface. -
TurnOnCommand
andTurnOffCommand
are concrete commands, each associated with turning the light on and off. -
Light
is the receiver, which knows how to perform the operations. -
RemoteControl
is the invoker, responsible for executing the command.
This pattern allows you to encapsulate a request as an object, parameterize clients with queues, requests, and operations, and support undoable operations. It's particularly useful in scenarios where you need to decouple senders and receivers of requests.