findxc / blog

88 stars 5 forks source link

RxJS 学习笔记 #88

Open findxc opened 9 months ago

findxc commented 9 months ago

What is RxJS & Why we need RxJS

直接看官方文档的解释: https://rxjs.dev/guide/overview

我的理解: RxJS 是一个针对异步场景的工具库。如果你的项目中异步场景相对复杂,那么你会觉得这个工具好用,值得花时间学习,可以通过 一个 RxJS 实际应用的例子 感受一下。

对于复杂的异步场景,使用 RxJS 更容易写出“高内聚”的代码(更少的变量定义,更集中的逻辑)。

(但是不得不说,用 RxJS 很容易写出 bug ,所以对于复杂异步场景,还有更简洁的解决方案吗?🤔)

实际使用时需要注意的问题

取消订阅

每次写下 .subscribe() 的时候,我们都要想想,需要写对应的 .unsubscribe() 代码吗?更多细节见 RxJS 使用时的取消订阅问题

错误处理

每次写下 .subscribe() 的时候,还需要想想,我们需要做错误处理吗?

比如下面这段代码,每次点击后会去发一个请求。那么,如果某次点击时,刚好这次 API 请求失败了,下一次再点击,还会发请求吗?答案是不会,因为请求失败使得整个 Observable 进入了 error 状态,不会再 next 值了。

fromEvent(this.button.nativeElement, 'click')
  .pipe(switchMap(() => this.http.get('/users')))
  .subscribe()

所以如果希望某次请求的失败不会影响后面的请求,需要加上 catchError 来处理异常,并且请注意这个 catchError 需要加在 this.http.get('/users') 这个 Observable 上才行。

fromEvent(this.button.nativeElement, 'click')
  .pipe(switchMap(() => this.http.get('/users').pipe(catchError(() => of([])))))
  .subscribe()

补充关于 Observable 状态的两个概念:

仔细测试 Observable

比如我们 subscribe 的这个 Observable 什么时候会 next 值,什么时候会 error ,什么时候会 complete ,细节是魔鬼,确认过细节后你才能确定代码的执行是符合你的预期的。

比如 a$.pipe(combineLatestWith(b$)).subscribe(v => console.log(v)) ,如果 a$ next 值了,我们能看到 console 吗?如果 b$ 也 next 值了,我们能看到 console 吗?如果 b$ 又 next 值了,我们能看到 console 吗?以及哪些情况会 error ?

各种 Subject 我应该怎么选

没啥特殊需求就 Subject ;如果希望设置初始值或者希望能直接拿到当前值,那么就用 BehaviorSubject ;如果希望能记录旧值但是不需要设置初始值那就 ReplaySubject ,但是要注意 ReplaySubject 和 Subject 一样不能直接拿到值,只能通过 subscribe 来拿到值。

我现在觉得的最佳实践(也许未来会有不一样想法