본문 바로가기
카테고리 없음

[ React ] Context

by quessr 2022. 12. 3.

Tabs 컴포넌트를 만들며 적용한 React Context
개념 정리


  • React Context란?

  • 사용한 이유

  • 사용방법

  • 좋았던 점

 

 

 

 

React Context란?

 

React컴포넌트 트리 안에서 전역적이라고 볼 수 있는 데이터를 단계마다 일일이 props로 넘겨주지 않고도 컴포넌트 트리 전체에 데이터를 공유할 수 있도록 고안된 방법이다.

사용한 이유

Tabs 컴포넌트를 구현하기 위해서 Tab를 클릭함에 따라 바뀌는 인덱스값을 통해 Tab과 일치하는 인덱스의 TabPanel을 보여줘야했다. 따라서 바뀌는인덱스 값과 onChange함수를 Tabs컴포넌트 내에서 전역으로 관리할 필요성이 생겨 Context를 사용하게 되었다.

    <Tabs index={args.index} onChange={onChange}>
      <TabList>
        <Tab>One</Tab>
        <Tab>Two</Tab>
        <Tab>Three</Tab>
      </TabList>

      <TabPanels>
        <TabPanel>one!</TabPanel>
        <TabPanel>two!</TabPanel>
        <TabPanel>three!</TabPanel>
      </TabPanels>
    </Tabs>


사용 방법

 

  1. 리액트 패키지에서 createContext 함수를 불러온다.
  2. Provider 함수를 만들어준다.
  3. Provider 함수안에서 컴포넌트 트리 전체에 공유하고자 하는 값을 value라는 props로 설정하여 넘겨준다.
  4. 전역데이터를 사용하고자하는 컴포넌트의 최상위컴포넌트를 Provider컴포넌트로 감싸준다.
  5. useContext라는 Hook을 사용하여 Context에 넣은 값에 바로 접근할 수 있다.
useTabs.tsx (5)

const useTabs = () => {
  const context = useContext(TabsContext);
  if (!context) {
    throw new Error('useTabs 훅에 context가 제공되지 않았습니다.');
  }
  return context;
};

export default useTabs;
Tabs.context.tsx (2, 3)

const TabsProvider = ({
  children,
  index: indexProp,
  onChange: onChangeProp,
}: TabsProviderProps) => {
  const [activeIndex, setActiveIndex] = useState<number>(indexProp ?? 0);

  const onChange = useCallback(
    (index: number) => {
      if (onChangeProp) onChangeProp(index);
      else if (indexProp === undefined) setActiveIndex(index);
    },
    [indexProp, onChangeProp],
  );

  useEffect(() => {
    if (indexProp !== undefined) setActiveIndex(indexProp);
  }, [indexProp]);

  const value = useMemo(
    () => ({ activeIndex, onChange }),
    [activeIndex, onChange],
  );
  return <TabsContext.Provider value={value}>{children}</TabsContext.Provider>;
};

export default TabsProvider;
index.tsx (4)

const Tabs = ({ children, ...rest }: TapsProps) => {
  return (
    <TabsProvider {...rest}>
      <div>{children}</div>
    </TabsProvider>
  );
};

export default Tabs;

 

좋았던 점

 

작은규모의 앱에서 따로 전역상태관리 라이브러리를 사용하지 않고도 전역상태관리가 필요한 컴포넌트내에서만 props  drilling 문제를 발생시키지 않고 전역데이터를 공유하여 사용할 수 있다는 점이 좋았다.



참조: https://ko.reactjs.org/docs/context.html#when-to-use-context 

 

Context – React

A JavaScript library for building user interfaces

ko.reactjs.org

https://velog.io/@velopert/react-context-tutorial