最终可以观察到订阅


105

根据该条款onComplete和的onError功能subscribe是互斥的。

表示onErroronComplete事件会在我的网站上触发subscribe
我有一个逻辑块,无论收到错误还是成功完成信息准备工作,都需要执行该逻辑块。

finally在python中寻找了类似的东西,但是我发现的只是finally需要附加到我创建的可观察对象上。

但是我只想在订阅时以及流结束后(无论成功还是出错)执行该逻辑。

有任何想法吗?

Answers:


130

调用此运算符的当前“可点入”变体finalize()(自RxJS 6起)。调用了较旧且现在不推荐使用的“补丁”运算符finally()(直到RxJS 5.5)。

我认为finalize()运算符实际上是正确的。你说:

仅在我订阅时以及流结束后才执行该逻辑

我认为这不是问题。如果需要,您可以拥有一个sourcefinalize()在订阅前使用。这样,您就不必始终使用finalize()

let source = new Observable(observer => {
  observer.next(1);
  observer.error('error message');
  observer.next(3);
  observer.complete();
}).pipe(
  publish(),
);

source.pipe(
  finalize(() => console.log('Finally callback')),
).subscribe(
  value => console.log('#1 Next:', value),
  error => console.log('#1 Error:', error),
  () => console.log('#1 Complete')
);

source.subscribe(
  value => console.log('#2 Next:', value),
  error => console.log('#2 Error:', error),
  () => console.log('#2 Complete')
);

source.connect();

打印到控制台:

#1 Next: 1
#2 Next: 1
#1 Error: error message
Finally callback
#2 Error: error message

2019年1月:已针对RxJS 6更新


1
有趣的是,这与Promises的相反模式有关,因为该finally()方法首先被附加,并且订阅强制地强制通过/失败。
BradGreens

7
是的,那太糟糕了。有人会认为该finally块将在您的代码中排在最后。
d512

我喜欢Angular JS的Promise系统...正如d512所说,我希望“最终”是最后一个...一点都不喜欢……
Sampgun

10
从RXJS 5.5开始,“最终”不再是一种可观察的方法。使用“ finalize”运算符代替:source.pipe(finalize(()=> console.log('Finally callback')))。subscribe(...); github.com/ReactiveX/rxjs/blob/master/doc/pipeable-operators.md
Stevethemacguy,

finalize的问题是它等待“ complete()”调用。如果您希望在每次发射上都最终得到一个结果(如果可观察到的发射成功,那么做a,如果它出错了,那么用b代替..在两种情况下都做c)?
robertotomás

64

唯一对我有用的是

fetchData()
  .subscribe(
    (data) => {
       //Called when success
     },
    (error) => {
       //Called when error
    }
  ).add(() => {
       //Called when operation is complete (both success and error)
  });

26

我现在在Angular应用程序中使用RxJS 5.5.7,并且finalize对于我的用例,using 运算符具有怪异的行为,因为它在成功或错误回调之前被触发。

简单的例子:

// Simulate an AJAX callback...
of(null)
  .pipe(
    delay(2000),
    finalize(() => {
      // Do some work after complete...
      console.log('Finalize method executed before "Data available" (or error thrown)');
    })
  )
  .subscribe(
      response => {
        console.log('Data available.');
      },
      err => {
        console.error(err);
      }
  );

我必须使用add订阅中的方法来完成我想要的。基本上是finally成功或错误回调完成后的回调。像try..catch..finally块或Promise.finally方法。

简单的例子:

// Simulate an AJAX callback...
of(null)
  .pipe(
    delay(2000)
  )
  .subscribe(
      response => {
        console.log('Data available.');
      },
      err => {
        console.error(err);
      }
  );
  .add(() => {
    // Do some work after complete...
    console.log('At this point the success or error callbacks has been completed.');
  });

很高兴为您提供帮助。
pcasme'1
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.