레이아웃을 만들었는데 페이지 내용이 사라진 이유
문제 발생
공통 헤더를 넣으려고 레이아웃을 만들었더니 페이지 본문이 통째로 사라졌습니다.
<!-- layouts/default.vue -->
<template>
<AppHeader />
<AppFooter />
</template><slot />을 넣자 내용은 돌아왔는데, 이번에는 다른 프로젝트에서 레이아웃이 아예 적용되지 않는 경우도 만났습니다.
원인 분석
두 가지 연결이 각각 필요합니다.
첫째, 레이아웃은 <slot />으로 페이지를 그립니다. Nuxt 문서 설명대로 레이아웃은 공통 UI 패턴을 재사용 가능한 컴포넌트로 뽑아내고 <slot /> 요소를 통해 페이지 내용을 표시합니다. 슬롯이 없으면 페이지는 렌더될 자리가 없어 사라집니다 — 오류가 아니라 우리가 자리를 안 만든 것입니다.
둘째, app.vue에 <NuxtLayout>이 있어야 합니다. 문서가 명시합니다 — 레이아웃은 app.vue에 <NuxtLayout>을 추가함으로써 활성화되며, 그것이 <NuxtPage />를 감쌉니다. app.vue를 직접 만들면서 이걸 빠뜨리면 레이아웃 디렉터리가 통째로 무시됩니다.
구조 제약도 하나 있습니다 — 레이아웃은 레이아웃 전환 애니메이션을 적용할 수 있도록 단일 루트 요소를 가져야 하며, 그 루트 요소가 <slot />일 수는 없습니다.
해결 방안
- 레이아웃에 슬롯과 단일 루트를 둡니다.
<!-- layouts/default.vue -->
<template>
<div class="app-shell">
<AppHeader />
<main><slot /></main>
<AppFooter />
</div>
</template>app.vue에서 레이아웃을 켭니다.
<template>
<NuxtLayout>
<NuxtPage />
</NuxtLayout>
</template>-
기본 레이아웃 이름을 지킵니다.
~/layouts/default.vue는 별도 지정이 없을 때 자동으로 쓰이는 폴백입니다. -
페이지별로 바꿀 때는
definePageMeta를 씁니다.
<script setup>
definePageMeta({ layout: "admin" });
</script>-
레이아웃을 아예 쓰지 않는 페이지도 명시할 수 있습니다.
layout: false로 두면 그 페이지만 셸 없이 렌더됩니다 — 인쇄용 화면이나 임베드 페이지에 씁니다. -
레이아웃과 페이지의 책임을 나눕니다. 레이아웃은 셸(헤더·푸터·네비)만 담당하고 데이터 조회는 페이지가 합니다 — 레이아웃에서 요청 데이터를 읽기 시작하면 모든 페이지가 그 비용을 함께 냅니다.
댓글0
댓글을 남기려면 로그인이 필요해요. 로그인
아직 댓글이 없어요. 첫 의견을 편하게 남겨 보세요.