[Next.js V13] 정리 노트 - 1

Next JS 기초 개념 정리

Intro


Intro


  • 현재 블로그 또한 Next.js를 이용해 만들어졌지만 만든 시점은 12버전이었다. 당시 사전 지식 없이 무작정 만들다보니 부족한 부분이 보였고 블로그 업데이트가 필요하다고 느꼈다. 이 기회를 빌려 Next.js에 대해 알아보도록 해야겠다.
  • Next beta Docs를 참조하시면 더욱 도움이 됩니다.

I 준비사항


아래와 같은 환경이 구성되어있어야 합니다.

  • Node.js 16.8 이상의 버전

I-I 프로젝트 설정하기

프로젝트는 다음과 같이 구성하겠습니다. npx의 경우 node 설치 시 기본적으로 같이 설치가 진행됩니다.

bash
> npx create-next-app@13.1.1 --experimental-app
Need to install the following packages:
  create-next-app@13.1.1
Ok to proceed? (y) y
✔ What is your project named? … opentablenextjs
✔ Would you like to use TypeScript with this project? … No / Yes
✔ Would you like to use ESLint with this project? … No / Yes
Creating a new Next.js app in /Users/wooglim/dev/nextPractice/opentablenextjs.

또한 Typescript를 기본 언어로 사용하겠습니다.

프로젝트 구성 완료 시 package.json을 보시면 다음과 같이 script가 작성되어 있습니다. 일단 npm run dev명령을 입력해 서버를 실행해 봅시다.

json
// package.json
"scripts": {
    "dev": "next dev",
    "build": "next build",
    "start": "next start",
    "lint": "next lint"
  }

npm run dev입력

bash
> npm run dev

브라우저에서 접속하면 다음과 같은 페이지가 보입니다. 해당 루트 페이지의 경로는 /app/page.tsx입니다.

npm run dev

app폴더 부분에서 가장 많은 작업이 일어날 것입니다. global.css 및 레이아웃을 주로 구성할테니 말이죠.

I-II 유용한 CSS 라이브러리 설치하기


페이지 작업 시 CSS를 직접 작성하는건 매우 어렵습니다.. 제 기준에서는요, 그래서 tailwindcss를 이용하겠습니다.

설치는 공식문서와 같이 진행합니다. 버전은 알아보신 후 명시하시길 권장드립니다. 우선dev종속성을 갖도록 설정하겠습니다.

bash
> npm install -D tailwindcss@3.2.4 postcss@8.4.20 autoprefixer@10.4.13

다음으로 초기화가 필요합니다. 이후 폴더를 보시면 tailwind.config.js, postcss.config.js가 추가될겁니다.

bash
> npx tailwindcss init -p

이후 tailwind.config.js에 다음과 같이 설정해줍니다. app폴더내 모든 디렉토리에 포함된 js,ts,jsx,tsx파일은 tailwindcss를 사용할 수 있게됩니다.

js
// tailwind.config.js

/** @type {import('tailwindcss').Config} */
module.exports = {
  // tailwind CSS 를 적용할 경로를 app폴더내 모든 디렉토리내 js,ts,jsx,tsx파일에 적용
  content: ["./app/**/*.{js,ts,jsx,tsx}"],
  theme: {
    extend: {},
  },
  plugins: [],
}

추가로 app/global.css파일 루트에 다음과 같이 Tailwind의 레이어에 대한 지시문을 파일에 추가합니다.

css
@tailwind base;
@tailwind components;
@tailwind utilities;

여기까지입니다. 이제 app 폴더내 js,ts,jsx,tsx 파일에서 tailwindCSS를 온전히 사용할 수 있게됩니다. 다음과 같이 공식문서를 보시면 적용할 수 있는 스타일을 조회할 수 있습니다.

tailwindCSS

폰트 크기도 달라지게 되므로 다음과 같이 tailwind.config.js에 폰트 사이즈를 지정할 수 있습니다. 이후 사용 시 태그 className(눈치채셨겠지만 React를 따릅니다.) 속성에 text-설정명과 같이 적용할 수 있습니다.

js
// tailwind.config.js
/** @type {import('tailwindcss').Config} */
module.exports = {
  // tailwind CSS 를 적용할 경로를 app폴더내 모든 디렉토리내 js,ts,jsx,tsx파일에 적용
  content: ["./app/**/*.{js,ts,jsx,tsx}"],
  theme: {
    extend: {},
    fontSize: {
      "2xsm": "10px",
      xsm: "12px",
      sm: "13px",
      reg: "15px",
      lg: "18px",
      "2xl": "22px",
      "3xl": "25px",
      "4xl": "32px",
      "5xl": "40px",
      "6xl": "50px",
      "7xl": "70px"
    }
  },
  plugins: [],
}

I-III 파일 기반 라우팅


Next JS는 파일 기반 라우팅을 따릅니다. 그리고 루트 페이지인 App/page.tsx경로는 도메인을 입력하면 렌더링 됩니다. 만일 locahost:3000/search와 같은 경로를 찾는다면 다음과 같은 폴더 트리 구조를 형성해야합니다.

text
  > APP[Folder]
    page.tsx
    > search[Folder]
      page.tsx
    > restaurant[Folder]
      > shakeshack[Folder]
        page.tsx

localhost:3000을 요청하면 App/page.tsx를 렌더링 하고 localhost:3000/search를 요청하면App/search/page.tsx를 렌더링합니다. 간단히 라우팅이 가능하지만 단점으로는 변경할 수 없습니다. 만일 동적인 라우팅이 가능하도록 하고 싶다면 아래와 같이 []로 묶어 경로를 설정합니다.

text
  > APP[Folder]
    page.tsx
    > search[Folder]
      page.tsx
    > restaurant[Folder]
      > [name][Folder]
        page.tsx

혹은 아래와 같이 slug를 설정하는 것이 대표적입니다. 찾는 경로에 따라 해당 디렉토리 경로로 이동하는 것이죠.

text
  > APP[Folder]
    page.tsx
    > search[Folder]
      page.tsx
    > restaurant[Folder]
      > [slug][Folder]
        page.tsx

I-IV 링크 구성 하기


HTML의 a태그와 같이 Link태그로 링크를 연결할 수 있습니다. 특정 버튼을 누르면 파일 기반 라우팅을 이용해 홈으로 이동할 수 있고, 타 메뉴 이동이 가능하죠. 다음 코드와 같다면 localhost:port즉 홈 경로로 이동할 것입니다.

tsx
import Link from "next/link"

<Link href="/" className="font-bold text-gray-700 text-2xl">
  Home
</Link>

Link태그는 a태그를 제외한 태그를 감쌀 수 있습니다. a태그의 스타일은 적용하지 않습니다. 어떠한 경로에 있는 파일(menu/page.tsx) 여도, Link 태그의 시작지점은 초기 도메인(루트 프로젝트 경로)입니다. 때문에 menu/page.tsx 페이지에서 restaurant/[slug]/page.tsx를 탐색하고 싶다면 Link태그 href속성으로 /restaurant/동적인 값만 입력해주면 됩니다.

I-V Hook 맛보기


먼저 훅을 대부분 클라이언트에서 작동하므로 page.tsx상단에 서버 구성 요소를 클라이언트 요소로 바꾸기 위해 "use client"를 입력해줍니다.

tsx
// page.tsx
"use client"

import Image from 'next/image'
import { Inter } from '@next/font/google'
import styles from './page.module.css'
import Link from 'next/link'
import {useRouter} from "next/navigation"
import { useState } from 'react'

const inter = Inter({ subsets: ['latin'] })

export default function Home() {
  const router = useRouter();
  const [location, setLocation] = useState("");

이후에는 useRouter, userState등 클라이언트에서 온전히 사용할 수 있게됩니다.
두개의 훅을 사용해 다음과 같이 검색을 구현할 수 있습니다. 버튼을 클릭하면 search구문이 url에 붙게됩니다.

tsx
<div className="text-left text-lg py-3 m-auto flex justify-center">
  <input
    className="rounded  mr-3 p-2 w-[450px]"
    type="text"
    placeholder="State, city or town"
    value={location}
    onChange={(e) => setLocation(e.target.value)}
  />
  <button className="rounded bg-red-600 px-9 py-2 text-white" onClick={() => {
    if(location === "banana") return;
    router.push("/search");
  }}>
    Let's go
  </button>
</div>