# Nuxt 라우팅 > **카테고리:** 핵심 개념 > **최종 수정:** 2026-05-13 > **관련:** [[nuxt-lifecycle]], [[nuxt-rendering-modes]] ## 요약 Nuxt는 `app/pages/` 디렉토리의 파일 구조를 기반으로 vue-router 라우트를 자동 생성한다. 동적 라우트, 중첩 라우트, 미들웨어를 파일 네이밍 컨벤션만으로 설정한다. --- ## 파일 기반 라우팅 ``` pages/ ├── index.vue → / ├── about.vue → /about └── posts/ ├── index.vue → /posts └── [id].vue → /posts/:id ``` > 💡 경험: `pages/` 디렉토리가 없으면 Nuxt는 vue-router를 포함하지 않음 (app.vue 단독 사용 가능). --- ## 라우트 파일 네이밍 패턴 | 파일명 | 라우트 | 설명 | |---|---|---| | `pages/index.vue` | `/` | 루트 | | `pages/about.vue` | `/about` | 정적 라우트 | | `pages/posts/[id].vue` | `/posts/:id` | 동적 파라미터 | | `pages/[...slug].vue` | `/*` | Catch-all | | `pages/[[optional]].vue` | `/` 또는 `/:optional` | 선택적 파라미터 | | `pages/user-[group]/[id].vue` | `/user-:group/:id` | 복합 동적 | ### 중첩 라우트 ``` pages/ └── parent/ ├── index.vue → /parent └── child.vue → /parent/child ``` 부모 레이아웃이 있다면 ``로 자식 라우트를 렌더링. --- ## 네비게이션 ### `` 뷰포트에 들어오면 자동으로 다음 페이지 컴포넌트와 payload를 프리패치. 전체 페이지 새로고침 없이 클라이언트 사이드 라우팅. ```vue ``` ### `navigateTo()` — 프로그래매틱 이동 ```typescript // 미들웨어나 이벤트 핸들러에서 await navigateTo('/login') await navigateTo({ path: '/search', query: { q: 'nuxt' } }) await navigateTo('https://external.com', { external: true }) ``` --- ## 라우트 파라미터 ```vue ``` --- ## 라우트 미들웨어 > ⚠️ 주의: 라우트 미들웨어는 Vue 앱의 클라이언트/서버 파트에서 실행됨. Nitro 서버의 `server/middleware/`와 다름. API 라우트(`/api/*`)에는 동작하지 않음. ### 종류 3가지 | 종류 | 위치 | 적용 범위 | |---|---|---| | **Global** | `middleware/auth.global.ts` | 모든 라우트 변경 | | **Named** | `middleware/auth.ts` | 지정한 페이지만 | | **Anonymous** | 페이지 컴포넌트 안 | 해당 페이지만 | ### Named 미들웨어 예시 ```typescript // middleware/auth.ts export default defineNuxtRouteMiddleware((to, from) => { const user = useUser() if (!user.value) { return navigateTo('/login') } }) ``` ```vue ``` ### Anonymous(Inline) 미들웨어 ```vue ``` ### 미들웨어에서 실행 흐름 제어 ```typescript export default defineNuxtRouteMiddleware((to, from) => { // 계속 진행 return // 다른 페이지로 리다이렉트 return navigateTo('/login') // 현재 라우트 abort (404 표시) return abortNavigation() // 커스텀 에러 return abortNavigation({ statusCode: 403, message: 'Forbidden' }) }) ``` --- ## 라우트 검증 (validate) ```vue ``` --- ## `definePageMeta` 주요 옵션 ```typescript definePageMeta({ layout: 'dashboard', // 레이아웃 지정 middleware: ['auth'], // 미들웨어 validate: (route) => true, // 라우트 검증 keepalive: true, // 컴포넌트 캐싱 pageTransition: { name: 'slide', mode: 'out-in' }, // 페이지 트랜지션 key: route => route.fullPath, // 컴포넌트 key 제어 }) ``` --- ## 참고 / 출처 - `reference/1.getting-started/07.routing.md` - `reference/2.directory-structure/1.app/1.middleware.md` - `reference/2.directory-structure/1.app/1.pages.md`