패턴 리스트 중 가장 일반적이다. 앵귤러1의 watcher와 listener를 사용한거 기억하니?
이 패턴은 action이 dispatch된 후에 어떤 프로세스를 트리거하는데 사용한다.
/* this is the saga you are going to register */
export function* aListenerOnlySaga() {
const somePossibleData = yield take('SOME_ACTION');
yield fork(someOtherSagaProcess);
}
function* someOtherSagaProcess() {
/* Any process calculation you need to do */
}
use case
다양한 정보를 보여주고 현재 선택에 따라 action을 취해야하는데 필요한 브랜치/상태를 지원해야한다.
/* We create a manager saga */
function* fetchDataManager() {
/* we need to start the service/saga */
yield put({
type: 'fetchSomeData_events',
});
/* we need to wait/listen when it ends...*/
yield take('fetchSomeData_events_success');
/* fork another process, query info from the state, do imperative stuff, whatever you need to do when the previous saga finishes, the sky is the limit... */
}
/* We create an orchestrator saga */
function* orchestratorSaga() {
while (true) {
yield fork(fetchDataManager);
}
}
/* your root saga then looks like this */
function* rootSagas() {
yield [takeEvery('other_action_trigger', orchestratorSaga)];
}
for/of collection
위 방법으로 대부분의 문제를 해결하지 않는다.
어떤 곳에서 collection 데이터를 가져온다고 해보자. 100개의 객체를 받고 각각에게 operation/service를 적용해야한다. 즉, 1개 잇아의 액션을 각 엘리먼트에 디스패치 해야한다. 보통, 리듀서에서 다룰 수 있지만, service catalog의 spirit을 유지하자(?)
saga에서 다음 행동을 할 수 없다.
function* someSagaName() {
/* code omitted for convenience */
const events = yield call(fetchEvents)
events.map((event) => {
/* this is syntactically invalid */
yield put({type: 'some_action', payload: event})
})
}
fetchSomeData_events_error 처리 중에 에러가 있다면 디스패치되는 액션
위 사가를 확장해야한다면?
/* We create a manager saga */
function* fetchDataManager() {
/* we need to start the service/saga */
yield put({
type: 'fetchSomeData_events',
});
/* we need to wait/listen when it ends...*/
yield take('fetchSomeData_events_success');
/* fork another process, query info from the state, do imperative stuff, whatever you need to do when the previous saga finishes, the sky is the limit... */
}
/* We create an orchestrator saga */
function* orchestratorSaga() {
while (true) {
yield fork(fetchDataManager);
}
}