我目前从承诺转为可观察。我正在使用Redux-Observable作为我的反应应用程序。基本上,我正在寻找最好的运算符,它将启用mutliple,并发ajax调用,并在所有observable已成功执行时返回响应。 这是我的应用程序的代码片段。
let epicPostAd = (action$, store, {ajax}) =>
action$.ofType(POST_AD)
.debounceTime(1000)
.mergeMap(({ payload }) =>
ajax(generateAjaxRequestSetting(POSTS_URL, 'post', payload,CT_JSON))
.map(response => postAdSuccessful(response))
.catch(e => Observable.of(postAdUnsuccessful(e.xhr.response)))
.takeUntil(action$.ofType(LOCATION_CHANGE))
)
这是一个简单的ajax请求,在响应为201时发布给定广告并发送POST_AD_SUCCESSFUL
,否则会在出错时调度POST_AD_UNSUCCESSFUL
。
但问题是我想在有响应时制作后续的ajax可观察流。如
.map(response => /* start a stream of ajax observables then process the response */)
如果你向我展示实现这一目标的最佳方式,我将不胜感激。
答案 0 :(得分:10)
听起来像是在寻找forkJoin
operator。
它将订阅您传递给它的所有Observable,并且在所有完成后,它将从数组内的每个中发出最后一个值。
在Epic中你想要做到这一点并不完全清楚,所以我只是做了一个通用的例子:
const somethingEpic = (action$, store, { ajax }) =>
action$.ofType(SOMETHING)
.mergeMap(() =>
Observable.forkJoin(
ajax('/first'),
ajax('/second'),
ajax('/third')
)
.do(results => {
// the results is an array, containing each
const [first, second, third] = results;
console.log(first, second, third);
})
.map(results => ({
type: 'SOME_RESULTS',
results
}))
);
从技术上讲,它支持您可以使用的最终resultSelector
参数,而不是使用后面的map
运算符,但我倾向于不使用它,因为我已经找到它了不太清楚,在常见的redux-observable风格案例中只有微不足道的性能优势。但它仍然很好知道。可以方便更多"数据规范化"东西,而不是"把它变成一个动作"东西。
const somethingEpic = (action$, store, { ajax }) =>
action$.ofType(SOMETHING)
.mergeMap(() =>
Observable.forkJoin(
ajax('/first'),
ajax('/second'),
ajax('/third'),
results => ({
type: 'SOME_RESULTS',
results
})
)
);
另外,如果您问自己"我使用什么操作员?"您应该尝试文档中的操作员向导:http://reactivex.io/rxjs/
向下滚动到显示:
的部分您是否需要为您的问题找到操作员?首先从下面的列表中选择一个选项:
- 我有一个现有的Observable,并且......
- 我有一些Observables组合成一个Observable,并且......
- 我还没有Observables,而且......
提示:打开你的DevTools来试验RxJS。
虽然在这种情况下,forkJoin
被正确建议但是当你点击它时,它还没有记录:sadface:但谷歌搜索会提供许多不同的网站,解释它的作用以及如何使用它(在RxJS和其他语言的其他Rx实现中)。像this helpful website
答案 1 :(得分:0)
这是我自己的问题的答案。尽管JayPhelps回答,但我意识到我的问题并不那么明确。使用周杰伦的推荐。我想出了以下内容:
let epicPostAd = (action$, store, {ajax, observable}) =>
action$.ofType(POST_AD)
.debounceTime(1000)
.mergeMap(({ payload }) =>
ajax(generateAjaxRequestSetting(POSTS_URL, 'post', payload, CT_JSON))
.mergeMap(response =>
observable.forkJoin(
ajax(''),
ajax('')
)
.do(res => {
const [first, second, third] = results;
console.log(first, second, third);
})
.map(res => postAdSuccessful(res))
)
.catch(e => observable.of(postAdUnsuccessful(e.xhr.response)))
.takeUntil(action$.ofType(LOCATION_CHANGE))
)
所以这里是如何运作的。我发出了一个post请求,并在ajax请求完成执行后立即.mergeMap
使用.forkJoin()
对ajax ovservables流的响应。然后处理结果