3. Next.js Document - data fetching

Eunsu·2022년 3월 16일

@ NextJS

목록 보기
3/3
post-thumbnail

◼ NEXT_JS 데이터 가져오기

  • SSR : 서버 측 렌더링
  • SSG : 정적 사이트 생성
  • CSR : 클라이언트 측 렌더링
  • Dynamic Routing : 동적 라우팅
  • ISR : 증분 정적 재생

🚀 getServerSideProps

페이지에서 getServerSideProps라는 NEXT.JS에서 제공하는 함수를 내보내는 경우 반환된 데이터는 사용하여 각 요청에서 이 페이지를 미리 렌더링 한다.

◻ getServerSideProps 실행 시점

기본적으로 getServerSideProps는 서버에서 실행되며, 브라우저에서는 실행되지 않는다.
또한 페이지에서만 내보앨 수 있고, 독립 실행형 기능으로 구성요소의 속성을 리턴하지 않으면 작동하지 않는다.

  • next/link를 사용해 페이지를 전환할 때
  • next/router 를 사용해 Next.js가 API요청을 서버에 전송할 때

◻ getServerSideProps 사용 시점

getServerSideProps는 데이터 요청 시 데이터를 가져와야 하는 페이지를 미리 렌더링 해야 하나는 경우에만 사용한다.

데이터를 미리 렌더링할 필요가 없다면 클라이언트 측 에서 데이터를 가져오는 것을 고려해야 한다.

◻ getServerSideProps 오류 페이지

내부에 오류가 발생 하게 되면 파일에 pages/500.js 가 표시 된다.

🚀 getStaticPaths & getStaticProps

◻ getStaticPaths

페이지에 동적 경로가 있고, getStaticProps로 정적으로 데이터를 불러오는 경우, 정적으로 생성할 경로 목록을 정의해야 하는데, 그때 사용되는 Next.js 함수이다.

  • 단독적으로 사용이 불가능하며, getStaticProps와 반드시 함께 사용해야 함.
  • Next.js에서 지정한 모든 경로를 정적으로 미리 렌더링 함.

◾ getStaticPaths 사용 시점

getStaticPaths는 동적경로를 사용하고, 페이지를 정적으로 사전 렌더링 하는 경우에 사용한다.

CMS, 데이터베이스, 파일 시스템의 데이터를 가져올 수 있고, 공개적으로 캐시할 수 있으며, 속도가 매우 빠르고 HTML, JSON파일 등 둘 다 CDN에 의해 캐시 될 수 있다.

◾ getStaticPaths 실행 시점

getStaticPaths는 프로덕션 환경에서 빌드하는 동안에만 실행되며 런타임에는 호출되지 않는다.

  • getStaticProps 빌드 중에 반환된 next build를 할 때
  • fallback : true로 지정할 경우 백그라운드에서 실행
  • fallback : blocking으로 지정할 경우 렌더링 전에 호출

fallback은 'blocking' 은 build time에 만들어지지 않은 페이지에 대한 요청이 들어왔을 때, 새로운 html을 만들기 전까지 페이지 이동을 blocking 하겠다는 뜻이다.

◻ getStaticProps

getStaticProps를 사용할 경우 빌드 시 미리 렌더링한다.

◾ HTML과 JSON을 모두 정적으로 생성

빌드 시 미리 렌더링되면 HTML파일 외 실행결과를 담은 JSON 파일을 생성한다.

  • next/link를 통해 클라이언트 라우팅을 할 떄 생성
  • next/router를 사용하여 미리 렌더링된 페이지로 이동하면 getStaticProps는 JSON파일을 가져와 페이지 구성 요소의 소품으로 사용한다. 내보낸 JSON만 사용되므로 클라이언트 측 페이지 전환이 호출되지 않는다.

◻ ISR (증분 정적 재생)

next.js를 사용하면 사이트를 구축 한 후 정적페이지를 만들거나 업데이트 할 수 있다. 하지만 ISR을 사용하면 전체 사이트를 다시 빌드할 필요 없이 페이지별로 정적 생성을 사용할 수 있다.

⛏ 사용방법

export async function getStaticProps(){
	cosnt data= await axios.get('url주소').then(res=> res.data);
    return {
    	props:{data},
        revalidate:10 //seconds 기본값은 fasle
    }
}
  • 초기 요청 후 10초 전에 페이지에 대한 모든 요청도 캐시됨.
  • 10초 후 다음요청은 캐싱된 페이지를 표시
  • 페이지가 성공적으로 생성되면 Next.js는 캐시를 무효화하고 업데이트 된 페이지를 표시함

html이 만들어지고 10초 동안은 사용자에게 같은 html파일을 그대로 응답한다. 10초가 지나고 GET 요청이 오면, 기존 html을 응답하면서 동시에 새로운 html을 regenerate 한다. 그리고 다음 GET 요청부터는 갱신된 html 문서를 응답한다.

◾ 온디맨드 재검증 사용 (이해안감 나중에 완독하고 다시볼꺼임)

다음 URL 구조를 사용하여 (수동으로 또는 웹훅을 사용하여) 경로에 액세스할 수 있다.

 // pages/api/revalidate.js
export default async function handler(req, res) {
  // 비밀 토큰이 있는지 확인.
  if (req.query.secret !== process.env.MY_SECRET_TOKEN) {
    return res.status(401).json({ message: 'Invalid token' })
  }
  try {
    await res.unstable_revalidate('/path-to-revalidate')
    return res.json({ revalidated: true })
  } catch (err) {
    return res.status(500).send('Error revalidating')
  }
}

◻ CSR (클라이언트 측 데이터 가져오기)

  • SEO 인덱싱이 필요 없을 때
  • 데이터를 미리 렌더링 할 필요가 없을 때
  • 페이지 콘텐츠를 자주 업데이트 해야 할 때

클라이언트 측 데이터 가져오기를 사용하면 애플리케이션의 성능과 페이지의 로드 속도에 영향을 미칠 수 있다는 점에 유의하는 것이 중요하다. 컴포넌트나 페이지가 마운트되는 시점에 데이터 페칭이 이루어지고 데이터가 캐싱되지 않기 때문이다.

◾ useEffect 사용

const Home = () => {
  const [data, setData] = useState(null);
  const [isLoad, setIsLoad] = useState(false);
  console.log(data);
  useEffect(() => {
    const fetch = async () => {
      await axios.get(`https://jsonplaceholder.typicode.com/posts`).then((res) => {
        setData(res.data);
        setIsLoad(true);
      });
    };
    fetch();
  }, []);
  return (
    <>
      <h1>Client Data Fetching</h1>
      <ul>{isLoad && data.map((post) => <li key={post.id}>{post.title}</li>)}</ul>
    </>
  );
};
export default Home;

◾ useSWR사용

캐싱, 재검증, 초점 추적, 간격으로 다시 가져오기 등을 처리한다.

SWR은 자동으로 데이터를 캐싱하고 데이터가 오래되면 유효성을 다시 검사한다.

type PostType = {
  userId: number;
  id: number;
  title: string;
  body: string;
};
const fetcher = (url: string) => axios.get(url).then((res) => res.data);
const Home = () => {
  const { data, error } = useSWR(`https://jsonplaceholder.typicode.com/posts`, fetcher);
  console.log(data);
  return (
    <>
      <h1>Client Data Fetching</h1>
      <ul>{data && data.map((post: PostType) => <li key={post.id}>{post.title}</li>)}</ul>
      {error && new Error("Found Error")}
    </>
  );
};
export default Home;

출처: https://vroomfan.tistory.com/4 [내실내놀 개발자]

profile
function = (Develope) => 'Hello World'

0개의 댓글