본문으로 바로가기

ES6에서 도입된 제너레이터(Generator) 함수는 iterable을 생성하는 함수이다.

 

다음은 제너레이터를 생성하고, yield로 중단점을 설정하며, next()를 통해 실행한 예이다.

function* generator() {
  console.log(1);
  yield; // 중단점
  console.log(2);
  yield; // 중단점
  console.log(3);
}

const gen = generator();
gen.next(); // 1 출력
console.log("첫 중단");
gen.next(); // 2 출력
console.log("다음 중단");
gen.next(); // 3 출력

 

다수의 yield를 여러개 설정하면 그 만큼 next로 yield를 건너 뛰어야 합니다.

function* generator() {
  console.log(1);
  yield 7; // 중단점
  yield 5; // 중단점
  yield 9; // 중단점
  console.log(2);
  yield 100; // 중단점
  console.log(3);
}

const gen = generator();

gen.next(); // 1 출력
gen.next();
gen.next();
gen.next(); // 2 출력

 

yield 1, yield 2, yield 3은 yield* [1, 2, 3] 로 간략하게 작성할 수도 있습니다.

 

이를 이용해서 next를 호출할 때마다 무한히 숫자를 증가시키는 로직을 구현해보겠습니다.

while true로 묶어놓았으니 매번 next를 호출할 때마다 숫자가 증가한 결과물을 출력하게 됩니다.

이 방식은 어떤 action을 무수히 많이 날렸을 때도 saga가 계속 반응하게끔 만들어주는 데 사용되는 로직이기도 합니다.

(saga에서 제너레이터를 watchxxxx 로 짓는 이유입니다.)

function* generator() {
  let i = 0;
  while (true) {
    console.log(i);
    yield i++;
  }
}

const gen = generator();

gen.next(); // 0
gen.next(); // 1
...

 

 

 

사실 제너레이터는 async/await가 등장하기 전에 사용되었던 기능입니다. 

 

함수를 중간에 멈출 수 있다는 점 때문에 async/await 보다 편의성은 떨어지지만 중단점을 설정할 수 있다는 점에서 조금 더 강력합니다. 예를 들어 동작은 5번만 액션을 허용하고 다음 액션은 무시하도록하게 할 수도 있습니다.

// 계속 watching
while (true) {
  yield take(ACTION);
}

// 5번만 action 작동
for (let i = 0 ; i< 5; i++) {
  yield take(ACTION);
}

 

이런 점이 redux-saga는 async/await를 사용하지 않고 제너레이터를 사용하는 이유입니다.

 

여튼, 이제 아래와 같은 saga 코드에서 이제 yield가 의미하는 바를 알 수 있을 겁니다.

function* login() {
  try {
    yield call(loginAPI);
    yield put({
      type: LOG_IN_SUCCESS,
    });
  } catch (e) {
    console.error(e);
    yield put({
      type: LOG_IN_FAILURE,
    });
  }
}

function* watchLogin() {
  yield takeLatest(LOG_IN, login);
}

export default function* userSaga() {
  yield all([fork(watchLogin)]);
}

 

 

 

 

참고한 글)

 

https://www.zerocho.com/category/ECMAScript/post/579b34e3062e76a002648af5

 

https://poiemaweb.com/es6-generator

 

https://medium.com/@jooyunghan/%EC%9E%90%EB%B0%94%EC%8A%A4%ED%81%AC%EB%A6%BD%ED%8A%B8-%EC%A0%9C%EB%84%88%EB%A0%88%EC%9D%B4%ED%84%B0%EC%9D%98-%EC%9E%AC%EB%AF%B8-246553cadfbd

 

https://wonism.github.io/javascript-generator/


darren, dev blog
블로그 이미지 DarrenKwonDev 님의 블로그
VISITOR 오늘 / 전체