February 17, 2020
간단한 라우팅시스템과 서버사이드 렌더링을 지원하는 리액트 프레임워크
npm i next
"scripts": {
"dev": "next",
"build": "next build",
"start": "next start"
}
scripts 에 next 명령어를 등록하면 npm 명령어로 next 명령어를 실행할 수 있다.
next 프레임워크의 Routing system은 프로젝트 root 디렉토리 안의 pages 디렉토리에서 이루어진다.
next 프레임워크의 주소 체계에서
'/'
즉, 해당 프로그램의 homepage는 기본적으로 index.js
를 실행한다.
그리고 pages 안에 디렉토리를 넣거나 js 파일 (정확히는 리액트 컴포넌트)을 넣으면 next 프레임워크에서 이를 반영해 자동으로 routing system을 구축해준다.
pages/about.js => localhost:3000/about
pages/user/me.jsx => localhost:3000/user/me
const Index = () => <div>Hello!</div>
next 프레임워크에서 컴포넌트 내부 라우팅(Link
태그)을 지원한다.
import Link from 'next/link'
const Main = () => (
<Link href="/about">
<a>어바웃페이지</a>
</Link>
)
next 프레임워크에서 html head태그의 요소(link, meta, script 등등)도 컴포넌트 형태로 쉽게 쓸 수 있게 지원한다.
import Head from 'next/head'
const Main = () => (
<Head>
<title>My page title</title>
<meta name="viewport" content="initial-scale=1.0, width=device-width" />
</Head>
)
Next.js uses the App component to initialize pages. You can override it and control the page initialization
프로그램의 레이아웃
역할을 하는 컴포넌트로 공통적으로 사용되는 요소들을 묶어서 최적화시키는 데 사용된다. 코드 스플리팅!
직접 pages 디렉토리에 _app.js 파일을 만들어 App 컴포넌트를 커스터마이징 할 수 있다.
import React from 'react'
import { Container } from 'next/app'
import { GlobalStyle } from '../reset.css.ts'
const App = ({ Component }) => {
return (
<>
{/* 이렇게 공통적으로 사용하는 styled-component 들을 가져오는 등 */}
<GlobalStyle />
<Container>
{/* 여기 Component 컴포넌트(?)가 page들 역할을 한다 */}
<Component />
</Container>
</>
)
}
A custom Document is commonly used to augment your application’s and
tags. This is necessary because Next.js pages skip the definition of the surrounding document’s markup.
Document는 App보다 상위 개념으로 html, body, head 등 공통적으로 쓰이는 html요소들을 읽어오는데 사용된다.
_app.js 와 마찬가지로 pages 디렉토리에 _document.js 파일을 만들면 Document 컴포넌트를 커스터마이징 할 수 있다.
import Document, { Html, Head, Main, NextScript } from 'next/document'
// ⭐ 클래스형 컴포넌트를 사용!
class MyDocument extends Document {
// ⭐ getInitialProps로 SSR도 가능 (밑에서 계속)
static async getInitialProps(ctx) {
const initialProps = await Document.getInitialProps(ctx)
return { ...initialProps }
}
render() {
return (
<Html>
<Head />
<body>
<Main />
<NextScript />
</body>
</Html>
)
}
}
export default MyDocument
Error컴포넌트(에러메시지표시)도 커스터마이징해서 쓸 수 있다. (client-side , server-side 둘다 가능)
function Error({ statusCode }) {
return (
<p>
{statusCode
? `An error ${statusCode} occurred on server`
: 'An error occurred on client'}
</p>
)
}
Error.getInitialProps = ({ res, err }) => {
const statusCode = res ? res.statusCode : err ? err.statusCode : 404
return { statusCode }
}
export default Error
🐥 다시 돌아와서 학습하기!
렌더링
은 렌더링엔진을 통해 html을 DOM Tree로 구성하고 요소들을 화면에 그려주는 행위를 의미한다.
💡 💡 💡 렌더링엔진이랑 자바스크립트엔진이 하는일은 다르다!! 화면을 그려준다 와 자바스크립트를 해독하고 작업을 수행한다는 개념 잘 생각해보기!!
지난 리액트 포스트에서 SPA를 알아봤다.
SPA (Single Page Application)
서버로부터 완전한 새로운 페이지를 불러오지 않고 현재의 페이지를 동적으로 다시 작성함으로써 사용자와 소통하는 웹 애플리케이션이나 웹사이트를 말한다.
사용자와 서비스 사이의 인터렉션(
슈퍼매직
)이 많은 어플리케이션에서 DOM 렌더링을 서버사이드에서 하면 비효율적이다. (요청,,요청,,응답,,응답)
초기에 필요한 리소스들을 모두 요청해 DOM변화에 따른 렌더링을 클라이언트측에서 하는 방식의 어플리케이션을 SPA라 한다.
클라이언트사이드 렌더링
클라이언트사이드 렌더링은 DOM의 변화에 따른 렌더링을 서버로 요청을 보내지 않고 현재 클라이언트 환경에서 렌더링하는 것을 말한다.
특징
문제점
예시
서버사이드 렌더링은 DOM의 변화에 따른 렌더링작업을 서버에 요청하고 서버에서 그 요청(렌더링)을 수행한 후 최종적인 파일을 응답해주는 매커니즘을 말한다.
특징
문제점
예시
next 는 위에서 설명했듯, 리액트 프레임워크로 간단한 라우팅시스템과 서버사이드 렌더링을 지원한다.
💡 💡 💡 리액트는 javascript로 화면(DOM tree)를 구성한다.
그래서 html을 찍어보면 virtual Dom이 들어갈 태그와 화면을 구성할 태그만 존재할 뿐 비어있다.
하지만 next를 이용하면 SSR을 적용시킬 수 있다.
SSR 덕분에
SEO 최적화
를 할 수 있고미리 필요한 데이터를 로드
해서 더나은 User Experience를 제공할 수 있다.💡 사용자 인터렉션을 클라이언트 사이드 렌더링으로 구현하고, 필요에 따라 서버사이드 렌더링을 같이하면 더나은 UX와 SEO가 가능함!! (
SPA X SSR
)
즉, 초기 랜더링은 SSR, 앱 내부변화는 CSR
next SSR의 핵심 메소드!
getInitialProps 는 초기 APP 컴포넌트를 실행할 때, 맨 처음 실행된다.
이 메소드를 사옹해,
class형
: Document 컴포넌트에서 쓰일듯..!
import fetch from 'isomorphic-unfetch'
import Document from 'next/document'
class Page extends Document {
static async getInitialProps(ctx) {
const res = await fetch('https://api.github.com/repos/zeit/next.js')
const json = await res.json()
return { stars: json.stargazers_count }
}
render() {
return <div>Next stars: {this.props.stars}</div>
}
}
export default Page
ctx에는 쿼리 데이터 등 next 서버데이터 요소들이 담겨있다.
console.log() 해볼것!
function 형
import fetch from 'isomorphic-unfetch'
function Page({ stars }) {
return <div>Next stars: {stars}</div>
}
Page.getInitialProps = async ctx => {
const res = await fetch('https://api.github.com/repos/zeit/next.js')
const json = await res.json()
return { stars: json.stargazers_count }
}
export default Page
For the initial page load,
getInitialProps
will execute on the server only.getInitialProps
will only be executed on the client when navigating to a different route via the next/link component or by using next/router.