简体   繁体   English

在 RxJS 中,为什么每个订阅都执行一次管道?

[英]In RxJS, why does a pipe get executed once for each subscription?

I want to have multiple subscriptions to react to an observable event, but I want to log the event as well, so I pipe it through a do() operator in which I do the logging.我想有多个订阅来对一个可观察的事件做出反应,但我也想记录该事件,所以我通过一个do()操作符来记录它。

The problem is, the event gets logged once for each of the subscriptions I create!问题是,我创建的每个订阅都会记录一次事件!

I'm getting around this at the moment by creating a Subject and calling next on it from an event callback, which allows me to log the event once and trigger multiple subscriptions as well.我目前正在通过创建一个Subject并从事件回调中调用next解决这个问题,这允许我记录一次事件并触发多个订阅。

Here is some code that demonstrates the issue: https://stackblitz.com/edit/rxjs-xerurd以下是一些演示该问题的代码: https : //stackblitz.com/edit/rxjs-xerurd

I have a feeling I'm missing something, isn't there a more "RxJS" way of doing this?我有一种感觉,我错过了一些东西,难道没有更“RxJS”的方式来做到这一点吗?

EDIT:编辑:

I'm not asking for a difference between hot & cold observable, in fact I was using a hot observable - the one created by fromEvent() and was wondering why does my presumably hot event source behave like it's cold.我不是要求区分热和冷 observable,实际上我使用的是热 observable - 由fromEvent()创建的fromEvent()并且想知道为什么我可能是热的事件源表现得像冷的一样。

I realize now - after reading about share() - that pipe() "turns" your observable cold ie returns a cold one based on the your source (which may be cold, may be hot)我现在意识到 - 在阅读了share() - pipe() “变成”了你可观察到的冷,即根据你的来源返回一个冷的(可能是冷的,可能是热的)

Because Observable sequences are cold by default, each subscription will have a separate set of site effects.因为 Observable 序列默认是冷的,所以每个订阅都会有一组单独的站点效果。

If you want your side effect to be executed only once - you can share subscription by broadcasting a single subscription to multiple subscribers.如果您希望只执行一次副作用 - 您可以通过向多个订阅者广播单个订阅来共享订阅。 To do this you can use share , shareReplay , etc.为此,您可以使用shareshareReplay等。

To better understand how it works, what is "cold" and publish, refer to the RxJS v4 documentation:为了更好地理解它是如何工作的,什么是“冷”和发布,请参阅 RxJS v4 文档:

4.8 Use the publish operator to share side-effects 4.8 使用发布操作符来分享副作用

EDIT : share() is finally working.编辑: share()终于开始工作了。 Please have a look to the comments below.请看看下面的评论。 Thx to @Oles Savluk.感谢@Oles Savluk。

I let my answer below for the records.我让我的回答在下面记录。 It may help.它可能会有所帮助。


share() and multicasting stuffs did not solve my very similar issue. share()和多播的东西并没有解决我非常相似的问题。

Here is how I solved it : https://stackblitz.com/edit/rxjs-dhzisp这是我解决它的方法: https : //stackblitz.com/edit/rxjs-dhzisp

const finalSource = new Subject();
fromEvent(button3, "click").pipe(
  tap(() => {
    console.log("this happens only once")
  }) 
).subscribe(() => finalSource.next())

finalSource.subscribe(
  () => console.log("first final subscription")
)

finalSource.subscribe(
  () => console.log("second final subscription")
)

finalSource.subscribe(
  () => console.log("third final subscription")
)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM