HOC, higher-order component
컴포넌트를 매개변수로 받아 새로운 컴포넌트를 반환하는 함수
React 특성상 사용되는 디자인 패턴 중 하나
컴포넌트 로직을 재사용하고 컴포넌트 간의 코드 공유를 단순화하는 방법을 제공
고차 컴포넌트는 다른 컴포넌트를 감싸고, 해당 컴포넌트에 추가적인 프로퍼티, 상태 또는 메서드를 제공하는 함수
- 컴포넌트 간에 로직을 공유하려면 로직을 HOC로 추출하여 여러 컴포넌트에서 사용 가능
- 상태를 다루는 로직을 분리하고, 여러 컴포넌트가 동일한 상태를 공유하도록 돕는데 사용
- 라우팅 라이브러리와 통합하여 특정 라우트에서 특정 컴포넌트를 렌더링하는데 사용
=> 컴포넌트와 컴포넌트 사이에 로직을 추가하고 싶고, 그 로직을 공통적으로 사용하고 싶을 때 사용한다!
로그인 고차 컴포넌트
import React, { useEffect } from 'react';
import getUserId from '../utils/localStorageHandlers';
import { useNavigate } from 'react-router-dom';
const withLogin = (InnerComponent: React.FC) => {
return () => {
const navigator = useNavigate();
const userId = getUserId;
useEffect(() => {
if (!userId) {
alert('로그인이 필요합니다.');
navigator('/intro');
return;
}
}, [userId, navigator]);
return userId ? <InnerComponent /> : null;
};
};
export default withLogin;
고차 컴포넌트 사용하기
import React from 'react';
import MyCard from './components/My.MyCard';
import DiaryList from './components/My.DiaryList';
import withLogin from '../../components/withLogin';
const MyPage: React.FC = () => {
return (
<main style={{ gap: '40px', height: '95vh' }}>
<MyCard />
<DiaryList />
</main>
);
};
export default withLogin(MyPage);
의문점
왜 굳이 컴포넌트와 컴포넌트 사이에 로직을 추가하는걸까?
가독성을 위해서일까?
=> yes
디자인 패턴 HOC
React에서 더 유연한, 재사용 가능한, 및 더 효율적인 코드 작성을 지원하는 중요한 디자인 패턴
컴포넌트 컴포지션을 통해 코드 재사용을 높이고 관리하기 쉽도록 도와줌
- 로직 재사용: HOC를 사용하면 컴포넌트에서 중복되는 로직을 추상화하여 여러 컴포넌트에서 재사용할 수 있습니다.
- 관심사 분리: HOC는 컴포넌트의 논리적인 관심사를 분리하여 컴포넌트가 더 간단하고 단일 책임을 갖도록 도와줍니다.
- 컴포넌트 컴포지션: 여러 HOC를 조합하여 컴포넌트를 빌드하고 컴포넌트를 더 작고 모듈화된 부분으로 분해할 수 있습니다.
- 포워딩 리팩토링: HOC를 사용하면 기존 컴포넌트에 로직을 추가하는 대신 새로운 컴포넌트로 래핑할 수 있어서 기존 코드를 변경하지 않고도 새로운 기능을 추가할 수 있습니다.
- 타입 안전성: TypeScript와 함께 사용할 때 타입 안전성을 제공할 수 있습니다.