使用 forRoot 传递配置数据

Posted

技术标签:

【中文标题】使用 forRoot 传递配置数据【英文标题】:Pass config data using forRoot 【发布时间】:2017-09-03 16:40:11 【问题描述】:

我正在尝试将配置数据传递到 Angular 中的自定义库中。

在用户应用程序中,他们会使用forRoot将一些配置数据传递给我的库

// Import custom library
import  SampleModule, SampleService  from 'custom-library';
...

// User provides their config
const CustomConfig = 
  url: 'some_value',
  key: 'some_value',
  secret: 'some_value',
  API: 'some_value'
  version: 'some_value'
;

@NgModule(
  declarations: [...],
  imports: [
    // User config passed in here
    SampleModule.forRoot(CustomConfig),
    ...
  ],
  providers: [
    SampleService
  ]
)
export class AppModule 

在我的自定义库中,特别是index.ts,我可以访问配置数据:

import  NgModule, ModuleWithProviders  from '@angular/core';
import  SampleService  from './src/sample.service';
...

@NgModule(
  imports: [
    CommonModule
  ],
  declarations: [...],
  exports: [...]
)
export class SampleModule 
  static forRoot(config: CustomConfig): ModuleWithProviders 
    // User config get logged here
    console.log(config);
    return 
      ngModule: SampleModule,
      providers: [SampleService]
    ;
  

我的问题是如何让自定义库的SampleService中的配置数据可用

目前SampleService 包含以下内容:

@Injectable()
export class SampleService 

  foo: any;

  constructor() 
    this.foo = ThirdParyAPI(/* I need the config object here */);
  

  Fetch(itemType:string): Promise<any> 
    return this.foo.get(itemType);
   

我已经阅读了 Providers 上的文档,但是 forRoot 的示例非常少,似乎没有涵盖我的用例。

【问题讨论】:

您能否将地图传递给您的自定义配置?像这样 myMap: Map;我正在尝试传递地图,但如果我打开 AOT (ng serve --AOT) 则它不起作用 【参考方案1】:

您快到了,只需在您的模块中同时提供SampleServiceconfig,如下所示:

export class SampleModule 
  static forRoot(config: CustomConfig): ModuleWithProviders<SampleModule> 
    // User config get logged here
    console.log(config);
    return 
      ngModule: SampleModule,
      providers: [SampleService, provide: 'config', useValue: config]
    ;
  

@Injectable()
export class SampleService 

  foo: string;

  constructor(@Inject('config') private config:CustomConfig) 
    this.foo = ThirdParyAPI( config );
  

更新

由于 Angular 7 ModuleWithProviders 是通用的,所以它需要 ModuleWithProviders&lt;SampleService&gt;

【讨论】:

很好的答案!我通常使用它,但我更喜欢使用 OpaqueToken(InjectionToken) 而不是 string 谢谢:)。我觉得OpaqueToken 解释起来太麻烦了,但你当然是对的。这是首选方式。现在其实是InjectionTokenangular.io/docs/ts/latest/api/core/index/… Not 使用InjectionToken实际上说明了注射器的灵活性。它还演示了非常有用的@Inject(dep) 模式的用法。 @AluanHaddad 这只是自行车:D,我不认为你的例子更好。 @Injectable() 标记一个类以使其可注入,因此名称还不错。 如果有嵌套模块,我该如何传递配置?我的意思是我不能在 AppModule 中使用:imports: [ModuleA.forRoot(parentConfig)],然后在 ModuleA 中有 imports: [ModuleB.forRoot(parentConfig.childConfig)]

以上是关于使用 forRoot 传递配置数据的主要内容,如果未能解决你的问题,请参考以下文章

如何将标题传递给ngx-logger(serverlURL)的post方法?

ionic3 隐藏子页面tabs

StoreModule.forRoot() 和 StoreModule.forFeature() 有啥区别

ionic2的返回按钮的编辑问题

ngrx StoreModule.forRoot 命名约定

StoreModule.forRoot() - 如何在没有附加键的情况下返回对象