Redux-Saga #2

김상현·2020년 6월 26일
0

React

목록 보기
16/16

Fork

call을 이용해서 비동기함수를 호출한다면 동기적으로 함수가 종료되고 반환할 때까지 기다려야한다. 하지만 호출 중간에 우발적으로 일어나는 다른 액션 또한 동작하기를 원한다면 fork을 이용해야한다.

import { take, call, put, cancelled } from 'redux-saga/effects'
import Api from '...'
function* loginFlow() {
  while (true) {
    const {user, password} = yield take('LOGIN_REQUEST')
    // LOGIN_REQUEST 액션을 pull한다.
    const task = yield fork(authorize, user, password)
    // authorize 함수 호출 명령을 실행한다.
    const action = yield take(['LOGOUT', 'LOGIN_ERROR'])
    // authorize 함수 호출 명령의 결과를 기다리는 동안 LOGOUT,LOGIN_ERROR가 있을 경우 결과를 기다리지 않고 액션을 pull한다.
    if (action.type === 'LOGOUT')
      yield cancel(task)
    yield call(Api.clearItem, 'token')
  }
}

  • 결합되어있는 fork들의 부모는 결합된 모든 fork들이 종료 된 뒤에 종료된다.
import { delay } from 'redux-saga'
import { fork, call, put } from 'redux-saga/effects'
import api from './somewhere/api' // app specific
import { receiveData } from './somewhere/actions' // app specific

function* fetchAll() {
  const task1 = yield fork(fetchResource, 'users')
  const task2 = yield fork(fetchResource, 'comments')
  yield call(delay, 1000)
}

function* fetchResource(resource) {
  const {data} = yield call(api.fetch, resource)
  yield put(receiveData(data))
}

function* main() {
  yield call(fetchAll)
}

  • 결합되어 있는 fork들 중 하나가 실패하면 바로 실패할 것이다. 에러가 발생하면 모든 대기 중인 effect들을 취소할 것이다.
function* fetchAll() {
  const task1 = yield fork(fetchResource, 'users')
  const task2 = yield fork(fetchResource, 'comments')
  yield call(delay, 1000)
}

function* fetchResource(resource) {
  const {data} = yield call(api.fetch, resource)
  yield put(receiveData(data))
}

function* main() {
  try {
    yield call(fetchAll)
    // 자식 중 하나가 실패한다면 대기 중인 effect를 취소하고 main 안의 catch에 잡힐 것이다.
  } catch (e) {
    // handle fetchAll errors
  }
}

0개의 댓글