React.lazy

J·2023년 8월 25일
0

todays-recipe

목록 보기
8/9
post-thumbnail

React.lazy?

  • React 내장 API.
  • 컴포넌트를 렌더링하는 시점에 비동기적으로 로드할 수 있게 해줌.
  • 코드 분할(Code Splitting)을 통해 필요한 부분만 초기 로드, 나머지 부분은 필요 시 로드.
  • CSR의 단점 중 하나인 초기 로딩 시간을 어느 정도 개선할 수 있음.

기존 라우터

import { BrowserRouter, Routes, Route } from 'react-router-dom';
import Main from '../pages/Main';
import Search from '../pages/Search';
import Recipe from '../pages/Recipe';
import Detail from '../pages/Detail';
import My from '../pages/My';
import Admin from '../pages/Admin';
import NotFound from '../pages/NotFound';
import Header from '../components/layout/Header';
import ScrollToTopButton from '../components/layout/ScrollToTopButton';

const Router = () => {
  return (
    <BrowserRouter>
      <Header />
      <Routes>
        <Route path="/" element={<Main />} />
        <Route path="/search/:keyword" element={<Search />} />
        <Route path="/recipe" element={<Recipe />} />
        <Route path="/detail/:id" element={<Detail />} />
        <Route path="/my" element={<My />} />
        <Route path="/admin" element={<Admin />} />
        <Route path="*" element={<NotFound />} />
      </Routes>
      <ScrollToTopButton />
    </BrowserRouter>
  );
};

export default Router;

lazy 적용 후 라우터

import { BrowserRouter, Routes, Route } from 'react-router-dom';
import React, { Suspense } from 'react';
import Header from '../components/layout/Header';
import ScrollToTopButton from '../components/layout/ScrollToTopButton';
import Loading from '../components/common/Loading';

const Main = React.lazy(() => import('../pages/Main'));
const Search = React.lazy(() => import('../pages/Search'));
const Recipe = React.lazy(() => import('../pages/Recipe'));
const Detail = React.lazy(() => import('../pages/Detail'));
const My = React.lazy(() => import('../pages/My'));
const Admin = React.lazy(() => import('../pages/Admin'));
const NotFound = React.lazy(() => import('../pages/NotFound'));

const Router = () => {
  return (
    <BrowserRouter>
      <Header />
      <Suspense fallback={<Loading />}>
        <Routes>
          <Route path="/" element={<Main />} />
          <Route path="/search/:keyword" element={<Search />} />
          <Route path="/recipe" element={<Recipe />} />
          <Route path="/detail/:id" element={<Detail />} />
          <Route path="/my" element={<My />} />
          <Route path="/admin" element={<Admin />} />
          <Route path="*" element={<NotFound />} />
        </Routes>
      </Suspense>
      <ScrollToTopButton />
    </BrowserRouter>
  );
};

export default Router;

사용 방법

  1. 동적 import를 위한 컴포넌트 생성
  • React.lazy 이용 동적으로 로드할 컴포넌트 생성. import()를 통해 해당 컴포넌트의 경로 전달.
    ex: 메인 페이지는 '../pages/Main' 경로의 default export된 컴포넌트를 동적으로 불러와 Main 이라는 변수에 할당.
    // 적용 전
    import Main from '../pages/Main';
    // 적용 후
    const Main = React.lazy(() => import('../pages/Main'));
  1. Suspence로 감싸주기
  • lazy를 적용한 컴포넌트들을 Suspense로 감싸줘야 함. Suspense 컴포넌트는 예하 컴포넌트가 준비될 때까지 대체 컨텐츠를 보여주는 역할. 기존 Loading 컴포넌트를 생성해뒀으므로 fallback prop에 import 된 Loading 컴포넌트를 지정해주면 기존 렌더링될 컴포넌트들이 아직 로드되고 있거나 렌더링이 끝나지 않았다면 Loading 컴포넌트를 대체해 먼저 보여줌.

추가

img 태그에 HTML의 loading = "lazy" 속성도 추가했다.
React.lazy는 React 컴포넌트를 동적으로 로드하기 위해 사용하는 api,
loading = "lazy"는 이미지 등의 컨텐츠의 로딩을 지연시키는 데 사용된다. 페이지가 처음 로드될 때 보이지 않는 이미지의 로딩을 지연시켜 성능을 개선할 수 있다. (스크롤 하단 보이지 않는이미지 등)

    <RecipeImgWrapper>
      <img src={recipe.image} alt={recipe.name} loading="lazy" />
    </RecipeImgWrapper>
  • img 태그에 속성을 추가하면 됨.
  • img에 width, height를 설정해주지 않았다면, default width, height이 0이기 때문에 로딩 이후에 img를 렌더링할 떄 전체 레이아웃 다시 계산해야 한다고 함. (RecipeImgWrapper 내부 속성에 img 사이즈 설정 해둠.)
profile
벨로그로 이사 중

0개의 댓글

Powered by GraphCDN, the GraphQL CDN