nuxt 的使用

阅读数:28 评论数:0

跳转到新版页面

分类

html/css/js

正文

一、概述

NUXT 是一个基于 Vue.js 的轻量级应用框架,可用来创建服务端渲染(SSR)应用,也可充当静态站点引擎生成静态站点应用。服务端渲染又称 SSR (Server Side Render) ,是指在服务端就完成页面的内容,而不是在客户端通过AJAX请求才获取数据。

官方文档:https://nuxt.com/

中文文档:https://nuxt.com.cn/

1、nuxt目录

目录     说明
assets 资源目录,用于组织未编译的静态资源如 LESS、SASS 或 JavaScript。
components 组件目录 ,用于组织应用的 Vue.js 组件。Nuxt.js 不会扩展增强该目录下 Vue.js 组件,即这些组件不会像页面组件那样有 asyncData 方法的特性。
layouts 布局目录 ,用于组织应用的布局组件。
pages 页面目录 ,用于组织应用的路由及视图。Nuxt.js 框架读取该目录下所有的 .vue 文件并自动生成对应的路由配置。
plugins 插件目录 ,用于组织那些需要在 根vue.js应用 实例化之前需要运行的 Javascript 插件。
nuxt.config.js  配置文件, 用于组织Nuxt.js 应用的个性化配置,以便覆盖默认配置。

二、安装

访问链接:https://codeload.github.com/nuxt/starter/tar.gz/refs/heads/v3

下载后,直接解压缩,然后进入解压缩目录

pnpm install
pnpm run dev

三、路由(pages目录)

nuxt是属于约定式的。

1、示例

  • 首先第一件事情就是删除 app.vue 里的 <NuxtWelcome />,这个是Nuxt官方的欢迎组件
  • 然后在 app.vue 里添加 <NuxtPage :page-key="$route.fullPath" />
  • 现在,我们只需要在根目录创建一个 pages 文件夹
  • 接着在 pages 文件夹里新增一个 .vue 文件(名称的话你自己取,我这里为了方便教程就命名为 about.vue ),然后这个文件就已经进入路由了,你可以通过 http://localhost:3000/about 访问了

2、嵌套路由

  • 比如我们现在有一个 /about 页了,我们现在需要 /about/1 页面,那么我们就需要在同级文件夹新建一个 about 文件夹,再在这个文件夹里新建一个 1.vue

  • 我们现在来通过 useRouter().options.routes 看一下routes的结构
  • 更多级的路由你只需要套娃式地操作即可咯,注意,如果你不设置同级相同名称的目录和.vue文件,那么不会形成嵌套关系

3、动态路由

在文件夹下创建 vue 文件,vue文件命名规范:_参数名称.vue ,注意是以下划线开头。

nuxt 中动态路由的 js 代码为:

window.location.href = '/hosp/' + hoscode

四、布局(layout目录)

这是Nuxt提供的一个可定制的公共布局框架

  • 在项目根目录下创建一个 layouts 文件夹
  • 然后我们在 layouts 文件夹下新建一个 default.vue ,它将作为 <NuxtLayout /> 的默认布局

  • 接着,在需要用到该布局的页面文件里添加 <NuxtLayout><NuxtLayout /> 即可
<template>
  <NuxtLayout>
    <NuxtPage : page-key="$route.fullPath" />
  </NuxtLayout>
</template>
  • 你在 <NuxtLayout><NuxtLayout /> 里添加的元素将添加到布局文件里的 slot插槽出口 上
  • 如果我们需要为某个页面指定某个布局,我这里用 admin 来作为演示,在 layouts 文件夹下新建一个 admin.vue,然后在需要用到该布局的页面文件里添加 <NuxtLayout name="admin" ><NuxtLayout /> 即可

五、中间件(middleware目录)

实际开发中,我们也许会在跳转某个路有前做点什么操作,或者说是决定是否跳转点击的路由

  • 在项目根目录下创建 middleware 文件夹
  • 这个文件夹里面的文件是以 .js 或者 .ts(推荐)为格式的
  • 你也可以叫他 导航守卫前

1、全局中间件

  • 我们首先就需要定义一个全局的中间件,它的命名应该是 default.global.ts 
export default defineNuxtRouteMiddleware((to: any, from: any) => {
  
});

2、在中间件里获取document、window等

有的时候我们可能需要在这里获取Html元素,这时候我们不能直接获取到元素,比如document、windows等等因为是在服务端没有挂载前是不存在的

  • 我们可以通过异步加载的方式获取

  • 不过我是不推荐在中间件里操作document的,因为有的时候会出现莫名其妙的问题,比如我之前在这里面通过接口获取网站配置并保存到 Pinia 里,出现了服务器部署后访问项目强制刷新时无法获取到 Pinia 里的数据,所有还是推荐直接在 app.vue 里进行类似操作

六、SEO相关

1、动态Title

  • 先在 app.vue 里添加 useHead() 配置

useHead({
  titleTemplate: (productCategory) => {
    const baseTitle = "时光小灶";
    return `${productCategory ? productCategory + " - " : ""}${baseTitle}`;
  },
});
  • 然后,在我们的每个页面添加一个 <Title></Title> 组件,标签里面的字符将作为当前页面的动态title

七、Element Plus

1、安装

npm i @element-plus/nuxt -D
// nuxt.config.ts
export default defineNuxtConfig({
  modules: ["@element-plus/nuxt"],
  elementPlus: {
    /** Options */
  },
});
  • 安装好后就不需要手动import引入了

2、icon图标

export default defineNuxtConfig({
  modules: ["@element-plus/nuxt"],
  elementPlus: {
    /** Options *
    icon: "ElIcon",
  },
});
  • 现在,你可以通过 import { User, Lock } from "@element-plus/icons-vue"; 来使用所需要的图标
  • 在 plugins 文件夹里的 global.ts 文件里添加如下代码,实现自动导入
import * as ElementPlusIconsVue from "@element-plus/icons-vue";

export default defineNuxtPlugin(async (NuxtApp) => {
  // 其他code
  // 全局组件引入
  for (const [key, component] of Object.entries(ElementPlusIconsVue)) {
    NuxtApp.vueApp.component(key, component);
  }
  // 其他code
});

八、Pinia及持久化

1、安装

npm i pinia @pinia/nuxt

2、使用

  • 在 项目名根目录 创建 stores 文件夹
  • 在 stores 文件夹里创建一个 .ts 文件,文件名自己取,之后使用的时候正确路径导入即可,下面以 adminInfo.ts 作为示例
// adminInfo.ts
import { defineStore } from "pinia";

export const adminConfig = defineStore("adminConfig", {
  state: () => {
    return {
      adminConfig: {},
    };
  },
  actions: {
   adminConfigSet(data = {}) {
      this.adminConfig = data;
    },
  },
});
  • 然后需要使用的页面导入即可
import { adminConfig } from "~/stores/adminConfig";
const store = reactive<any>(adminConfig().adminConfig);

2、持久化插件 pinia-plugin-persistedstate

  • 为了实现持久化,我们需要使用到一个依赖 @pinia-plugin-persistedstate/nuxt
npm i -D @pinia-plugin-persistedstate/nuxt
  • 然后在 nuxt.config.ts 里添加配置
export default defineNuxtConfig({
  // other code
  modules: ["@pinia/nuxt", "@pinia-plugin-persistedstate/nuxt"],
  // other code
});
  • 创建 Store 时,将 persist 选项设置为 true

// adminInfo.ts
import { defineStore } from "pinia";

export const adminConfig = defineStore("adminConfig", {
  state: () => {
    return {
      adminConfig: {},
    };
  },
  actions: {
   adminConfigSet(data = {}) {
      this.adminConfig = data;
    },
  },
  persist: true,// 设置为true
});
  • 默认情况下,Store 将被保存在 cookie 中(在底层使用 Nuxt 的 useCookie)
  • 但可以通过使用自动导入的 persistedState 变量下的可用 storage 来配置你想要使用的 storage
import { defineStore } from "pinia";

export const adminConfig = defineStore("adminConfig", {
  state: () => {
    return {
      adminConfig: {},
    };
  },
  actions: {
   adminConfigSet(data = {}) {
      this.adminConfig = data;
    },
  },
  persist: {
  // 下面的二选一
    storage: persistedState.localStorage,// localStorage
    storage: persistedState.sessionStorage,// sessionStorage
  }
});

九、在nuxt中安装axiios

第一步,执行 npm install axios ,并创建 utils 文件夹,在该文件夹中创建 request.js,代码如下:

import axios from 'axios'
import { MessageBox, Message } from 'element-ui'
// 创建axios实例
const service = axios.create({
    baseURL: 'http://localhost',
    timeout: 15000 // 请求超时时间
})
// http request 拦截器
service.interceptors.request.use(
    config => {
    // token 先不处理,后续使用时在完善
    return config
},
  err => {
    return Promise.reject(err)
})
// http response 拦截器
service.interceptors.response.use(
    response => {
        if (response.data.code !== 200) {
            Message({
                message: response.data.message,
                type: 'error',
                duration: 5 * 1000
            })
            return Promise.reject(response.data)
        } else {
            return response.data
        }
    },
    error => {
        return Promise.reject(error.response)
})
export default service

注:若出现 require() of ES Module错误 ,原因为当前使用的 axios 版本太高,执行下述命令即可解决:

npm uninstall axios
npm install axios@0.19.2

十、使用nginx打包部署

1、nuxt的generate和build的打包区别

(1)generate打包

打包方式简单,执行npm run dev会生成dist文件夹,放到服务器就好了。

  • 使用generate打包后每个对应的页面都会生成一个html,你在打包的时候不能关闭后台,他会请求后台数据生成首屏的数据
  • 这样打包有一个弊端,当你首屏的数据发生更改的时候,他还是显示的是之前的数据,要想改变的话,需要重新打包发布才行。
  • 所以,如果你的首屏是动态的就不建议使用这种打包方式了。
  • 打包之后每个页面都生成了HTML页面,只有首屏的数据是之前渲染好了,但是其它数据还是从后台获取,比如翻页,第二页数据是重新请求后台的,你再次返回第一页也是再次请求的。

(2)build打包

build打包生成的是动态页面,当然是同样具有SEO功能。

2、使用nginx部署的的过程

(1)打包nuxt.js应用程序

在生产环境中,你通常不会使用 nuxt generate 来生成静态站点,除非你的应用程序是一个完全静态的网站。对于大多数应用程序,你会使用 nuxt build 来为生产环境构建应用程序。

在项目根目录下,运行以下命令:

npm run build

这将创建 .output目录,其中包含编译后的代码和资源。

2、配置生产环境的启动

在生产环境中,你会使用 nuxt start 来启动一个生产服务器。在你的 package.json 文件中,可以添加一个启动脚本:

"scripts": {
  "start": "nuxt start"
}

3、安装和配置nginx

server {
    listen 80;
    server_name example.com; # 替换为你的域名

    location / {
        proxy_pass http://localhost:3000; # 假设 Nuxt.js 应用程序运行在端口 3000
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection 'upgrade';
        proxy_set_header Host $host;
        proxy_cache_bypass $http_upgrade;
        proxy_set_header X-Forwarded-Proto $scheme;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    }
}

确保将 example.com 替换为你的域名,并且 Nuxt.js 应用程序正在监听 localhost:3000

4、启动nginx

保存配置后,测试 Nginx 配置是否正确:

sudo nginx -t

如果没有错误,重启 Nginx 使配置生效.

5、启动nuxt.js应用程序

在你的 Nuxt.js 应用程序目录中,运行以下命令来启动应用程序:

npm run start

这将启动一个生产服务器,通常在 localhost:3000 端口。

另外,也可以使用pm2来管理运行项目,需要在根目录下配置ecosystem.config.js文件

module.exports = {
  apps: [
    {
      name: 'NuxtAppName',  // 设置启动项目名称
      exec_mode: 'cluster',
      instances: 'max',
      // 注意这里的相对路径
      script: '../.output/server/index.mjs'
    }
  ]
}

此时目录结构是这样

需要在项目的根目录下面执行命令

pm2 start ecosystem.config.js
# 然后使用下边的命令看一下启动的服务列表
pm2 list
pm2 logs name(服务名)     //查看服务执行日志
pm2 delete name(服务名)   //删除服务
pm2 stop name(服务名)     //停止服务
pm2 start name(服务名)    //启动服务
pm2 restart name(服务名)  //重启服务




相关推荐

module.exports = { "plugins": { "postcss-import": {},

在我们封装请求的js文件中加一个判断即可,先声明一个变量showMsg来控制是否需要弹框,初始化为true,然后在请求判断中如果token失效导致走了401,先判断当前是否可以显示弹框,初始化为

一、生命周期 1、vue2生命周期 beforeCreate #实例初始化之后,进行数据侦听和事件/侦听器的配置之前同步调用 created #实例创建完成后被立即同步调用 beforeMount #

一、使用pnpm新建项目 可以使用npm 或yarn或pnpm来初始化Vite项目 pnpm create vite xxx(项目名称) #选择vue #选择js cd xxx (进入项目目录) #安

一、概述 <script setup> 是在单文件组件(SFC)中使用组合式API的编译时语法糖,解决Vue3.0中setup需要频繁将声明的变量、函数以及import引入的内容通过return向外

一、概述 在vue2中,data函数里返回的值直接为响应式,但在vue3中我们需要使用一些函数才能达到这个效果。 setup函数中拿不到vue的this。 二、常用函数 <template> <d

<script> export default { setup() { const func1= () => { console.log("func1");

缓存页面主要Jul为了防止重复渲染dom,减少加载时间及性能消耗,提高用户体验。 一、旧版的语法 <keep-alive> <router-view v-if="$route.meta.kee

一、在main.js挂载 import { createApp } from 'vue' import App from './App.vue' import router from './route

一、概述 在vue3中没有$refs这个对象,可以使用如下方法 <template> <div><input type="text" ref="txt1" value="hello" /></div>