通过DI实现自定义的模式

时间:2017-02-20 14:57:00

标签: angular angular2-di

我正在查看in-memory-web-api的实施,并且有以下代码:

@Injectable()
export class InMemoryBackendService {
  protected config: InMemoryBackendConfigArgs = new InMemoryBackendConfig();
            ^^^^^^
  ...

      constructor(
        @Inject(InMemoryBackendConfig) @Optional() config: InMemoryBackendConfigArgs 
                                                   ^^^^^^
        ) {
        ...

据我所知,模式如下:

  1. 定义的类属性并在不使用DI
  2. 的情况下实例化依赖项
  3. 可选择注入依赖
  4. 如果用户通过DI提供修改后的依赖关系,它将被注入,并且将覆盖没有DI实例化的默认实例。我怀疑在RequestOptions模块中可能与HTTP类似。

    这是一种常见模式吗?

    修改

    事实证明in-memory-web-api并不完全是我所询问的模式。假设,我有一个类A,它使用类B的实例注入令牌B。所以他们都注册了根注入器:

    提供者:[A,B]

    现在,如果用户想要自定义B,他可以在同一令牌下注册自定义版本,从而有效地覆盖原始B

    providers: [{provide:B, useClass: extendedB}]`
    

    这是RequestOptions模块中http的扩展方式。

1 个答案:

答案 0 :(得分:2)

不仅会覆盖默认值。这里的most important part

Object.assign(this.config, config || {})

没有它就什么都不会发生。

此模式并非特定于DI,它是默认属性值的常用配方,类似于_.defaults

我会说InMemoryBackendConfig default implementation在这里是无用的抽象。由于this.config始终与config合并,因此前者可能只是一个普通对象

  protected config: InMemoryBackendConfigArgs = { ... };

InMemoryBackendConfigRequestOptions使用此模式的复杂变体。是的,在大多数基本形式中,这是如何做到的:

providers: [{provide:B, useClass: extendedB}]`

此模式被AngularJS中的constant服务广泛用于配置对象,但将B作为类而不是普通对象允许扩展原始值而不是替换它们。