참고:
Next.js 13에서는app/디렉토리(베타)를 도입합니다. 이 새로운 디렉토리는 레이아웃, 중첩 라우트 및 기본적으로Server Components를 사용할 수 있습니다.app/안에서 레이아웃을 포함한 전체 애플리케이션의 데이터를 가져올 수 있으며, 더욱 정교한 중첩 레이아웃(데이터 가져오기를 포함한)을 지원합니다.
app/를 점진적으로 적용하는 방법에 대해 자세히 알아보세요.
Next.js는 페이지를 초기화하기 위해 App 컴포넌트를 사용합니다. 이를 재정의하여 페이지 초기화를 제어할 수 있으며 다음과 같은 작업을 수행할 수 있습니다.
App을 덮어쓰려면 다음과 같이 ./pages/_app.js 파일을 만듭니다.export default function MyApp({ Component, pageProps }) {
return <Component {...pageProps} />
}
Component prop은 활성 페이지입니다. 따라서 라우트 간에 이동할 때마다 Component가 새 페이지로 변경됩니다. 따라서 Component에 보내는 모든 props는 페이지에서 받게됩니다.
pageProps는 초기 프로퍼티가 포함된 객체입니다. 이 프로퍼티는 데이터 가져오기 메소드 중 하나로 페이지에 사전로드된 것입니다. 그렇지 않으면 빈 객체입니다.
App.getInitialProps는 context.ctx라는 단일 인수를 받습니다. 이것은 getInitialProps의 context 객체와 동일한 속성 집합의 객체입니다.
pages/_app.js가 이전에 없었다면 필요하지 않습니다.getInitialProps를 추가하면 정적 생성이 없는 페이지에서 자동 정적 최적화가 비활성화됩니다.getInitialProps를 추가할 때는 "next/app"에서 App을 가져와서 getInitialProps 내부에서 App.getInitialProps(appContext)를 호출하고 반환된 객체를 반환 값에 병합해야 합니다.App은 Next.js 데이터 가져오기 메소드(getStaticProps 또는 getServerSideProps)를 지원하지 않습니다. 전역 데이터 가져오기가 필요한 경우 app/ 디렉토리를 점진적으로 적용하는 것을 고려하세요.TypeScript를 사용하는 경우 TypeScript 문서를 참조하세요
참고:
Next.js 13은app/디렉터리를 (베타로) 도입합니다. 이 새 디렉터리는 레이아웃, 중첩된 경로 및 기본적으로 서버 컴포넌트를 사용합니다.app/내에서 루트 레이아웃을 사용하여 초기html및body태그를 수정할 수 있습니다.
app/적용에 대해 자세히 알아보기
사용자 정의 Document를 사용하면 페이지를 렌더링하는 데 사용되는 <html> 및 <body> 태그를 업데이트할 수 있습니다. 이 파일은 서버에서만 렌더링되므로 onClick과 같은 이벤트 핸들러는 _document에서 사용할 수 없습니다.
기본 Document를 재정의하려면 다음과 같이 파일 pages/_document.js를 만듭니다.
import { Html, Head, Main, NextScript } from 'next/document'
export default function Document() {
return (
<Html>
<Head />
<body>
<Main />
<NextScript />
</body>
</Html>
)
}
위 코드는 Next.js에서 추가한 기본 Document입니다. 사용자 정의 속성은 프로퍼티로 허용됩니다. 예를 들어 <html> 태그에 lang="en"을 추가할 수 있습니다.
<Html lang="en">
또는 body 태그에 className을 추가할 수 있습니다.
<body className="bg-white">
<Html>, <Head />, <Main /> 및 <NextScript />는 페이지가 올바르게 렌더링되기 위해 필요합니다.
_document에서 사용하는 <Head /> 컴포넌트는 next/head와 같지 않습니다. 여기서 사용하는 <Head /> 컴포넌트는 모든 페이지에 공통적인 <head> 코드에만 사용해야 합니다. 다른 모든 경우, 예를 들어 <title> 태그와 같은 경우, 페이지나 컴포넌트에서 next/head를 사용하는 것이 좋습니다.
<Main /> 외부의 React 컴포넌트는 브라우저에서 초기화되지 않습니다. 여기에 응용 프로그램 로직이나 사용자 정의 CSS(styled-jsx와 같은)를 추가하지 마십시오. 모든 페이지에서 공유되는 컴포넌트(메뉴 또는 툴바와 같은)가 필요한 경우, 대신 레이아웃(Layouts)을 읽으십시오.
현재 Document는 getStaticProps나 getServerSideProps와 같은 Next.js 데이터 가져오기 메서드를 지원하지 않습니다.
참고: 이 기능은
CSS-in-JS와 같은 라이브러리가 서버 측 렌더링을 지원하는 경우에만 사용하면 됩니다. 내장styled-jsx지원에는 필요하지 않습니다.
React 18 지원을 위해서는 가능하면 getInitialProps와 renderPage를 커스터마이징하지 않는 것이 좋습니다.
아래에 나오는 ctx 객체는 renderPage를 추가한 getInitialProps에서 받는 것과 동일합니다.
import Document, { Html, Head, Main, NextScript } from 'next/document'
class MyDocument extends Document {
static async getInitialProps(ctx) {
const originalRenderPage = ctx.renderPage
// React 렌더링 로직을 동기적으로 실행합니다.
ctx.renderPage = () =>
originalRenderPage({
// 전체 React 트리를 래핑하는 데 유용합니다.
enhanceApp: (App) => App,
// 각 페이지에 대해 래핑하는 데 유용합니다.
enhanceComponent: (Component) => Component,
})
// 부모 `getInitialProps`를 실행합니다. 이제 사용자 정의 `renderPage`가 포함됩니다.
const initialProps = await Document.getInitialProps(ctx)
return initialProps
}
render() {
return (
<Html>
<Head />
<body>
<Main />
<NextScript />
</body>
</Html>
)
}
}
export default MyDocument
참고:
_document의getInitialProps는 클라이언트 측 전환 중에 호출되지 않습니다.
TypeScript를 사용하는 경우 내장 DocumentContext 타입을 사용하여 파일 이름을 ./pages/_document.tsx로 변경할 수 있습니다.
import Document, { DocumentContext, DocumentInitialProps } from 'next/document'
class MyDocument extends Document {
static async getInitialProps(
ctx: DocumentContext
): Promise<DocumentInitialProps> {
const initialProps = await Document.getInitialProps(ctx)
return initialProps
}
}
export default MyDocument