TIL: Next.js (6) Dynamic URL - 220621

Lumpen·2022년 6월 21일
0

TIL

목록 보기
59/242

Next.js

DynamicURL

URL에 변수를 넣을 수 있다
/:변수 로

next.js에서는 따로 router를 설정하지 않기 때문에
폴더와 파일의 이름으로 설정한다

/movies 로 접속하면
movies/index.tsx로 가게되고
movies/all로 접속하면 movies/all.tsx 로 가게된다

next.js는 폴더 구조가 중첩 라우터 같은 기능을 해준다
페이지가 하나밖에 없다면 폴더로 만들어주지 않아도 된다

URL의 변수를 사용하려면 대괄호를 사용하여 movies/[변수명].tsx 로 만들어준다
/movies/변수명 주소로 접속하는 것과 같은 것

useRouter() 를 사용하면
query 프로퍼티에 queryString이 들어있다

// pages/movies/[id].tsx
import { useRouter } from "next/router";

export default function Detail() {
  const router = useRouter();
  console.log(router);
  return "detail";
}


Link, a 태그로 텍스트를 감싸주고 Link에 herf 설정
a태그 내에는 div 등이 들어갈 수 없다
-> router hook 을 이용해 navigating을 해준다

// pages/index.tsx

export default function Home({ results }: Props) {
  const router = useRouter();
  const onClick = (id: number) => {
    router.push(`/movies/${id}`);
  };
  return (
    <div className="container">
      <SEO title="Home" />
      <h1 className="active">Hello</h1>

      {results?.map((movie) => (
        <div onClick={() => onClick(movie.id)} className="movie" key={movie.id}>
          <img src={`https://image.tmdb.org/t/p/w500/${movie.poster_path}`} />
          <h4>
            <Link href={`/movies/${movie.id}`}>
              <a>{movie.original_title}</a>
            </Link>
          </h4>
        </div>
      ))}
    </div>
  );
}

router.push()를 이용할 때 api key가 노출되므로 rewrites() 를 해준다

source와 destination의 변수명을 같게 설정해줘야 함

// next.config.js

async rewrites() {
    return [
      {
        source: "/api/movies",
        destination: `https://api.themoviedb.org/3/movie/popular?api_key=${API_KEY}`,
      },
      {
        source: "/api/movies/:id",
        destination: `https://api.themoviedb.org/3/movie/:id?api_key=${API_KEY}`
      }
    ];
  },

useRouter()

URL에 정보를 숨겨서 보낼 수 있다
URL -> URL 로 state를 넘겨주고, 숨길 수 있다

  1. router.push에 params객체로 값을 넘겨준다
  2. as에 설정한 값으로 URL 마스킹
    -> URL은 마스킹 되지만 데이터는 router.query안에 객체 형식으로 :id 다음에 담겨있음
  3. Link 태그의 href, as 를 설정한다
// pages/index.tsx 
	const router = useRouter();
 const onClick = (id: number) => {
    router.push(
      {
        pathname: `/movies/${id}`,
        query: {},
      },
      `/movies/${id}`
    );
  };
// pages/index.tsx
export default function Home({ results }: Props) {
  const router = useRouter();
  const onClick = (id: number, title: string) => {
    router.push(
      {
        pathname: `/movies/${id}`,
        query: {
        	title, // router 객체의 query에 담긴다
        },
      },
      `/movies/${id}`
    );
  };
  return (
    <div className="container">
      <SEO title="Home" />
      <h1 className="active">Hello</h1>

      {results?.map((movie) => (
        <div
          onClick={() => onClick(movie.id, movie.original_title)}
          className="movie"
          key={movie.id}
        >
          <img src={`https://image.tmdb.org/t/p/w500/${movie.poster_path}`} />
          <h4>
             <Link
              href={{
                pathname: `/movies/${movie.id}`,
                query: {
                  title: movie.original_title,
                },
              }}
              as={`/movies/${movie.id}`}
            >
              <a>{movie.original_title}</a>
            </Link>
          </h4>
        </div>
      ))}
    </div>
  );
}

// pages/movies/[id].tsx

import { useRouter } from "next/router";

export default function Detail() {
  const router = useRouter();
  return (
    <div>
      <h4>{router.query.title || "Loading..."}</h4>
    </div>
  );
}
profile
떠돌이 생활을 하는. 실업자는 아니지만, 부랑 생활을 하는

0개의 댓글