Angular2组件无法通过服务中的observable进行通信

时间:2016-03-03 08:15:40

标签: angular typescript rxjs

我正在尝试让组件通过共享服务发送消息,例如cookbook's“父母和孩子通过服务进行通信”。我有一个Sender组件调用服务的方法,在该方法中触发一个事件。并且有一个Receiver组件,它只是监听事件。

问题是Receiver没有收到任何事件。这是代码:

import {bootstrap} from 'angular2/platform/browser'
import {Injectable, Component} from 'angular2/core';

import 'rxjs/Rx';
import {Subject}    from 'rxjs/Subject';

@Injectable()
export class TestService {
    private _subject = new Subject<any>();
    event$ = this._subject.asObservable();

    doFoo() {
        console.log('Doing foo hard...')
        this._subject.next('hey');
    }
}

@Component({
    selector: 'receiver-component',
    template: 'Value is {{ value }}',
    providers: [
        TestService
    ],
})
export class ReceiverComponent {
    private value: number = 'nope';

    constructor(private service: TestService) {
        this.service.event$.subscribe(data => this.value = data)
    }
}

@Component({
    selector: 'sender-component',
    template: '<button (click)="fireEvent()">Click me</button>',
    providers: [
        TestService
    ],
})
export class SenderComponent {
    constructor (private service: TestService) {}

    fireEvent() {
        this.service.doFoo()
    }
}

bootstrap(SenderComponent);
bootstrap(ReceiverComponent);

当我单击按钮时,我会看到来自TestService.doFoo()的调试消息,因此它会被执行。但事件消息并没有通过。为什么呢?

更新:我正在使用angular2@2.0.0-beta.7rxjs@5.0.0-beta.2

1 个答案:

答案 0 :(得分:3)

这不是共享服务。每个组件都有自己的实例。

如果将服务添加到组件的providers列表中,则每个组件都将获得一个新实例。

如果您运行bootstrap()两次,则会创建两个不共享任何内容的不同Angular应用程序。请参阅代码的最后几行,无论如何都要建立连接:

import {bootstrap} from 'angular2/platform/browser'
import {Injectable, Component, provide} from 'angular2/core';

import 'rxjs/Rx';
import {Subject}    from 'rxjs/Subject';

@Injectable()
export class TestService {
    private _subject = new Subject<any>();
    event$ = this._subject.asObservable();

    doFoo() {
        console.log('Doing foo hard...')
        this._subject.next('hey');
    }
}

@Component({
    selector: 'receiver-component',
    template: 'Value is {{ value }}',
//    providers: [
//        TestService
//    ],
})
export class ReceiverComponent {
    private value: number = 'nope';

    constructor(private service: TestService) {
        this.service.event$.subscribe(data => this.value = data)
    }
}

@Component({
    selector: 'sender-component',
    template: '<button (click)="fireEvent()">Click me</button>',
//    providers: [
//        TestService
//    ],
})
export class SenderComponent {
    constructor (private service: TestService) {}

    fireEvent() {
        this.service.doFoo()
    }
}

sharedService = new TestService();
bootstrap(SenderComponent, [provide(TestService, {useValue: sharedService})]);
bootstrap(ReceiverComponent, [provide(TestService, {useValue: sharedService})]);