1 直接执行/转换
用于from
直接将先前创建的 Promise 转换为 Observable。
import { from } from 'rxjs';
// getPromise() is called once, the promise is passed to the Observable
const observable$ = from(getPromise());
observable$
将成为一个热门的 Observable,它可以有效地向订阅者重放 Promise 值。
它是一个热门的 Observable,因为生产者(在本例中为 Promise)是在 Observable 外部创建的。多个订阅者将共享同一个 Promise。如果内部 Promise 已得到解决,Observable 的新订阅者将立即获得其值。
2 每个订阅的延迟执行
使用defer
Promise 工厂函数作为输入,以推迟 Promise 到 Observable 的创建和转换。
import { defer } from 'rxjs';
// getPromise() is called every time someone subscribes to the observable$
const observable$ = defer(() => getPromise());
observable$
将是一个冷的 Observable。
它是一个冷的 Observable,因为生产者(Promise)是在 Observable 内部创建的。每个订阅者将通过调用给定的 Promise 工厂函数来创建一个新的 Promise。
这允许您创建一个 Promise observable$
,而无需立即创建并执行 Promise,也无需与多个订阅者共享此 Promise。每个用户都可以observable$
有效地进行呼叫from(promiseFactory()).subscribe(subscriber)
。因此,每个订阅者创建自己的新 Promise 并将其转换为新的 Observable,并将自己附加到这个新的 Observable。
3 不少运营商直接接受承诺
大多数组合(例如,,,merge
... concat
)或转换可观察值(例如,,,, ...)的RxJS 运算符直接接受 Promise forkJoin
。如果您无论如何都使用其中之一,则不必首先使用包装承诺(但要创建**冷可观察,**您仍然可能需要使用)。combineLatest``switchMap``mergeMap``concatMap``catchError``from``defer
// Execute two promises simultaneously
forkJoin(getPromise(1), getPromise(2)).pipe(
switchMap(([v1, v2]) => v1.getPromise(v2)) // map to nested Promise
)
检查文档或实施以查看您使用的运算符是否接受ObservableInput
或SubscribableOrPromise
。
type ObservableInput<T> = SubscribableOrPromise<T> | ArrayLike<T> | Iterable<T>;
// Note the PromiseLike ----------------------------------------------------v
type SubscribableOrPromise<T> = Subscribable<T> | Subscribable<never> | PromiseLike<T> | InteropObservable<T>;
from
和之间的区别defer
示例: https://stackblitz.com/edit/rxjs-6rb7vf
const getPromise = val => new Promise(resolve => {
console.log('Promise created for', val);
setTimeout(() => resolve(`Promise Resolved: ${val}`), 5000);
});
// the execution of getPromise('FROM') starts here, when you create the promise inside from
const fromPromise$ = from(getPromise('FROM'));
const deferPromise$ = defer(() => getPromise('DEFER'));
fromPromise$.subscribe(console.log);
// the execution of getPromise('DEFER') starts here, when you subscribe to deferPromise$
deferPromise$.subscribe(console.log);
defer
可能是大多数人正在寻找的运算符,因为许多应用程序都依赖 Observables 来保持冷状态并在订阅时触发数据获取。from
不过,对于某些用例来说,这仍然是一个可行的选择,例如,当您想在某些初始化过程中创建一次 Promise,然后通过将被订阅多次的 Observable 传播其值,但又不想创建和执行再次向每一位订阅者承诺。