首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何在redux-saga中取消正在运行的网络请求?

如何在redux-saga中取消正在运行的网络请求?
EN

Stack Overflow用户
提问于 2020-06-26 10:01:35
回答 1查看 1.8K关注 0票数 1

我有个故事:

代码语言:javascript
复制
function* sagaOne() {
   yield call(apiOne);
   yield call(apiTwo);
   yield call(apiThree);
}

function* sagaTwo() {
   try {
      yield all(users.map((user) => call(sagaOne, user));
      yield put(successAction);
   } catch (err) {
     yield put(errAction);
   }
}

function* sagaThree() {
   const task = yield fork(sagaTwo);
   yield take(CancelAction);
   yield cancel(task);
}

我的问题是--当sagaThree开火时,它会叉sagaTwo。如果我分派cancel操作,而sagaOne已经处于更深的状态-- apiOne调用已经解析,apiTwo启动了,则不会取消整个请求。

问题:如何正确取消“更深”,“嵌套”任务(sagaOne),当它已经在第二或第三?

总结:只有当我在启动后立即取消任务,并且还没有一个apiTwo尚未启动时,取消才有效。如果更深入,取消将无法工作,并且每个sagaOne中的每个调用都会解决。

EN

回答 1

Stack Overflow用户

发布于 2020-06-29 05:20:29

对于返回允诺结果的函数,可以通过将[CANCEL]附加到允诺来插入自己的取消逻辑。

更多关于取消剩余-传奇任务这里的信息。

因此,我们需要用一种方法丰富axios返回的承诺,该方法将在取消时由redux-saga调用,并将取消传出的xhr请求。这里您可以找到相关的axios文档。

好的,让我们将其应用于api调用:

代码语言:javascript
复制
import axios from 'axios';
import { CANCEL } from 'redux-saga'

const CancelToken = axios.CancelToken;

const apiOne = () => {
  const source = CancelToken.source();
  const promise = axios.post('url', {
    cancelToken: source.token
  });

  promise[CANCEL] = () => source.cancel();
  return promise;
};

现在,一旦sagaOne被取消,api调用也将被取消(当然,如果它还没有完成)。

这是基本的想法。您可以将公共逻辑提取到包装器或适配器中,因此不需要在每个api函数中都这样做。还可以通过将executor函数传递给CancelToken构造函数来创建取消令牌。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/62592384

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档