【发布时间】:2018-04-28 05:48:20
【问题描述】:
我一直在尝试找到一个将 Observable 包装到订阅者中以监视异步调用状态的示例,例如加载、完成或出错。你能提供一个简短的例子吗?
【问题讨论】:
-
顺便说一句,这是标记为
rxjs的第 5000 个问题 :)。 -
酷!看来今天是我的幸运日:)。
我一直在尝试找到一个将 Observable 包装到订阅者中以监视异步调用状态的示例,例如加载、完成或出错。你能提供一个简短的例子吗?
【问题讨论】:
rxjs 的第 5000 个问题 :)。
不确定这是否是您的意思,但您可以像这样包装异步 http 调用
const httpStream = Observable.create(observer => {
fetch('http://server.com')
.then(response => response.json())
.then(data => {
observer.next(data); // if http call provides progress as well as completion
// these can all be pushed with observer.next()
observer.complete();
})
.catch(err => observer.error(err));
});
httpStream.subscribe(data => console.log(data));
当然,如果它实际上是 fetch 你想包装你可以改为这样做
var result = Rx.Observable.fromPromise(fetch('http://myserver.com/'));
编辑:如果您使用的是 Angular HttpClient,则无需包装它,因为它已经是可观察的。要获得进度更新以及最终响应,如下所示应该可以工作
const req = new HttpRequest('POST', 'http://api.server.com', body, {
reportProgress: true
});
this._http.request(req)
.filter((event) => event.type === HttpEventType.UploadProgress || event instanceof HttpResponse)
.map((event) => {
if (event.type === HttpEventType.UploadProgress) {
const percentDone = Math.round(100 * event.loaded / event.total);
return { type: 'uploadProgress', percentDone };
} else if (event instanceof HttpResponse) {
return { type: 'httpResponse', status: event.status };
}
})
.subscribe((response) => {
if (response.type === 'uploadProgress') {
console.log(`upload still in progress - percent done = ${response.percentDone}%`);
} else {
console.log(`upload completed - status = ${response.status}`);
}
});
如果实际上您只想知道所有请求何时完成,并且不需要每个请求的进度更新,而不是将请求推送到数组中,更好的选择可能是使用 forkJoin - 这是与 promise.all 类似,只有在所有子可观察对象完成后才能从可观察对象获得输出 - https://www.learnrxjs.io/operators/combination/forkjoin.html
【讨论】:
let obs = http.get(); let sub = obs.subscribe()。我还需要介绍一个单独的观察者吗?
obervable 或 subscription,但不在实际通话中。例如subs.push(obs | sub),然后在 subs 数组上工作以显示忙碌指示符(如果有任何元素正在进行中)。