[英]How to handle for promise inside a piped map
我肯定我在这里很困惑,所以请提供任何帮助。
这是我的场景:
我从 Firestore 中提取了一个文档:
return this.afs.collection("events").doc(eventID).snapshotChanges().pipe(
map( document => {
})
);
到这里为止一切都很好。
但在地图内我需要一个承诺来解决(或不解决)
例如:
return this.afs.collection("events").doc(eventID).snapshotChanges().pipe(
map( document => {
// This is a promise the below part
const data = await EventImporterJSON.getFromJSON(document.payload.data())
return data
})
);
我知道await
不能在那里发生。 我很困惑如何解决这个问题,也许我在 observables 和 rxjs 上工作的时间不够长。
最后我想要实现的是:
获取文档。 映射并处理它,但在这个过程中,我需要处理一个承诺。
不过,我不想将该承诺返回给调用者。
这有意义吗?
还是我的结构完全错误?
这是mergeMap
或concatMap
的典型用例:
return this.afs.collection("events").doc(eventID).snapshotChanges().pipe(
mergeMap(document => {
// This is a promise the below part
return EventImporterJSON.getFromJSON(document.payload.data())
})
);
但是,您也可以使用async - await
因为诸如mergeMap
类的运算符以相同的方式处理 Observables、Promises、数组等,因此您只需在mergeMap
的项目函数中返回一个 Promise 就可以正常工作。
通常,您不需要在单个方法中使用多个await
,因为更“Rx”的做事方式是链接运算符,但如果您愿意,您可以因为async
方法返回一个 Promise 并且 RxJS 会像处理它一样任何其他承诺。
const delayedPromise = () => new Promise(resolve => {
setTimeout(() => resolve(), 1000);
})
of('a').pipe(
mergeMap(async v => {
console.log(1);
await delayedPromise();
console.log(2);
await delayedPromise();
console.log(3);
await delayedPromise();
return v;
})
).subscribe(console.log);
// 1
// 2
// 3
// a
Live demo: https://stackblitz.com/edit/rxjs-3fujcs
Observables 可以看作是 Promise 的一层,你为什么不这样使用你的 Promise 呢? 像这样 :
let getDataFromJson(payloadData){
return from(EventImporterJSON.getFromJSON(payloadData());
}
return this.afs.collection("events").doc(eventID).snapshotChanges().pipe(
map(document=>document.payload.data),
switchMap( payloadData=> getDataFromJson(payloadData)))
.subscribe(result=>{
//final result
});
1 用 map 管道你的第一个 observable 只是为了简化你的返回值
2 switchMap 到另一个可观察对象,这将是您作为可观察对象的承诺(使用“来自”运算符);
map 运算符用于以同步和“纯”方式改进结果,例如仅返回对象的少数属性或过滤数据,在这里您想要链接两个异步操作,因此我建议您将其保留在 rx 方法中
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.