TypeScript 3.6 Strict Generator 타입 체크 적용기
문제 상황
회사 프로젝트를 TypeScript 3.6으로 업그레이드했더니 Redux-Saga 코드에서 타입 에러가 쏟아졌다. 3.6부터 Generator의 next(), return(), throw()의 타입 체크가 엄격해진 게 원인이었다.
// 기존 코드 - 3.5에서는 통과
function* fetchUser() {
const response = yield call(api.getUser);
// response가 any로 추론됨
yield put(setUser(response.data));
}
해결 방법
@types/redux-saga 패키지를 최신 버전으로 올리고, SagaIterator를 명시적으로 사용했다.
import { SagaIterator } from 'redux-saga';
import { call, put } from 'redux-saga/effects';
function* fetchUser(): SagaIterator {
const response: ApiResponse = yield call(api.getUser);
yield put(setUser(response.data));
}
더 정확한 타입을 원한다면 제네릭을 활용할 수 있다.
function* fetchUser(): Generator<
CallEffect | PutEffect,
void,
ApiResponse
> {
const response = yield call(api.getUser);
yield put(setUser(response.data));
}
교훈
타입 체크가 엄격해지면서 기존에 숨어있던 잠재적 버그들이 드러났다. 특히 API 응답을 any로 처리하던 부분들이 많았는데, 이번 기회에 인터페이스를 제대로 정의하게 됐다.
Generator 타입 시그니처가 복잡해 보이지만, SagaIterator 정도만 사용해도 실용적으로는 충분했다. 100여 개의 saga 함수를 수정하는 데 하루 정도 걸렸지만, 타입 안정성이 확실히 개선됐다.