如何在两个模块之间共享服务 - @NgModule在角度之间而不是在组件之间?

Ani*_*Das 38 angular2-services angular2-modules angular

在我的应用程序中,我有两个不同的bootstrap模块(@NgModule)在一个应用程序中独立运行.没有一个角度app位单独的bootstrap模块,现在我希望他们应该相互通信并共享数据.

我知道通过@Injectable服务作为模块中的提供者,我可以在所有组件下共享数据,@NgModule但是我将如何在两个不同模块(不是模块内部组件)之间共享数据.

有没有办法在另一个模块中访问一个服务对象?有没有办法可以访问浏览器内存中可用的服务对象并在我的其他角度模块中使用它?

Fac*_*nda 49

根据Angular 2的最终版本,模块提供的服务可用于导入它的每个其他模块.在官方风格指南建议,应用范围的服务,这是要在应用程序中的任何地方重复使用(单身)应该被某些人提供Core Module,即在主需要进口App Module,因此将注射无处不在.

如果您不使用涉及具有共享单例的核心模块的结构,并且您要独立开发两个NgModule,并且您希望其中一个服务在另一个中使用,那么唯一的解决方案是将提供程序导入另一个 :

这是提供者模块:

/// some.module.ts
import { NgModule } from '@angular/core';

import { SomeComponent }   from './some.component';

@NgModule({
    imports: [],
    exports: [],
    declarations: [SomeComponent],
    providers: [ MyService ], // <======================= PROVIDE THE SERVICE
})
export class SomeModule { }
Run Code Online (Sandbox Code Playgroud)

这是另一个想要使用的模块 MyService

/// some-other.module.ts
import { NgModule } from '@angular/core';

import { SomeModule } from 'path/to/some.module'; // <=== IMPORT THE JSMODULE

import { SomeOtherComponent }   from './some.other.component';

@NgModule({
    imports: [ SomeModule ], // <======================== IMPORT THE NG MODULE
    exports: [],
    declarations: [SomeOtherComponent],
    providers: [],
})
export class SomeOtherModule { }
Run Code Online (Sandbox Code Playgroud)

这样,服务应该可以在任何组件SomeOtherModule声明中注入,而在SomeModule本身 - 只需在构造函数中请求它:

/// some-other.module.ts

import { MyService } from 'path/to/some.module/my-service';

/* ...
    rest of the module
*/

export class SomeOtherModule {
    constructor( private _myService: MyService) { <====== INJECT THE SERVICE
        this._myService.dosmth();
    }
}
Run Code Online (Sandbox Code Playgroud)

如果这不能回答你的问题,我邀请你重新制定它.

  • 这个答案真的适用于单独的自举模块吗?我试过了,但它对我不起作用.仅当在模块内的组件中使用共享服务时,它才有效. (3认同)
  • 这行不通。它为每个服务创建两个实例,因此您并不是真正共享服务...在这里看看:/sf/answers/3237025711/ (3认同)

Hag*_*Aly 16

  1. 创建共享模块

    __CODE__

  2. 在app模块中,您的父app模块会像这样导入共享模块

    __CODE__

  3. 任何子模块如果你需要导入共享模块导入它而不用for root

    __CODE__

https://angular-2-training-book.rangle.io/handout/modules/shared-modules-di.html


Gün*_*uer 9

您可以在Angular之外实例化一个服务并提供一个值:

class SharedService {
  ...
}
Run Code Online (Sandbox Code Playgroud)
window.sharedService = new SharedService();

@NgModule({
  providers: [{provide: SharedService, useValue: window.sharedService}],
  ...
})
class AppModule1 {}

@NgModule({
  providers: [{provide: SharedService, useValue: window.sharedService}],
  ...
})
class AppModule2 {}
Run Code Online (Sandbox Code Playgroud)

如果一个应用程序更改状态SharedService或调用导致Observable发出值的方法,并且订户与发射器位于不同的应用程序中,则订户中的代码将在发射器中执行NgZone.

因此在订阅SharedService使用中的观察时

class MyComponent {
  constructor(private zone:NgZone, private sharedService:SharedService) {
    sharedService.someObservable.subscribe(data => this.zone.run(() => {
      // event handler code here
    }));
  }
}
Run Code Online (Sandbox Code Playgroud)

另请参见如何动态创建自举模式作为Angular2组件?

  • 这可能有用,但它不是一个优雅的解决方案.正确的方法是为Root()实现静态方法并返回服务的唯一实例.看看这里:/sf/answers/3237025711/ (3认同)
  • 此外,在执行`... .subscribe(data => this.zone.run()=> {//事件处理程序代码})`时,是否存在语法错误,因为我不明白它是如何工作的? (2认同)