Nuxt 3 심화
Nuxt 3의 진가는 미들웨어, SEO 최적화, 모듈 생태계, 유연한 배포 전략에서 나타납니다. 프로덕션 레벨의 앱을 만들기 위한 심화 내용입니다.
Nuxt 3 입문에서 기본을 다뤘다면, 이번에는 실전에서 꼭 알아야 하는 고급 기능들을 정리합니다.
라우트 미들웨어
// middleware/auth.ts — 이름 있는 미들웨어
export default defineNuxtRouteMiddleware((to, from) => {
const { isAuthenticated } = useAuth()
if (!isAuthenticated.value) {
return navigateTo('/login')
}
})
<!-- pages/dashboard.vue -->
<script setup lang="ts">
definePageMeta({
middleware: 'auth' // 미들웨어 적용
})
</script>
// middleware/auth.global.ts — 전역 미들웨어 (.global 접미사)
export default defineNuxtRouteMiddleware((to) => {
// 모든 라우트에서 실행
const publicRoutes = ['/login', '/register', '/']
if (!publicRoutes.includes(to.path)) {
const { isAuthenticated } = useAuth()
if (!isAuthenticated.value) {
return navigateTo('/login')
}
}
})
SEO와 메타 태그
<script setup lang="ts">
// 페이지별 SEO 설정
useHead({
title: '대시보드 — My App',
meta: [
{ name: 'description', content: '사용자 대시보드 페이지입니다.' },
{ property: 'og:title', content: '대시보드' },
{ property: 'og:description', content: '사용자 대시보드' }
],
link: [
{ rel: 'canonical', href: 'https://example.com/dashboard' }
]
})
// 또는 useSeoMeta — 타입 안전한 SEO 메타
useSeoMeta({
title: '대시보드',
ogTitle: '대시보드 — My App',
description: '사용자 대시보드 페이지입니다.',
ogDescription: '사용자 대시보드',
ogImage: 'https://example.com/og-image.png',
twitterCard: 'summary_large_image'
})
</script>
// nuxt.config.ts — 전역 SEO 설정
export default defineNuxtConfig({
app: {
head: {
title: 'My App',
meta: [
{ charset: 'utf-8' },
{ name: 'viewport', content: 'width=device-width, initial-scale=1' },
{ name: 'description', content: '기본 설명' }
],
link: [
{ rel: 'icon', type: 'image/x-icon', href: '/favicon.ico' }
]
}
}
})
서버 미들웨어와 플러그인
// server/middleware/log.ts — 서버 미들웨어
export default defineEventHandler((event) => {
console.log(`[${new Date().toISOString()}] ${event.method} ${event.path}`)
// 응답을 반환하지 않으면 다음 핸들러로 진행
})
// server/plugins/db.ts — 서버 플러그인 (Nitro)
export default defineNitroPlugin((nitro) => {
// DB 연결 등 서버 시작 시 초기화
console.log('서버 플러그인 초기화')
})
Nuxt 모듈
// nuxt.config.ts
export default defineNuxtConfig({
modules: [
'@nuxtjs/tailwindcss', // Tailwind CSS
'@pinia/nuxt', // Pinia 상태 관리
'@nuxt/image', // 이미지 최적화
'@nuxtjs/i18n', // 국제화
'@vueuse/nuxt', // VueUse composables
],
// 모듈별 설정
i18n: {
locales: ['ko', 'en'],
defaultLocale: 'ko'
}
})
렌더링 모드
// nuxt.config.ts
export default defineNuxtConfig({
// 전역 렌더링 모드
ssr: true, // SSR 활성화 (기본값)
// 라우트별 렌더링 규칙
routeRules: {
'/': { prerender: true }, // SSG — 빌드 시 생성
'/blog/**': { swr: 3600 }, // ISR — 1시간마다 재생성
'/admin/**': { ssr: false }, // CSR — 클라이언트만
'/api/**': { cors: true }, // API CORS 설정
'/old-page': { redirect: '/new-page' } // 리다이렉트
}
})
상태 관리 — useState
Pinia 외에 Nuxt 자체의 SSR 호환 상태 관리도 있습니다.
<script setup lang="ts">
// useState — SSR에서 서버→클라이언트 상태 전달
// 서버에서 설정한 값이 클라이언트 하이드레이션 시 그대로 사용됨
const counter = useState('counter', () => 0)
const user = useState('user', () => null)
</script>
에러 처리
<!-- error.vue — 에러 페이지 -->
<script setup lang="ts">
const props = defineProps<{
error: {
statusCode: number
statusMessage: string
message: string
}
}>()
const handleClear = () => clearError({ redirect: '/' })
</script>
<template>
<div class="error-page">
<h1>{{ error.statusCode }}</h1>
<p>{{ error.message }}</p>
<button @click="handleClear">홈으로</button>
</div>
</template>
배포
// nuxt.config.ts
export default defineNuxtConfig({
// Vercel
// 별도 설정 불필요 — 자동 감지
// Cloudflare Pages
nitro: {
preset: 'cloudflare-pages'
}
// Node.js 서버
// nitro: { preset: 'node-server' }
// 정적 사이트 (SSG)
// npx nuxi generate
})
면접 팁
- Nuxt의
routeRules를 설명할 수 있으면 ** 하이브리드 렌더링 **에 대한 이해도를 보여줄 수 있습니다 useState와 Pinia의 차이: useState는 SSR 하이드레이션에 최적화된 간단한 상태 관리, Pinia는 복잡한 상태 로직에 적합- Nitro 서버 엔진이 다양한 플랫폼으로 배포 가능한 이유를 설명할 수 있으면 좋습니다
요약
Nuxt 3의 심화 기능은 미들웨어(인증/로깅), SEO(useHead/useSeoMeta), 모듈 생태계, routeRules를 통한 하이브리드 렌더링으로 구성됩니다. Nitro 서버 엔진 덕분에 Vercel, Cloudflare, Node.js 등 다양한 플랫폼에 배포할 수 있습니다.
댓글 로딩 중...