javaScript设计模式-命令模式

Command(命令)模式

Command 模式旨在将方法调用、请求或操作封装到单一对象中,从而根据我们不同的请求对客户进行参数化和传递可供执行的方法调用。

Command 模式背后的主要思想是:它为我们提供了一种分离职责的手段,这些职责包括从执行命令的任意地方发布命令以及将该职责转而委托给不同对象。

实施明智的、简单的命令对象把 action 动作和调用该动作的对象绑定在一起。它们始终包括一个执行操作。所有具有相同接口的 Command 对象可以根据需要轻松交换,这被认为是该模式的一个更大好处。

这里是一个简单的汽车购买服务

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
(function(){

var CarManager = {

// 请求信息
requestInfo: function(model, id) {
return "The information fro " + model + " with ID" + id + " is foobar";
},

// 订购汽车
buyVehicle: function(model, id) {
return "You have successfully purchased Item" + id + ", a " + model;
},

// 组织一个view
arrangeViewing: function(model, id) {
arrangeViewing: function(model, id) {
return "You have successfully booked a viewing of " + model + "("+id+")";
}
},


};
})()

上面的代码,它可以通过直接访问对象轻松地调用我们的的CarManager方法。从技术上讲,它是完全有效的JavaScript。然而,它在有些情况下可能是不利的。

如果CarManager里的核心API改变了会怎么样? 这将要求程序里所有直接访问这些方法的对象都需要进行修改。这可能被视为一个耦合层,它实际上最大程度地违反了松耦合对象的OOP方法论。我们可以进一步抽象API来解决这个问题。

现在让我们来扩展CarManager,这样Command模式下的应用程序会产生如下结果:接受任意可以在CarManager对象上执行的命名方法,传递可以使用的任意数据,如CarModel(模型)和ID

这时我们希望能够实现的内容: CarManager.execute("buyVehicle", "Food Escort", "453543");

按照这个结构,我们现在应该为CarManager.execute方法添加一个定义,如下所示:

1
2
3
CarManager.execute = function(name) {
return CarManager[name] && CarManager[name].apply(CarManager, [].slice.call(arguments, 1));
};

最终的示例调用看起来时这样的:

1
2
3
4
CarManager.execute("arrangerViewing", "Ferrari", "14523");
CarManager.execute("requestInfo", "Ford Mondeo", "54323");
CarManager.execute("requestInfo", "Ford Escort", "322232");
CarManager.execute("buyVehicle", "Ford Eecort", "223343");