Skip to content

Instantly share code, notes, and snippets.

@ryo33
Last active October 18, 2016 12:35
Show Gist options
  • Save ryo33/a7103e0c75558131b724f4be0893fc2a to your computer and use it in GitHub Desktop.
Save ryo33/a7103e0c75558131b724f4be0893fc2a to your computer and use it in GitHub Desktop.
function* relay(request, relayChannel, nextChannel) {
const result = yield call(request)
yield put(relayChannel, [result, nextChannel])
}
function* runSequencially(requestChannel, resultChannel) {
let head = channel()
let tail = head
while (true) {
const { request, relayResult } = yield race({
request: take(requestChannel),
relayResult: take(head)
})
if (request) {
const nextTail = channel()
yield fork(relay, request, tail, nextTail)
tail = nextTail
} else {
const [result, nextHead] = relayResult
yield put(resultChannel, result)
head = nextHead
}
}
}
@ryo33
Copy link
Author

ryo33 commented Oct 18, 2016

Code

import { fork, race, take, put, call } from 'redux-saga/effects';
import { channel, delay } from 'redux-saga';

function* testSaga() {
  const requestChannel = channel();
  const resultChannel = channel();
  yield fork(runSequencially, requestChannel, resultChannel);
  yield fork(function*() {
    const base = Date.now();
    for (let i = 0; i < 10; i ++) {
      const wait = Math.floor(Math.random() * 100);
      const func = (message) => console.log(`${Date.now() - base}\t\t${message}\t\ti: ${i}\twait: ${wait}`);
      requestChannel.put(() => {
        func('called');
        return new Promise(resolve => setTimeout(() => {
          func('timeout');
          resolve(func);
        }, wait));
      });
      yield call(delay, Math.floor(Math.random() * 10));
    }
  });
  while (true) {
    const func = yield take(resultChannel);
    func('result');
  }
}

Result

0       called      i: 0    wait: 20
9       called      i: 1    wait: 84
11      called      i: 2    wait: 46
17      called      i: 3    wait: 34
21      timeout     i: 0    wait: 20
22      result      i: 0    wait: 20
27      called      i: 4    wait: 68
35      called      i: 5    wait: 58
41      called      i: 6    wait: 84
53      called      i: 7    wait: 91
53      timeout     i: 3    wait: 34
58      timeout     i: 2    wait: 46
59      called      i: 8    wait: 29
65      called      i: 9    wait: 63
89      timeout     i: 8    wait: 29
94      timeout     i: 1    wait: 84
94      result      i: 1    wait: 84
95      result      i: 2    wait: 46
95      result      i: 3    wait: 34
96      timeout     i: 5    wait: 58
97      timeout     i: 4    wait: 68
97      result      i: 4    wait: 68
98      result      i: 5    wait: 58
127     timeout     i: 6    wait: 84
128     result      i: 6    wait: 84
129     timeout     i: 9    wait: 63
144     timeout     i: 7    wait: 91
145     result      i: 7    wait: 91
145     result      i: 8    wait: 29
146     result      i: 9    wait: 63

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment