页面和布局
了解如何从 Nuxt 2 迁移到 Nuxt 3 的页面和布局。
app.vue
Nuxt 3 通过 ~/app.vue 为你的应用提供了一个中心入口点。
app.vue 文件,Nuxt 将使用它自己默认的版本。
::这个文件非常适合放置任何需要在应用启动时运行一次的代码,以及出现在应用每个页面上的任何组件。例如,如果你只有一个布局,你可以将其移入 app.vue。迁移
考虑创建一个 app.vue 文件,并包含任何需要在应用顶层运行一次的逻辑。你可以在此查看一个示例。
布局
如果你的应用对多个页面使用了布局,则只需要做稍微的改动。
在 Nuxt 2 中,<Nuxt> 组件用于布局中以渲染当前页面。在 Nuxt 3 中,布局改用插槽(slot),因此你需要将该组件替换为 <slot />。这也允许了使用具名插槽和作用域插槽的高级用例。阅读更多关于布局的内容。
你还需要更改你定义页面所使用的布局的方式,使用 definePageMeta 编译器宏。布局名将采用 kebab-case(短横线命名)。因此 app/layouts/customLayout.vue 在你的页面中引用时变为 custom-layout。
迁移
- 将
<Nuxt />替换为<slot />app/layouts/custom.vue<template> <div id="app-layout"> <main> - <Nuxt /> + <slot /> </main> </div> </template> - 使用
definePageMeta来选择你的页面使用的布局。app/pages/index.vue+ <script setup> + definePageMeta({ + layout: 'custom' + }) - <script> - export default { - layout: 'custom' - } </script> - 将
~/layouts/_error.vue移动到~/error.vue。参见错误处理文档。如果你想确保该页面使用某个布局,可以在error.vue中直接使用<NuxtLayout>:error.vue<template> <div> <NuxtLayout name="default"> <!-- --> </NuxtLayout> </div> </template>
页面
Nuxt 3 附带了一个可选的 vue-router 集成,它由源目录中是否存在 app/pages/ 目录来触发。如果你只有一个页面,可以考虑将其移入 app.vue 以获得更轻量的构建。
动态路由
在 Nuxt 3 中定义动态路由的格式与 Nuxt 2 略有不同,因此你可能需要重命名 app/pages/ 中的一些文件。
- 你之前使用
_id来定义动态路由参数,现在改为使用[id]。 - 你之前使用
_.vue来定义全捕获(catch-all)路由,现在改为使用[...slug].vue。
嵌套路由
在 Nuxt 2 中,你会使用 <Nuxt> 和 <NuxtChild> 定义任何嵌套路由(包含父组件和子组件)。在 Nuxt 3 中,它们已被单一的 <NuxtPage> 组件所取代。
页面键和 Keep-alive 属性
如果你之前向 <Nuxt> 传递了自定义页面键或 keep-alive 属性,现在将使用 definePageMeta 来设置这些选项。
页面和布局过渡
如果你之前在组件选项中直接定义了页面或布局的过渡,现在需要使用 definePageMeta 来设置过渡。自 Vue 3 起,-enter 和 -leave CSS 类已被重命名。当在 <slot> 上使用 <Nuxt> 的 style 属性时,它不再适用于过渡,因此将样式移到你的 -active 类中。
迁移
- 重命名任何带有动态参数的页面以匹配新格式。
- 将
<Nuxt>和<NuxtChild>更新为<NuxtPage>。 - 如果你正在使用 Composition API,也可以将
this.$route和this.$router迁移为使用useRoute和useRouter组合式函数。
示例:动态路由
- URL: /users
- Page: /pages/users/index.vue
- URL: /users/some-user-name
- Page: /pages/users/_user.vue
- Usage: params.user
- URL: /users/some-user-name/edit
- Page: /pages/users/_user/edit.vue
- Usage: params.user
- URL: /users/anything-else
- Page: /pages/users/_.vue
- Usage: params.pathMatch
- URL: /users
- Page: /pages/users/index.vue
- URL: /users/some-user-name
- Page: /pages/users/[user].vue
- Usage: params.user
- URL: /users/some-user-name/edit
- Page: /pages/users/[user]/edit.vue
- Usage: params.user
- URL: /users/anything-else
- Page: /pages/users/[...slug].vue
- Usage: params.slug
示例:嵌套路由和 definePageMeta
<template>
<div>
<NuxtChild
keep-alive
:keep-alive-props="{ exclude: ['modal'] }"
:nuxt-child-key="$route.slug"
/>
</div>
</template>
<script>
export default {
transition: 'page', // 或 { name: 'page' }
}
</script>
<template>
<div>
<NuxtPage />
</div>
</template>
<script setup lang="ts">
// 这个编译器宏在 <script> 和 <script setup> 中都能工作
definePageMeta({
// 你也可以传入字符串或 computed 属性
key: route => route.slug,
transition: {
name: 'page',
},
keepalive: {
exclude: ['modal'],
},
})
</script>
<NuxtLink> 组件
全局的 NuxtLink 组件的语法和功能大部分相同。如果你之前使用快捷的 <NLink> 格式,应该将其更新为使用 <NuxtLink>。
<NuxtLink> 现在是所有链接的即插即用替代品,即使是外部链接也是如此。你可以阅读更多关于它的内容,以及如何扩展它来提供你自己的链接组件。
编程式导航
当从 Nuxt 2 迁移到 Nuxt 3 时,你将不得不更新你以编程方式导航用户的方式。在 Nuxt 2 中,你可以通过 this.$router 访问底层的 Vue Router。在 Nuxt 3 中,你可以使用 navigateTo() 工具方法,它允许你将一个路由和参数传递给 Vue Router。
await(等待)navigateTo,或者通过在函数中返回其结果来链式调用它。<script>
export default {
methods: {
navigate () {
this.$router.push({
path: '/search',
query: {
name: 'first name',
type: '1',
},
})
},
},
}
</script>
<script setup lang="ts">
function navigate () {
return navigateTo({
path: '/search',
query: {
name: 'first name',
type: '1',
},
})
}
</script>