2016-11-06 6 views
9

私はこの方法で簡単な確認ダイアログサービス(角2)を構築:Subject.complete()はすべてのリスナーを登録解除しますか?

confirm(body?: string, title?: string): Subject<void> { 
    this.confirmation = new Subject<void>(); 
    // ... show dialog here... "are you sure?" 
    return this.confirmation; 
} 

_onYesClicked() { 
    // ... closing the dialog 
    this.confirmation.next(); 
    this.confirmation.complete(); 
} 

_onNoClicked() { 
    // ... closing the dialog 
    this.confirmation.complete(); 
} 

使用法:

confirmationService.confirm().subscribe(() => alert("CONFIRMED")); 

を誰かがサービスを使用している場合、彼は(観察可能である)件名を取得し、返さそれに "subscribe()"することができます。 「はい」をクリックすると、サブスクリプションが呼び出され、確認が行われました...

これは正しい方法ですか?そして、もっと重要な...

this.confirmation.complete(); 

への呼び出しが加入リスナーを解除し、したがって、任意の余韻の参照(メモリリーク)を防ぐことができますか?

+0

'complete()'メソッドがObervableのインターフェースの一部ではないため、タイトルを編集しました。 –

答えて

13

すべてのオブザーバーが削除されていることを確認したい場合は、https://github.com/ReactiveX/rxjs/blob/master/src/Subject.ts#L82でご自身で確認できます。すべてのオブザーバでcomplete()が呼び出されます(オブザーバは通常、Observer interfaceを実装するダムオブジェクトです)。次にthis.observers.length = 0;を設定します。だから答えはイエスです。

あなたのアプローチは有効です。Angular2と基本的に同じですが、EventEmitterで定期的に行います。 Subjectが公開されると、改善できる点はasObservable()を使用することです。これは、あなたがSubjectを使っているという事実を隠し、通常のObservableを返します。このようにして、あなたのユーザーを偶然に(または誤解によって)あなたのSubjectnext()complete()、またはerror()と呼ぶことはできません。

メモリリークに関しては、これはRxJSで処理する必要がありますので、心配する必要はありません。もし問題がある場合は、著者より先に気付くでしょう。

+0

ユーザーがNoをクリックしたときにcomplete()の代わりにerror()を呼び出すか、ObservableではなくPromiseを使用します。これは、ng-bootstrapのモーダルが行うことには至りません。 –

+0

Hehehe ...それは天才だ、ちょうどソースを見て - それは私が確かに参照が保持されていないことを非常に確実に感じさせる。 "asObservable()"についてのアドバイスもあります - ありがとう! – Wolfgang

+0

@JBNizet「いいえ」をクリックしても、必ずしもエラーを意味するわけではありませんが、これはOPの質問ではありません。 – martin

関連する問題