【Redux Saga炼金笔记】做一个可以重试N次的action

来源:互联网 发布:盈用软件图片 编辑:程序博客网 时间:2024/04/27 17:26

配方

  • action: redoable
  • effects: put, take, takeEvery

流程

  1. 点击按钮,执行sayHello的action
  2. sayHello的action只有执行第3次的时候才会成功
  3. 如果sayHello失败则自动重试直到成功或到达重试次数

实现

1 先定义一个redoable的action creator

/** * @params action: 需要被重试的标准action * @params successType: 当action成功后会被dispatch的action type * @params failureType: 当action失败后会被dispatch的action type * @params time: 重试最大次数 */function redoable(action, successType, failureType, time = 1) {  return {    type: 'REDOABLE',    payload: {      successType,      failureType,      action,      time    }  };}

2 点击按钮时dispatch一个REDOABLE的SAY_HELLO的action

function Hello({  handleSayHello}) {  return (    <div>      <button onClick={handleSayHello}>Say Hello</button>    </div>  );}Hello = connect(  () => ({}),  (dispatch) => ({    handleSayHello() {      dispatch(redoable({        type: 'SAY_HELLO'      }, 'SAY_HELLO_SUCCESS', 'SAY_HELLO_FAILURE', 3));    }  }))(Hello);

3 实现sayHello的saga来处理SAY_HELLO的action

function* sayHello(action) {  times++;  if (times < 3) {    yield put({      type: 'SAY_HELLO_FAILURE'    });    return;  }  times = 0;  alert('Hello, nice to meet you!');  yield put({    type: 'SAY_HELLO_SUCCESS'  });}

4 实现redoableInvoke的saga来处理REDOABLE的action

function* redoableInvoke(action) {  const {    action: realAction,    successType,    failureType,    time  } = action.payload;  yield put(realAction);  const {type} = yield take([successType, failureType]);  if (type === failureType) {    if (time === 0) {      return;    }    const nextAction = {...action};    nextAction.payload = {...nextAction.payload, time: time - 1};    yield put(nextAction);  }}

5 使用takeEvery来运行两个saga

store.runSaga(function * () {  yield takeEvery('REDOABLE', redoableInvoke);  yield takeEvery('SAY_HELLO', sayHello);});
See the Pen <a href="http://codepen.io/awaw00/pen/BppVgJ/">Redux Saga Cookbook 02</a> by aaron wang (<a href="http://codepen.io/awaw00">@awaw00</a>) on <a href="http://codepen.io">CodePen</a>.&#10;
0 0