2

我们正在使用 Backbone 创建可重用的组件。我们创建控制器是为了设置模型和视图之间的绑定。我们希望为人们提供用他们自己的实现替换模型和视图的能力。

由于大多数人将使用我们提供的组件,我不想强​​迫开发人员配置或创建任何与默认设置没有区别的东西。

这意味着某人应该能够将他们想要用作模型或视图的对象的实例传递给控制器​​,所有配置和设置并准备就绪,或者他们可以将一些配置传递给控制器​​将使用的内容默认。

我不确定最好的方法是什么。

// Idea #1
var controller = new Controller({
    dependencyA: {
         conf: { // config for depedencyA }
    },
    dependencyB: {
         conf: { // config for dependencyB }
         class: custom.implement.Class
    }
});

在这种方法中,用户无法控制如何实例化对象。这样做的坏处是,例如,Backbone 模型在构造函数中采用两个参数,而视图只采用一个。

// Idea #2
var controller = new Controller({
    dependencyA: {
        args: ['arg1',{
            opt1: 'opt-value',
        }]
    },
    dependencyB: {
        args: ['a','b','c']
        class: custom.implement.Class
    }
});

Args 将是传递给构造函数的参数。这意味着控制器使用 args 数组调用构造函数,并且如果您传递默认依赖项的自定义配置,这只会对您真正有益。如果您想通过自己的实现,那就更尴尬了。

// Idea #3  
var controller = new Controller({
    dependencyA: new outOfBoxModel({ // configuration }),
    dependencyB: new custom.imeplement.Class('a','b','c')
});

在这种方法中,用户被迫实例化开箱即用的模型。如果模型的默认设置都是合适的,那么用户正在做不必要的工作。他们唯一要做的就是创建一个他们自己的自定义实现的实例。

我不确定这里最好的方法是什么?

4

1 回答 1

2

在这三种方法中,我最喜欢方法 3。原因如下:

  1. 它比其他方法更一致。在第 3 种方法中,用户只需学习将构造的依赖关系实例传递给控制器​​。在其他方法中,用户必须传入 args 或 args 和类名。
  2. 它不违反单一职责原则。在前两种方法中,您的控制器负责构建和配置其依赖项。这根本不像依赖注入!我认为将依赖项的构建留给用户或应用程序的其他部分会更好、更简单。在我看来,强迫用户构建他们自己的实现并不是一件可怕的事情——它让他们可以自由地定义他们想要的构造函数,而不是强迫你为Controllers依赖项定义和维护构造函数 API,并强迫用户以符合他们。

一个不同的想法:

如果您在应用程序中有这种自由,我会考虑将您的Controller构造逻辑放在工厂类或方法中:

var createController = function(config) {
  // Parse, validate, extract relevant config items
  // var a = create dependency a
  // var b = create dependency b
  return new Controller(a, b);
}

这种方法使您可以随心所欲地定义您的定义config-您可以支持您在原始帖子中提供的所有三个配置定义-尽管我不建议这样做:-)。至少,我会让工厂方法支持零参数调用(在这种情况下,它将返回 的默认构造Controller)和您首选的配置定义之一。

于 2013-06-09T17:32:39.993 回答