本章的目标是提供一个关于框架不同部分、它们的执行顺序以及它们如何协同工作的高级概述。
在服务器端,对于你的应用程序的每个初始请求,会执行以下步骤:
Nuxt 由Nitro提供支持,它是一个现代服务器引擎。
当 Nitro 启动时,它会初始化并执行 /server/plugins 目录下的插件。这些插件可以:
初始化 Nitro 服务器后,server/middleware/ 下的中间件会针对每个请求执行。中间件可用于身份验证、日志记录或请求转换等任务。
首先创建 Vue 和 Nuxt 实例。之后,Nuxt 执行其服务器插件。这包括:
unhead。app/plugins/ 目录中的自定义插件,包括那些没有后缀的(例如 myPlugin.ts)和带有 .server 后缀的(例如 myServerPlugin.server.ts)。插件以特定顺序执行,并且可能相互依赖。有关更多详细信息,包括执行顺序和并行性,请参阅插件文档。
app:created 钩子,可用于执行额外逻辑。初始化插件之后、执行中间件之前,如果 definePageMeta 函数中定义了 validate 方法,Nuxt 会调用它。validate 方法可以是同步的也可以是异步的,通常用于验证动态路由参数。
validate 函数应返回 true。false 或一个包含 statusCode 和/或 statusMessage 的对象以终止请求。有关更多信息,请参阅路由验证文档。
中间件允许你在导航到特定路由之前运行代码。它通常用于身份验证、重定向或日志记录等任务。
在 Nuxt 中,有三种类型的中间件:
Nuxt 在初始页面加载时(在服务器和客户端上)执行所有全局中间件,然后在任何客户端导航之前再次执行。命名和匿名中间件仅在相应页面组件中定义的页面(路由)元数据中的中间件属性中指定的路由上执行。
有关每种类型和示例的详细信息,请参阅中间件文档。
服务器上的任何重定向都将导致 Location: 头发送到浏览器;然后浏览器会向此新位置发起一个新请求。除非数据保存在 cookie 中,否则所有应用程序状态都将在此发生时重置。
Nuxt 在此步骤中渲染页面及其组件,并使用 useFetch 和 useAsyncData 获取任何所需的数据。由于在服务器上没有动态更新,也没有 DOM 操作发生,因此 Vue 生命周期钩子(例如 onBeforeMount、onMounted 和后续钩子)在 SSR 期间**不**执行。
默认情况下,Vue 在 SSR 期间暂停依赖跟踪以获得更好的性能。
<script setup> 的根作用域中产生需要清理的副作用代码。这种副作用的一个例子是使用 setInterval 设置计时器。在仅客户端的代码中,我们可以设置一个计时器,然后在 onBeforeUnmount 或 onUnmounted 中将其销毁。然而,由于卸载钩子在 SSR 期间永远不会被调用,计时器将永远存在。为避免这种情况,请将副作用代码移到 onMounted 中。获取所有所需数据并渲染组件后,Nuxt 将渲染的组件与 unhead 的设置结合起来,生成完整的 HTML 文档。此 HTML 以及相关数据随后发送回客户端以完成 SSR 过程。
app:rendered 钩子。render:html 钩子。此钩子允许你操作生成的 HTML,例如注入额外的脚本或修改元标签。生命周期的这一部分完全在浏览器中执行,无论你选择了哪种 Nuxt 模式。
此步骤与服务器端执行类似,包括内置插件和自定义插件。
app/plugins/ 目录中的自定义插件,例如那些没有后缀的(例如 myPlugin.ts)和带有 .client 后缀的(例如 myClientPlugin.client.ts),在客户端执行。
app:created 钩子,可用于执行额外逻辑。此步骤与服务器端执行相同,包括 definePageMeta 函数中定义的 validate 方法。
Nuxt 中间件在服务器和客户端上运行。如果你希望某些代码在特定环境中运行,可以考虑使用 import.meta.client 针对客户端和 import.meta.server 针对服务器进行拆分。
调用 app.mount('#__nuxt') 将 Vue 应用程序挂载到 DOM。如果应用程序使用 SSR 或 SSG 模式,Vue 会执行一个水合步骤,使客户端应用程序具有交互性。在水合过程中,Vue 重新创建应用程序(不包括服务器组件),将每个组件与其对应的 DOM 节点匹配,并附加 DOM 事件监听器。
为了确保正确的水合,保持服务器和客户端之间数据的一致性至关重要。对于 API 请求,建议使用 useAsyncData、useFetch 或其他 SSR 友好的组合式函数。这些方法确保在水合过程中重用服务器端获取的数据,避免重复请求。任何新请求都应在水合之后才触发,以防止水合错误。
app:beforeMount 钩子。app:mounted 钩子。与服务器不同,浏览器会执行完整的Vue 生命周期.