reduxjs/toolkit 더 자세히 알아보기 (typescript 적용)

예전에 역시 redux toolkit을 사용해보고 글을 남긴적이 있었다.

https://citron031.tistory.com/entry/Redux-Toolkit-rtk-%EC%82%AC%EC%9A%A9%ED%95%98%EA%B8%B0

 

Redux Toolkit (rtk) 사용하기

로그인 정보를 전역 상태로 사용하기 위하여 redux를 사용하기로 마음먹었다. 자연스럽게 일단 전역 상태를 저장할 store를 만들기 위해 createStore를 불러왔는데, 다음과 같은 상황에 처했다. 커서

citron031.tistory.com

단순한 사용법에 대해서 작성했었는데, 타입스크립트의 적용이나 dev tool 사용하는 법 등 좀 더 사용하고 알게된 점들에 대해서 추가로 남기기로 하였다.

 

import {configureStore} from '@reduxjs/toolkit';
import {useDispatch} from 'react-redux';
import logger from 'redux-logger'

import rootReducer from '../slices';

const store = configureStore({
  reducer: {rootReducer},
  devTools: process.env.NODE_ENV !== "production"
  // react-native의 경우에는 devTools: __DEV__,
  middleware: getDefaultMiddleware => 
  	getDefaultMiddleware().concat(logger),
});

export type RootState = ReturnType<typeof store.getState>;

export type AppDispatch = typeof store.dispatch;
export const useAppDispatch: () => AppDispatch = useDispatch;

export default store;

redux toolkit은 dev tool을 내장하고 있기 때문에, 따로 설치를 할 필요가 없다.

configureStore의 설정에서 devtools 옵션을 설정해줌으로써, redux devtools을 사용할 수 있다.

개발 도구는 실제 배포 상황에서는 반드시 꺼져야 한다. 데이터 구조의 유출과 같은 문제가 발생할 수 있기 때문이다.

 

미들웨어를 사용하고자 한다면, 기존의 미들웨어에 추가적으로 새로운 미들웨어를 덧붙일 수 있다. (배열의 형태로 구성된다)

WARN  The object notation for `createSlice.extraReducers` is deprecated, and will be removed in RTK 2.0. Please use the 'builder callback' notation instead: https://redux-toolkit.js.org/api/createSlice

또한, 최신 버전의 RKT를 사용할 때 다음과 같은 경고 메세지를 볼 수 있었다.

extraReducers에 대해서 에러가 발생하는데, 과거와 사용법이 달라질 예정이라는 듯 하다.

import {createSlice} from '@reduxjs/toolkit';

const userSlice = createSlice({
  name: 'user',
  initialState: {
    ...
   },
  reducers: {
    ...
   },
  },
  extraReducers(builder) {},
});

export const {...} = userSlice.actions;
export default userSlice.reducer;

앞으로는 위와 같이 builder를 인자로 갖는 callback 함수로 extraReducers를 사용해야 한다.

 

타입스크립트로 useDispatch를 사용할 땐, 위에서 선언된 useAppDispatch를 사용한다.

useSelector 역시 타입 설정이 필요한데, 다음과 같이 사용할 수 있다.

import {RootState} from '../store';

const user = useSelector((state: RootState) => state.rootReducer.user);

https://redux-toolkit.js.org/usage/usage-with-typescript

 

Usage With TypeScript | Redux Toolkit

 

redux-toolkit.js.org

https://react-redux.js.org/using-react-redux/usage-with-typescript#typing-the-usedispatch-hook

 

Usage with TypeScript | React Redux

Usage > TypeScript: how to correctly type React Redux APIs

react-redux.js.org

 

또한, slice를 작성할 때 RTK를 사용한다면 더 이상 불변성을 관리하지 않아도 된다.

immer가 built in 되어있기 때문인데, 덕분에 더 간결하게 코드를 작성할 수 있고 불변성 관리를 위해서 작성하는 코드의 오류를 사전에 차단할 수 있다.

 

https://redux-toolkit.js.org/usage/immer-reducers#why-immer-is-built-in

 

Writing Reducers with Immer | Redux Toolkit

 

redux-toolkit.js.org

 

만약, next.js에서 redux를 사용한 개발 환경을 구축하고자 한다면, next-redux-wrapper 라이브러리를 사용하여 redux를 래핑해주어야 한다.

특히나 서버 사이드 렌더링을 한다면, 구조적으로 redux에 호환되지 않기 때문에 추가적인 설정이 필요하다.

https://github.com/kirill-konshin/next-redux-wrapper

 

GitHub - kirill-konshin/next-redux-wrapper: Redux wrapper for Next.js

Redux wrapper for Next.js. Contribute to kirill-konshin/next-redux-wrapper development by creating an account on GitHub.

github.com

HYDRATE 액션으로 getServerSideProps의 결과물을 적용하는 등의 설정이 필요하다.