Angular 2如何为延迟加载的模块提供单例服务

根据我对Angular 2 rc5的理解,要从另一个模块(不是AppModule)提供服务作为单个模块提供给每个组件,即使是那些延迟加载的模块,我们也不会将该服务包含在该其他模块的providers数组中.我们改为使用RouterModule.forRoot()导出它并将结果导入AppModule

According to the docs

The SharedModule should only provide the UserService when imported by
the root AppModule. The SharedModule.forRoot method helps us meet this
challenge…the SharedModule does not have providers…When we add
the SharedModule to the imports of the AppModule,we call forRoot. In
doing so,the AppModule gains the exported classes and the
SharedModule delivers the singleton UserService provider at the same
time

我真的很挣扎如何为延迟加载的路由提供第三方服务(我的AppModule的导入数组中的模块使用的服务).我无法控制这个第三方模块,因此我不能从该模块的NgModule.providers数组中删除该服务,并将其放在RouterModule.forRoot()中,就像我使用其中一个服务一样.

具体服务是MdIconRegistry,它是Angular Material 2 alpha 7-3的MdIconModule的提供者.此服务用于注册svg图标,然后可以使用< md-icon svgIcon ='iconName'>显示页面上.标签.所以:

>我在我的根AppModule中导入了MdIconModule
>我使用有问题的服务在我的AppComponent中注册svg图标

该图标可见并且运行良好,但仅适用于启动时加载的模块.延迟加载的模块无法看到这些图标,因此我怀疑Angular注入器没有注入MdIconRegistry服务的同一个实例.

tl; dr:我如何从第三方模块使服务可用于我的延迟加载组件?

Here is a plunker that demonstrates the problem(用打字稿编码).

PS:这引起了MdIconModule开发人员on github.的注意

I do not think it has anything to do with the component being lazy-loaded.

LazyLoadedComponent不是AppModule的一部分 – 它是LazyModule的一部分.根据文档,组件只能是一个模块的一部分.如果您也尝试将LazyLoadedComponent添加到AppModule,则会收到相应的错误.所以LazyLoadedComponent甚至根本没有看到MdIconModule.您可以通过查看调试器中的模板输出来确认这一点 – 它保持不变.

<md-icon svgIcon="play"></md-icon>

解决方案似乎是将MdIconModule添加到LazyModule,虽然仅此一项不能解决问题,但它确实会在输出添加错误.

Error retrieving icon: Error: Unable to find icon with the name “:play”

现在模板输出看起来像这样,所以我们知道它正在加载.

<md-icon role="img" svgicon="play" ng-reflect-svg-icon="play" aria-label="play"></md-icon>

我从LazyLoadedComponent添加了对addSvgIconSet的调用,并且它使它工作……所以这证明每个组件有一个MdIconRegistry服务的实例 – 不是你想要的,但可能指向正确的方向.

这是新款 – http://plnkr.co/edit/YDyJYu?p=preview

经过进一步审查,我在docs发现了这个:

Why is a service provided in a lazy loaded module visible only to that module?

Unlike providers of the modules loaded at launch,providers of lazy loaded modules are module-scoped.

最后更新!这是答案.没有为延迟加载的组件正确设置MdIconModule …但是我们可以轻松创建我们自己的模块,该模块已正确设置并使用它.

import { NgModule } from '@angular/core';
import { HttpModule } from '@angular/http';

import { MdIcon } from '@angular2-material/icon';
import { MdIconRegistry } from '@angular2-material/icon';

@NgModule({
  imports: [HttpModule],exports: [MdIcon],declarations: [MdIcon]
})
export class MdIconModuleWithProviders {
  static forRoot(): ModuleWithProviders {
    return {
      ngModule: MdIconModuleWithProviders,providers: [ MdIconRegistry ]
    };
  }
}

Plunk更新并完全正常工作. (对不起,更新了同一个) – > http://plnkr.co/edit/YDyJYu?p=preview

有人可能会提交拉取请求,以便Angular Material导出两种样式的模块.

相关文章

ANGULAR.JS:NG-SELECTANDNG-OPTIONSPS:其实看英文文档比看中...
AngularJS中使用Chart.js制折线图与饼图实例  Chart.js 是...
IE浏览器兼容性后续前言 继续尝试解决IE浏览器兼容性问题,...
Angular实现下拉菜单多选写这篇文章时,引用文章地址如下:h...
在AngularJS应用中集成科大讯飞语音输入功能前言 根据项目...
Angular数据更新不及时问题探讨前言 在修复控制角标正确变...