
React 프로젝트를 개발하다 보면 전역 상태 관리가 필요할 때가 많다. Redux, MobX, Context API 등 다양한 상태 관리 라이브러리가 있지만 Recoil은 React의 철학과 구조에 잘 맞는 가벼운 상태 관리 라이브러리로 주목받고 있다. (사실 나온지 좀 많이 됨)
이번 글에서는 Recoil의 사용법과 Redux와의 차이점, 그리고 Recoil만의 장점에 대해 알아보도록 하자.
Recoil은 Facebook에서 만든 React 상태 관리 라이브러리로, React와 밀접하게 통합되어 컴포넌트 기반 상태 관리를 제공한다.
주요 특징:
Recoil은 상태를 Atom과 Selector로 관리한다.
Atom은 Recoil의 가장 기본적인 상태 단위로 React 컴포넌트에서 공유할 수 있는 전역 상태를 말한다.
Selector는 Recoil 상태에서 파생 상태(derived state)를 생성하는데 사용된다.
Atom이나 다른 Selector 값을 기반으로 계산된 값을 제공한다. React useMemo와 비슷한 역할을 수행.
npm install recoil
Recoil 상태를 사용하려면 최상위 컴포넌트를 RecoilRoot로 감싸야 한다.
const RestrictedLayout = ({ children }: React.PropsWithChildren) => {
return (
<RecoilRoot>
<AppRouterCacheProvider>
<CssBaseline />
<ThemeProvider>{children}</ThemeProvider>
</AppRouterCacheProvider>
</RecoilRoot>
);
};
atom 함수로 전역 상태를 정의
import { atom } from "recoil";
interface HashTagValue {
district: string[];
usetype: string;
category: string[];
rentable: string;
user: string[];
}
export const defaultValue = {
district: [],
usetype: "",
category: [],
rentable: "",
user: [],
};
const AssetHashtagAtom = atom<HashTagValue>({
key: "AssetHashtag",
default: defaultValue,
});
export default AssetHashtagAtom;
useRecoilState 훅을 이용해 Atom을 사용한다.
import { useRecoilState } from "recoil";
import AssetHashtagAtom from "./state/Hashtag";
const test() => {
const [hashtagState, setHashtagState] = useRecoilState(AssetHashtagAtom);
const onClickCategoryButton = async (item: string) => {
let data: string[] = [];
if (category.includes(item)) data = category.filter((f) => f !== item);
else data = [...category, item];
setCategory(data);
setHashtagState((prev) => ({ ...prev, category: data }));
onCategoryChange(data);
};
내 프로젝트에서는 selector를 사용하지 않아서 다른 예제를 첨부
import { selector } from "recoil";
import { counterState } from "./atoms";
export const doubledCounterState = selector({
key: "doubledCounterState",
get: ({ get }) => get(counterState) * 2,
});
useRecoilValue 훅을 이용해 selector를 사용한다
import { useRecoilValue } from "recoil";
import { doubledCounterState } from "./selectors";
function DoubleCounter() {
const doubledCount = useRecoilValue(doubledCounterState);
return <p>Doubled Count: {doubledCount}</p>;
}
이 처럼 사용법이 매우 간단하다.
| 특징 | Recoil | Redux |
|---|---|---|
| 설치 복잡도 | 간단 (recoil 설치 후 RecoilRoot 추가) | 복잡 (스토어, 리듀서, 액션, 미들웨어 설정 필요) |
| 상태 관리 단위 | Atom과 Selector | Store |
| 설정 및 초기화 | 간단 (RecoilRoot만 추가하면 동작) | 복잡 (스토어, 리듀서, 미들웨어 설정 필요) |
| 비동기 작업 | Selector로 기본 지원 | Redux-Thunk 또는 Redux-Saga 필요 |
| 학습 곡선 | 완만 (React Hooks와 유사) | 가파름 (Flux 패턴 학습 필요) |
| 리렌더링 최적화 | 상태 단위(Atom)별로 관리, 최소 리렌더링 | 상태 변경 시 전체 컴포넌트 트리 리렌더링 가능성 있음 |
| 주요 사용 사례 | 컴포넌트 기반 상태 관리 | 복잡한 상태 관리 및 대규모 애플리케이션 |
Redux는 사용하려면 스토어, 리듀서를 설정하고 여러가지 복잡한 코드가 추가된다. Redux는 나중에 쓰고 싶을 때 내용 작성을 하도록 하겠다..
Recoil은 React와 강력하게 통합된 상태 관리 라이브러리로 간결하고 유연한 상태 관리 경험을 제공한다. Redux보다 배우기 쉽고 설정이 간단하며 비동기 상태 관리도 기본적으로 지원한다. 전역 상태 관리라는 기능에 초점을 맞춰도 전혀 부족함이 없기 때문에 간단하게 사용하려면 Recoil을 강추하는 바이다.