首页 >web前端 >js教程 >Nuxt.js 实际应用:Vue.js 服务器端渲染框架

Nuxt.js 实际应用:Vue.js 服务器端渲染框架

Mary-Kate Olsen
Mary-Kate Olsen原创
2024-12-31 06:35:10259浏览

Nuxt.js in action: Vue.js server-side rendering framework

创建 Nuxt.js 项目

首先,确保您已经安装了 Node.js 和 YARN 或 NPM。然后,通过命令行创建一个新的 Nuxt.js 项目:

yarn create nuxt-app my-nuxt-project
cd my-nuxt-project

在创建过程中,您可以选择是否需要UI框架、预处理器等选项,并根据需要进行配置。

目录结构

Nuxt.js遵循特定的目录结构,部分关键目录如下:

├── .nuxt/ # Automatically generated files, including compiled code and configuration
├── assets/ # Used to store uncompiled static resources, such as CSS, images, fonts
├── components/ # Custom Vue components
├── layouts/ # Application layout files, defining the general structure of the page
│ └── default.vue # Default layout
├── middleware/ # Middleware files
├── pages/ # Application routes and views, each file corresponds to a route
│ ├── index.vue # Default homepage
│ └── [slug].vue # Dynamic routing example
├── plugins/ # Custom Vue.js plugins
├── static/ # Static resources, will be copied to the output directory as is
├── store/ # Vuex state management file
│ ├── actions.js # Vuex actions
│ ├── mutations.js # Vuex mutations
│ ├── getters.js # Vuex getters
│ └── index.js # Vuex store entry file
├── nuxt.config.js # Nuxt.js configuration file
├── package.json # Project dependencies and scripts
└── yarn.lock # Or npm.lock, record dependency versions
  • .nu​​xt/:该目录是自动生成的,包含编译后的代码。一般不需要直接修改。
  • asset/:存放未编译的静态资源,如CSS、JavaScript、图片等。 Nuxt.js 将在构建期间处理这些资源。
  • Components/:存储可以在应用程序的不同部分重用的自定义 Vue 组件。
  • layouts/:定义页面的布局。可以有一个默认布局或多个特定布局。
  • page/:每个文件对应一个路由,文件名就是路由名。动态路由用方括号[]表示。
  • middleware/: 放置自定义中间件,可以在页面渲染前后执行逻辑。
  • plugins/: Vue.js 插件的自定义入口文件。
  • static/:不做任何处理,直接复制到构建输出目录,常用于存放robots.txt或favicon.ico等
  • store/:Vuex 状态管理目录,存储 actions、mutations、getters 以及整个 store 的入口文件。
  • nuxt.config.js:Nuxt.js配置文件,用于自定义项目设置。
  • package.json:项目依赖和脚本配置。
  • yarn.lock 或 npm.lock:记录项目依赖的准确版本,以保证不同环境下依赖的一致性。

页面渲染

在pages/目录下创建一个index.vue文件。这是应用程序的主页:

<!-- pages/index.vue -->
<template>
  <div>
    <h1>Hello from Nuxt.js SSR</h1>
    <p>{{ message }}</p>
  </div>
</template>

<script>
export default {
  data() {
    return {
      message: 'This content is server-rendered!'
    };
  },
  asyncData() {
    // Here you can get data on the server side
    // The returned data will be used as the default value of data
    return { message: 'Data fetched on server' };
  }
};
</script>

Nuxt.js页面渲染的过程分为两个主要阶段:服务器端渲染(SSR)和客户端渲染(CSR)。以下是Nuxt.js页面渲染的详细步骤:

初始化:

用户在浏览器中输入URL并向服务器发送请求。

服务器收到请求后,开始处理。

路线分辨率:

Nuxt.js 使用 nuxt.config.js 中的路由配置(如果存在)或自动从pages/目录生成路由。

识别对应的页面文件,如pages/index.vue或pages/about.vue。

数据预取:

Nuxt.js 在页面组件中查找 asyncData 或 fetch 方法(如果存在)。

这些方法将在服务器端运行,以从 API 或其他数据源获取数据。

获取到数据后,会序列化并注入到页面模板中

模板渲染:

Nuxt.js 使用 Vue.js 的渲染引擎将组件和预取的数据转换为 HTML 字符串。
HTML 字符串包含客户端所需的所有初始数据,内联在 <script> 中。 JSON 格式的标签。</script>

返回 HTML:

服务器将生成的 HTML 响应发送回客户端(浏览器)。

客户端初始化:

浏览器收到 HTML 后,开始解析并执行内联 JavaScript。
Nuxt.js 客户端库 (nuxt.js) 已加载并初始化。

客户端渲染:

客户端库接管渲染,创建 Vue.js 实例,并将数据从内联 JSON 注入到 Vue 实例中。
页面完成初始渲染,用户可以看到完整的页面内容。
此时,页面是交互式的,用户可以触发事件并进行导航。

后续导航:

当用户导航到其他页面时,Nuxt.js 使用客户端路由(Vue Router)进行无刷新跳转。
如果新页面需要数据,则 asyncData 或 fetch 方法将在客户端运行,获取新数据并更新视图。

SSG(静态站点生成):

在开发之外,您可以使用 nuxtgenerate 命令生成静态 HTML 文件。

每个页面都将预渲染为一个单独的 HTML 文件,其中包含所有必要的数据和资源。

使用异步数据

asyncData 方法是 Nuxt.js 独有的,允许您在服务器上预取数据并在客户端上重用它。在上面的示例中,我们只是更改了 message 的值,但在实际应用中,您可能会在这里调用 API 来获取数据。

中间件

中间件(Middleware)是一个功能,可以让你在路由改变之前和之后执行特定的逻辑。中间件可以在全局、页面级别或布局级别使用,以处理身份验证、数据预加载、路由防护等任务。

1. 全局中间件

全局中间件在 nuxt.config.js 文件中配置,并影响应用程序中的所有页面:

yarn create nuxt-app my-nuxt-project
cd my-nuxt-project

中间件文件通常位于middleware/目录下,如middleware/globalMiddleware1.js:

├── .nuxt/ # Automatically generated files, including compiled code and configuration
├── assets/ # Used to store uncompiled static resources, such as CSS, images, fonts
├── components/ # Custom Vue components
├── layouts/ # Application layout files, defining the general structure of the page
│ └── default.vue # Default layout
├── middleware/ # Middleware files
├── pages/ # Application routes and views, each file corresponds to a route
│ ├── index.vue # Default homepage
│ └── [slug].vue # Dynamic routing example
├── plugins/ # Custom Vue.js plugins
├── static/ # Static resources, will be copied to the output directory as is
├── store/ # Vuex state management file
│ ├── actions.js # Vuex actions
│ ├── mutations.js # Vuex mutations
│ ├── getters.js # Vuex getters
│ └── index.js # Vuex store entry file
├── nuxt.config.js # Nuxt.js configuration file
├── package.json # Project dependencies and scripts
└── yarn.lock # Or npm.lock, record dependency versions

2.页面级中间件

页面级中间件仅影响特定页面。在页面组件中声明中间件:

yarn create nuxt-app my-nuxt-project
cd my-nuxt-project

对应的中间件文件位于middleware/目录下,例如middleware/pageMiddleware.js:

├── .nuxt/ # Automatically generated files, including compiled code and configuration
├── assets/ # Used to store uncompiled static resources, such as CSS, images, fonts
├── components/ # Custom Vue components
├── layouts/ # Application layout files, defining the general structure of the page
│ └── default.vue # Default layout
├── middleware/ # Middleware files
├── pages/ # Application routes and views, each file corresponds to a route
│ ├── index.vue # Default homepage
│ └── [slug].vue # Dynamic routing example
├── plugins/ # Custom Vue.js plugins
├── static/ # Static resources, will be copied to the output directory as is
├── store/ # Vuex state management file
│ ├── actions.js # Vuex actions
│ ├── mutations.js # Vuex mutations
│ ├── getters.js # Vuex getters
│ └── index.js # Vuex store entry file
├── nuxt.config.js # Nuxt.js configuration file
├── package.json # Project dependencies and scripts
└── yarn.lock # Or npm.lock, record dependency versions

3.布局级中间件

布局级中间件与页面级类似,但它适用于所有使用布局的页面。在布局组件中声明中间件:

<!-- pages/index.vue -->
<template>
  <div>
    <h1>Hello from Nuxt.js SSR</h1>
    <p>{{ message }}</p>
  </div>
</template>

<script>
export default {
  data() {
    return {
      message: 'This content is server-rendered!'
    };
  },
  asyncData() {
    // Here you can get data on the server side
    // The returned data will be used as the default value of data
    return { message: 'Data fetched on server' };
  }
};
</script>

对应的中间件文件位于middleware/目录:

// nuxt.config.js
export default {
// ...
    router: {
        middleware: ['globalMiddleware1', 'globalMiddleware2'] // can be a string array
    }
};

中间件上下文

中间件函数接收一个上下文对象作为参数,其中包含以下属性:

  • req(HTTP请求对象,仅在服务器端有效)

  • res(HTTP响应对象,仅在服务器端有效)

  • redirect(用于重定向的函数)

  • app(Vue 实例)

  • 路线(当前路线信息)

  • store(Vuex 商店,如果启用)

  • payload(如果有asyncData返回的数据)

中间件可以顺序执行,每个中间件都可以通过重定向功能决定是继续执行链中的下一个中间件还是中断路由。

动态路由

Nuxt.js支持动态路由,这对于处理博客文章、用户个人资料等具有动态ID的内容非常有用。在pages/目录中创建动态路由文件,例如[id].vue:

// middleware/globalMiddleware1.js
export default function (context) {
    // context contains information such as req, res, redirect, app, route, store, etc.
    console.log('Global Middleware 1 executed');
}

这里的[id]代表一个动态参数,asyncData会自动处理这个参数并获取对应ID的博文。

布局
布局允许您定义全局或特定页面的通用结构。在layouts/目录下创建default.vue文件:

// pages/about.vue
export default {
    middleware: 'pageMiddleware' // can be a string or a function
};

默认情况下,所有页面都将使用此布局。如果你想为特定页面设置不同的布局,可以在页面组件中指定:

// middleware/pageMiddleware.js
export default function (context) {
    console.log('Page Middleware executed');
}

插件和库集成
Nuxt.js 支持 Vue.js 插件,您可以在 nuxt.config.js 中配置:

// layouts/default.vue
export default {
    middleware: ['layoutMiddleware1', 'layoutMiddleware2']
};

然后在plugins/目录下创建对应的文件,如vuetify.js:

// middleware/layoutMiddleware1.js
export default function (context) {
    console.log('Layout Middleware 1 executed');
}

// middleware/layoutMiddleware2.js
export default function (context) {
    console.log('Layout Middleware 2 executed');
}

配置与优化

Nuxt.js 配置文件 (nuxt.config.js)

nuxt.config.js 是 Nuxt 应用程序的主要配置文件,用于自定义应用程序的行为。以下是一些常用的配置项:

  • mode:设置应用程序的运行模式。可选值为'spa'(单页应用)、'universal'(服务器端渲染)和'static'(静态生成)。默认为“通用”。
  • head:配置页面的部分,如标题、元数据、链接等
  • css:指定全局CSS文件,可以是文件路径数组
  • build:配置构建过程,例如transpile、extractCSS、extend等。例如,您可以在此处添加Babel插件或调整Webpack配置。
  • router:自定义路由配置,如基本路径、模式等
  • axios:配置axios模块,包括基础URL、代理设置等
  • plugins:注册全局Vue插件,可以指定在客户端或者服务端加载。
  • modules:加载外部模块,如@nuxtjs/axios、@nuxtjs/proxy等
  • env:定义环境变量,该变量将在构建时注入到客户端和服务器中。
yarn create nuxt-app my-nuxt-project
cd my-nuxt-project

优化策略

  • 异步数据预取(asyncData/fetch):使用asyncData或fetch方法在服务器端预取数据,以减轻客户端渲染的负担。
  • 代码拆分:Nuxt.js 自动拆分代码,确保只有在访问路由时才加载相关代码。
  • 静态站点生成(SSG):使用 nuxtgenerate 命令生成静态 HTML 文件,适合内容变化不频繁的站点,提高加载速度和 SEO 友好性。
  • 缓存策略:使用ETag、Last-Modified等HTTP缓存策略,减少重复请求。
  • Vue.js 优化:确保Vue组件的优化,比如避免无用的watchers、使用v-once减少重新渲染等
  • 图片优化:使用正确的图片格式(如WebP),保证图片大小合适,使用延迟加载技术。
  • Service Worker:集成 PWA 支持并使用 Service Worker 进行离线缓存和推送通知。
  • Tree Shaking:确保您的依赖项支持 Tree Shaking 以删除未使用的代码。
  • 分析与监控:使用 nuxt build --analyze 或集成第三方工具(如 Google Lighthouse)进行性能分析,持续监控应用性能。

静态站点生成 (SSG)

Nuxt.js 的静态站点生成(SSG)是通过 nuxtgenerate 命令实现的。该命令遍历应用程序的路由并为每个路由生成一个预渲染的 HTML 文件,该文件可以直接部署到任何静态文件托管服务。以下是有关 SSG 的一些要点:

1。配置:在nuxt.config.js文件中,可以配置generate选项来控制静态生成的行为:

yarn create nuxt-app my-nuxt-project
cd my-nuxt-project

2。生成:运行npm rungenerate或yarngenerate来启动静态生成过程。 Nuxt.js会根据generate.routes中的配置生成相应的HTML文件。如果没有显式定义,会自动扫描pages/目录下的所有文件生成路由。

3。数据预取:在页面组件中,可以使用asyncData或fetch方法来预取数据。这些数据会在生成静态页面时注入到 HTML 中,这样客户端加载时页面不需要额外的请求:

├── .nuxt/ # Automatically generated files, including compiled code and configuration
├── assets/ # Used to store uncompiled static resources, such as CSS, images, fonts
├── components/ # Custom Vue components
├── layouts/ # Application layout files, defining the general structure of the page
│ └── default.vue # Default layout
├── middleware/ # Middleware files
├── pages/ # Application routes and views, each file corresponds to a route
│ ├── index.vue # Default homepage
│ └── [slug].vue # Dynamic routing example
├── plugins/ # Custom Vue.js plugins
├── static/ # Static resources, will be copied to the output directory as is
├── store/ # Vuex state management file
│ ├── actions.js # Vuex actions
│ ├── mutations.js # Vuex mutations
│ ├── getters.js # Vuex getters
│ └── index.js # Vuex store entry file
├── nuxt.config.js # Nuxt.js configuration file
├── package.json # Project dependencies and scripts
└── yarn.lock # Or npm.lock, record dependency versions

4。中间件处理:SSG过程中不会执行服务器端中间件,因为SSG在没有服务器环境的情况下生成静态文件。因此,如果生成时需要执行一些逻辑,最好在 asyncData 或 fetch 中处理。

5。部署:生成的静态文件可以部署到任何静态文件托管服务,例如 Netlify、Vercel、GitHub Pages 或 AWS S3。这些服务通常不需要运行任何服务器端代码,只需上传生成的 dist 文件夹即可。

6。 SEO 优化:SSG 改进了 SEO,因为搜索引擎爬虫可以读取预渲染的 HTML 内容,而无需等待 JavaScript 执行。

7。动态路由:对于动态路由,Nuxt.js 将尝试生成所有可能的组合。如果无法预测所有可能的动态路由,可以在generate.routes中手动指定,或者使用generate.includePaths和generate.excludePaths进行控制。

8。 404页面:将generate.fallback设置为true将为未预渲染的动态路由生成404页面。当用户访问这些路由时,Nuxt.js 会尝试在客户端渲染它们。

运行 nuxtgenerate 命令,Nuxt.js 将生成静态 HTML 文件。

验证和错误处理

验证

验证通常涉及表单数据或 API 请求的输入验证。 Nuxt.js 本身不直接提供验证库,但你可以集成第三方库如 Vuelidate、vee-validate,或者使用 TypeScript 进行类型检查。

使用 Vee-Validate
1.安装:首先需要安装vee-validate库:

yarn create nuxt-app my-nuxt-project
cd my-nuxt-project

2。配置:在nuxt.config.js中添加Vue插件配置:

├── .nuxt/ # Automatically generated files, including compiled code and configuration
├── assets/ # Used to store uncompiled static resources, such as CSS, images, fonts
├── components/ # Custom Vue components
├── layouts/ # Application layout files, defining the general structure of the page
│ └── default.vue # Default layout
├── middleware/ # Middleware files
├── pages/ # Application routes and views, each file corresponds to a route
│ ├── index.vue # Default homepage
│ └── [slug].vue # Dynamic routing example
├── plugins/ # Custom Vue.js plugins
├── static/ # Static resources, will be copied to the output directory as is
├── store/ # Vuex state management file
│ ├── actions.js # Vuex actions
│ ├── mutations.js # Vuex mutations
│ ├── getters.js # Vuex getters
│ └── index.js # Vuex store entry file
├── nuxt.config.js # Nuxt.js configuration file
├── package.json # Project dependencies and scripts
└── yarn.lock # Or npm.lock, record dependency versions

3。创建插件:在plugins/vee-validate.js中配置Vee-Validate:

<!-- pages/index.vue -->
<template>
  <div>
    <h1>Hello from Nuxt.js SSR</h1>
    <p>{{ message }}</p>
  </div>
</template>

<script>
export default {
  data() {
    return {
      message: 'This content is server-rendered!'
    };
  },
  asyncData() {
    // Here you can get data on the server side
    // The returned data will be used as the default value of data
    return { message: 'Data fetched on server' };
  }
};
</script>

4。用法:在组件中使用 Vee-Validate 进行表单验证:

// nuxt.config.js
export default {
// ...
    router: {
        middleware: ['globalMiddleware1', 'globalMiddleware2'] // can be a string array
    }
};

错误处理

Nuxt.js 提供了多种处理错误的方法,包括全局错误处理和特定于页面的错误处理。

全局错误处理

  • 自定义错误页面:在layouts目录下创建error.vue文件,用于自定义错误页面布局。
  • 捕获全局错误:在 nuxt.config.js 中配置 error 属性来捕获全局错误:
// middleware/globalMiddleware1.js
export default function (context) {
    // context contains information such as req, res, redirect, app, route, store, etc.
    console.log('Global Middleware 1 executed');
}

页面特定的错误处理

在页面组件中,可以使用asyncData或fetch方法的try-catch结构来处理错误:

// pages/about.vue
export default {
    middleware: 'pageMiddleware' // can be a string or a function
};

API 请求错误处理

对于API请求,如果使用@nuxtjs/axios模块,可以在请求拦截器中统一处理错误:

// middleware/pageMiddleware.js
export default function (context) {
    console.log('Page Middleware executed');
}

确保在 nuxt.config.js 中注册此插件。

Vue生态系统整合

Vue路由器:

Nuxt.js 根据文件结构自动为您的应用程序生成路由系统。路由配置通常不需要手动编写,而是可以通过nuxt.config.js的router属性进行扩展。

视图:

Nuxt.js 自动创建一个 Vuex 存储。在 store 目录下,您可以创建模块化状态、突变、操作和 getter。例如,创建一个 store/modules/users.js 文件来管理用户数据。

// layouts/default.vue
export default {
    middleware: ['layoutMiddleware1', 'layoutMiddleware2']
};

Vue 命令行界面:

Nuxt.js 提供了自己的构建工具,但它也是基于 Vue CLI 的。这意味着您可以使用类似于 Vue CLI 的命令行工具,例如 npx nuxtgenerate(静态生成)或 npxnuxtbuild(构建应用程序)。

通天塔:

Nuxt.js 默认配置了 Babel 以支持最新的 JavaScript 功能。除非有特殊需要,通常不需要手动配置 Babel。

打字稿:

要使用 TypeScript,请在​​ nuxt.config.js 中设置 typescript: true ,Nuxt.js 将自动配置 TypeScript 支持。

ESLint:

为了检查代码质量,您可以在项目中安装 ESLint 并配置 .eslintrc.js。 Nuxt.js 提供 @nuxt/eslint-module 插件来简化集成。

// middleware/layoutMiddleware1.js
export default function (context) {
    console.log('Layout Middleware 1 executed');
}

// middleware/layoutMiddleware2.js
export default function (context) {
    console.log('Layout Middleware 2 executed');
}

Vue使用:

VueUse 是一个 Vue 用例库,包含各种实用功能。要集成,首先安装@vueuse/core,然后导入并使用组件中的功能。

yarn create nuxt-app my-nuxt-project
cd my-nuxt-project
├── .nuxt/ # Automatically generated files, including compiled code and configuration
├── assets/ # Used to store uncompiled static resources, such as CSS, images, fonts
├── components/ # Custom Vue components
├── layouts/ # Application layout files, defining the general structure of the page
│ └── default.vue # Default layout
├── middleware/ # Middleware files
├── pages/ # Application routes and views, each file corresponds to a route
│ ├── index.vue # Default homepage
│ └── [slug].vue # Dynamic routing example
├── plugins/ # Custom Vue.js plugins
├── static/ # Static resources, will be copied to the output directory as is
├── store/ # Vuex state management file
│ ├── actions.js # Vuex actions
│ ├── mutations.js # Vuex mutations
│ ├── getters.js # Vuex getters
│ └── index.js # Vuex store entry file
├── nuxt.config.js # Nuxt.js configuration file
├── package.json # Project dependencies and scripts
└── yarn.lock # Or npm.lock, record dependency versions

Vue 插件:

可以通过nuxt.config.js中的plugins配置项全局注册Vue插件。例如,集成 Vue Toastify 来显示通知:

<!-- pages/index.vue -->
<template>
  <div>
    <h1>Hello from Nuxt.js SSR</h1>
    <p>{{ message }}</p>
  </div>
</template>

<script>
export default {
  data() {
    return {
      message: 'This content is server-rendered!'
    };
  },
  asyncData() {
    // Here you can get data on the server side
    // The returned data will be used as the default value of data
    return { message: 'Data fetched on server' };
  }
};
</script>
// nuxt.config.js
export default {
// ...
    router: {
        middleware: ['globalMiddleware1', 'globalMiddleware2'] // can be a string array
    }
};

使用 Nuxt.js 的工作流程

Nuxt.js 提供了完整的开发、构建和部署工作流程。使用 nuxt 命令启动开发服务器,使用 nuxt build 进行生产构建,使用 nuxt start 启动生产服务器,使用 nuxtgenerate 生成静态文件。

性能优化

  1. 静态生成(SSG):使用nuxtgenerate命令生成预渲染的HTML文件,可以大大提高首屏加载速度,并且对SEO友好。

  2. 代码拆分:Nuxt.js 默认会进行代码拆分,将应用分成多个小块,只加载当前页面所需的代码,减少初始加载量。

  3. 延迟加载:对于大型应用程序,可以考虑延迟加载组件或模块,仅在需要时加载它们。您可以使用 或 结合异步组件来实现这一点。

  4. 优化资源:

  • 图像:使用正确的格式(例如 WebP)、压缩图像、使用延迟加载(Nuxt.js 实际应用:Vue.js 服务器端渲染框架)或使用 nuxt-图像或 nuxt-picture 组件。

  • CSS:将 CSS 提取到单独的文件并减少内联样式。

  • JS:使用 Tree Shaking 删除未使用的代码。

  1. 异步数据预取:使用asyncData或fetch方法预加载数据,确保渲染前数据准备就绪。

  2. 服务器端缓存:使用 nuxt-ssr-cache 模块缓存服务器端渲染的结果,减少不必要的 API 调用。

  3. HTTP缓存:设置正确的缓存头(如Cache-Control),使用浏览器缓存静态资源。

  4. 路由守卫:使用 beforeRouteEnter 等路由守卫以避免在不需要时加载数据。

  5. 减少 HTTP 请求:结合多个 CSS 和 JS 文件,减少 HTTP 请求数量。

  6. 优化API性能:优化后端接口,减少响应时间,使用分页、过滤、缓存策略。

  7. 利用 CDN:在 CDN 上托管静态资源,以加快全球用户的加载速度。

  8. 优化 Vuex 状态管理:避免不必要的计算属性和监听器,以减少状态更改的开销。

  9. 性能审计:使用Lighthouse、Chrome DevTools或其他性能审计工具定期检查应用程序性能,并根据报告进行改进。

  10. Service Worker:如果适用,集成 PWA 功能并使用 Service Worker 进行离线缓存和资源预加载。

  11. 模块优化:选择高性能的第三方模块,并确保它们针对SSR进行了优化。

以上是Nuxt.js 实际应用:Vue.js 服务器端渲染框架的详细内容。更多信息请关注PHP中文网其他相关文章!

声明:
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn