VUE 3.x 实战项目从0到1搭建

目录

一、开发环境配置

1、安装node.js

2、npm配置淘宝镜像

3、安装 Vue CLI 

升级版本

4、创建一个项目

二、项目框架结构

三、常用的集成

1、Vue Router

安装

使用

 2、Vuex

安装

使用

3、axios

安装

使用

四、CLI 服务 

1、使用命令

2、vue-cli-service serve 

3、vue-cli-service build

4、缓存和并行处理

五、模式和环境变量

1、模式

 2、环境变量

只在本地有效的变量 

六、本地预览


一、开发环境配置

1、安装node.js

通过官网下载安装node.js

http://nodejs.cn/

在用 Vue 构建大型应用时需要使用到node里面的 npm 来安装各种插件

Node 版本要求

Vue CLI 4.x 需要 Node.js v8.9 或更高版本 (推荐 v10 以上)。你可以使用 n,nvm 或 nvm-windows 在同一台电脑中管理多个 Node 版本。

2、npm配置淘宝镜像

如果在本地一直装不上npm的包,可以考虑用国内的淘宝镜像,使用淘宝定制的 cnpm (gzip 压缩支持) 命令行工具代替默认的 npm

npm install -g cnpm --registry=https://registry.npm.taobao.org
 
npm config set registry https://registry.npm.taobao.org

3、安装 Vue CLI 

Vue CLI 是 Vue 提供的一个命令行工具,为单页面应用 (SPA) 快速搭建繁杂的脚手架。它为现代前端工作流提供了功能齐备的构建设置。只需要几分钟的时间就可以运行起来并带有热重载、保存时 lint 校验,以及生产环境可用的构建版本。

对于 Vue 3,我们应该使用 npm 上可用的 Vue CLI v4.5 作为 @vue/cli

可以使用下列任一命令安装cli:

npm install -g @vue/cli
# OR
yarn global add @vue/cli

安装之后,我们就可以在命令行中访问 vue 命令。可以通过简单运行命令 vue,看看是否展示出了一份所有可用命令的帮助信息,来验证它是否安装成功。

查看vue版本可输入以下命令,可检查其版本是否正确:

vue --version

升级版本

如需升级全局的 Vue CLI 包,可运行:

npm update -g @vue/cli

# 或者
yarn global upgrade --latest @vue/cli

4、创建一个项目

运行 vue create 命令创建一个 名为 hello-world 的项目

vue create hello-world

运行之后,我们会被提示选取一个 preset。

你可以选默认的包含了基本的 Babel + ESLint 设置的 preset,也可以选“手动选择特性”来选取需要的特性。

VUE 3.x 实战项目从0到1搭建_第1张图片

这个默认的设置非常适合快速创建一个新项目的原型,而手动设置则提供了更多的选项,它们是面向生产的项目更加需要的。 

VUE 3.x 实战项目从0到1搭建_第2张图片

二、项目框架结构

|- node_modules // 项目依赖包
|- public // 一般用于存放静态文件,打包时会被直接复制到输出目录(./dist)
|- src // 项目源代码
    |- assets // 静态资源文件夹,用于存放静态资源,打包时会经过 webpack 处理
    |- components // 组件文件夹,存放 Vue 组件
         └─ loading
                   |- index.vue
                   |- index.ts
                   |- index.less
    |- pages // 页面视图文件夹
         |- Index
              |- index.vue
              |- index.ts
              |- index.less
    |- router // 路由配置文件夹
          |- router.js // 路由文件配置
    |- store // vuex文件夹
          ├── index.js          # 我们组装模块并导出 store 的地方
          ├── actions.js        # 根级别的 action
          ├── mutations.js      # 根级别的 mutation
          └── modules
                  ├── cart.js       # 购物车模块
                  └── products.js   # 产品模块
    |- service // 服务请求文件夹
          |- http.js // 请求接口文件
          |- request.js // 请求配置文件
    |- utils // 工具类文件夹
    |- App.vue // 入口文件
    |- main.js // 注册路由与服务
|- .env // 环境配置文件
|- .env.development // dev环境配置文件
|- .env.test // test环境配置文件
|- .env.production // prd环境配置文件
|- vue.config.js // 配置文件
|- package.json // 包管理代码
|- .gitignore // git忽略文件
|- README.md // 说明文件

三、常用的集成

1、Vue Router

安装

npm install vue-router@4

使用

用 Vue + Vue Router 创建单页应用非常简单:通过 Vue.js,我们已经用组件组成了我们的应用。当加入 Vue Router 时,我们需要做的就是将我们的组件映射到路由上,让 Vue Router 知道在哪里渲染它们。

App.vue

Hello App!

Go to Home Go to About

router-link:我们没有使用常规的 a 标签,而是使用一个自定义组件 router-link 来创建链接。这使得 Vue Router 可以在不重新加载页面的情况下更改 URL,处理 URL 的生成以及编码。

router-view: 将显示与 url 对应的组件。可以把它放在任何地方,以适应布局。

router.js

import { createRouter, createWebHashHistory } from 'vue-router'

const Steps = () => import('@/pages/Steps/index')
const Guide = () => import('@/pages/Guide/index')
const Distinguish = () => import('@/pages/Distinguish/index')
const Massage = () => import('@/pages/Massage/index')
const Project = () => import('@/pages/Project/index')
const Custom = () => import('@/pages/Custom/index')
const Referrals = () => import('@/pages/Referrals/index')
const Main = () => import('@/pages/Main/index')

const AudioTest = () => import('@/pages/AudioTest/index')
const CameraTest = () => import('@/pages/cameraTest/index')

import Test from '@/pages/Test/index'

const routes = [
  { path: '/', name: 'firstPage', component: Project }, // 我的方案
  { path: '/steps', component: Steps },
  { path: '/guide', component: Guide },
  {
    path: '/distinguish',
    component: Distinguish,
    meta: {
      keepAlive: false
    }
  },
  { path: '/massage', component: Massage },
  { path: '/test', component: Test },
  { path: '/custom', component: Custom }, // 方案定制
  { path: '/referrals', component: Referrals }, // 推荐测肤
  { path: '/main', component: Main },
  { path: '/audio', component: AudioTest },
  { path: '/cameraTest', component: CameraTest },
]

const router = createRouter({
  // 4. 内部提供了 history 模式的实现。为了简单起见,我们在这里使用 hash 模式。
  history: createWebHashHistory(),
  routes, // `routes: routes` 的缩写
})

router.beforeEach((to, from, next) => {
  // console.log(to, from, location.href)
  // 地址参数纠正
  if (to.name === 'firstPage') {
    // 代码逻辑
  }
  next()
})

// 滚动条回到顶部
router.afterEach(() => {
  document.body.scrollTop = 0
  document.documentElement.scrollTop = 0;
})

export default router

main.js

import router from 'router.js'

// 5. 创建并挂载根实例
const app = Vue.createApp({})
//确保 _use_ 路由实例使
//整个应用支持路由。
app.use(router)

app.mount('#app')

// 现在,应用已经启动了!

通过调用 app.use(router),我们可以在任意组件中以 this.$router 的形式访问它,并且以 this.$route 的形式访问当前路由:

// Index.vue
export default {
  computed: {
    username() {
      // 我们很快就会看到 `params` 是什么
      return this.$route.params.username
    },
  },
  methods: {
    goToDashboard() {
      if (isAuthenticated) {
        this.$router.push('/dashboard')
      } else {
        this.$router.push('/login')
      }
    },
  },
}

要在 setup 函数中访问路由,请调用 useRouter 或 useRoute 函数。

 2、Vuex

Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式 + 库。它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化。

安装

npm install vuex@next --save

# OR

yarn add vuex@next --save

使用

注意:vue 3.x 和 4.x 的写法有点不一致,具体请查阅官方文档

import Vue from 'vue';
import Vuex from 'vuex';
import createVuexAlong from 'vuex-along';

Vue.use(Vuex);

export default new Vuex.Store({
  state: {
    urlParams: {},
    albumList: [],
    albumCourse: []
  },
  getters: {
    musicById: state => id => {
      for (let i = 0; i < state.albumCourse.length; i++) {
        const course = state.albumCourse[i];
        for (let j = 0; j < course.length; j++) {
          if (id === course[j].id) {
            return course[j];
          }
        }
      }
    }
  },
  mutations: {
    urlParams: (state, payload) => {
      state.urlParams = payload;
    },
    albumList: (state, payload) => {
      state.albumList = payload;
    }
  },
  actions: {
    createAudio(context, audio) {
      return new Promise(resolve => {
        const audioObj = new Audio(audio.url);
        context.commit('audioObj', audioObj);
        resolve(audioObj);
      });
    }
  },
  modules: {},
  plugins: [createVuexAlong({
    name: '__phzn-store',
    justSession: true,
    session: {
      list: []
    }
  })]
});

State

computed: {
  localComputed () { /* ... */ },
  // 使用对象展开运算符将此对象混入到外部对象中
  ...mapState([
    // 映射 this.count 为 store.state.count
    'count'
  ])
}

Getter 

import { mapGetters } from 'vuex'

export default {
  // ...
  computed: {
  // 使用对象展开运算符将 getter 混入 computed 对象中
    ...mapGetters([
      'doneTodosCount',
      'anotherGetter',
      // ...
    ])
  }
}


// 如果你想将一个 getter 属性另取一个名字,使用对象形式:
...mapGetters({
  // 把 `this.doneCount` 映射为 `this.$store.getters.doneTodosCount`
  doneCount: 'doneTodosCount'
})

Mutation 

import { mapMutations } from 'vuex'

export default {
  // ...
  methods: {
    ...mapMutations([
      'increment', // 将 `this.increment()` 映射为 `this.$store.commit('increment')`

      // `mapMutations` 也支持载荷:
      'incrementBy' // 将 `this.incrementBy(amount)` 映射为 `this.$store.commit('incrementBy', amount)`
    ]),
    ...mapMutations({
      add: 'increment' // 将 `this.add()` 映射为 `this.$store.commit('increment')`
    })
  }
}

Action

import { mapActions } from 'vuex'

export default {
  // ...
  methods: {
    ...mapActions([
      'increment', // 将 `this.increment()` 映射为 `this.$store.dispatch('increment')`

      // `mapActions` 也支持载荷:
      'incrementBy' // 将 `this.incrementBy(amount)` 映射为 `this.$store.dispatch('incrementBy', amount)`
    ]),
    ...mapActions({
      add: 'increment' // 将 `this.add()` 映射为 `this.$store.dispatch('increment')`
    })
  }
}

Module 

由于使用单一状态树,应用的所有状态会集中到一个比较大的对象。当应用变得非常复杂时,store 对象就有可能变得相当臃肿。

为了解决以上问题,Vuex 允许我们将 store 分割成模块(module)。每个模块拥有自己的 state、mutation、action、getter、甚至是嵌套子模块——从上至下进行同样方式的分割:

const moduleA = {
  state: () => ({ ... }),
  mutations: { ... },
  actions: { ... },
  getters: { ... }
}

const moduleB = {
  state: () => ({ ... }),
  mutations: { ... },
  actions: { ... }
}

const store = new Vuex.Store({
  modules: {
    a: moduleA,
    b: moduleB
  }
})

store.state.a // -> moduleA 的状态
store.state.b // -> moduleB 的状态

3、axios

Axios 是一个基于 promise 的 HTTP 库,可以用在浏览器和 node.js 中。

安装

npm install axios

使用

import axios from 'axios'

// create an axios instance
const service = axios.create({
  baseURL: process.env.VUE_APP_BASE_API, // url = base url + request url
  // withCredentials: true, // send cookies when cross-domain requests
  timeout: 30e3 // request timeout
})

// request interceptor
service.interceptors.request.use(
  config => {
    // do something before request is sent

    return config
  },
  error => {
    // do something with request error
    console.log(error) // for debug
    return Promise.reject(error)
  }
)

// response interceptor
service.interceptors.response.use(
  /**
   * If you want to get http information such as headers or status
   * Please return  response => response
   */

  /**
   * Determine the request status by custom code
   * Here is just an example
   * You can also judge the status by HTTP Status Code
   */
  response => {
    return response.data
  },
  error => {
    console.log('err   ' + error) // for debug
   
    return Promise.reject(error.response)
  }
)

export default service
import request from './request'

const baseurl = 'api/'

export function userClockin(data) {
  return request({
    url: baseurl + 'clockin',
    params: data,
    method: 'get'
  })
}

export function updateUserProject(data) {
  return request({
    url: baseurl + 'update',
    data,
    method: 'post'
  })
}

4、Pinia

Pinia 是一个 Vue 存储库,推荐使用 Pinia 替代 Vuex

Pinia 中文文档

四、CLI 服务 

1、使用命令

在一个 Vue CLI 项目中,@vue/cli-service 安装了一个名为 vue-cli-service 的命令。你可以在 npm scripts 中以 vue-cli-service、或者从终端中以 ./node_modules/.bin/vue-cli-service 访问这个命令。

这是使用默认 preset 的项目的 package.json

{
  "scripts": {
    "serve": "vue-cli-service serve",
    "build": "vue-cli-service build"
  }
}

我们可以通过 npm 或 Yarn 调用这些 script: 

npm run serve
# OR
yarn serve

如果可以使用 npx (最新版的 npm 应该已经自带),也可以直接这样调用命令: 

npx vue-cli-service serve

2、vue-cli-service serve 

用法:vue-cli-service serve [options] [entry]

选项:

  --open    在服务器启动时打开浏览器
  --copy    在服务器启动时将 URL 复制到剪切版
  --mode    指定环境模式 (默认值:development)
  --host    指定 host (默认值:0.0.0.0)
  --port    指定 port (默认值:8080)
  --https   使用 https (默认值:false)

vue-cli-service serve 命令会启动一个开发服务器 (基于 webpack-dev-server) 并附带开箱即用的模块热重载 (Hot-Module-Replacement)。

除了通过命令行参数,也可以使用 vue.config.js 里的 devServer 字段配置开发服务器。

命令行参数 [entry] 将被指定为唯一入口 (默认值:src/main.js,TypeScript 项目则为 src/main.ts),而非额外的追加入口。尝试使用 [entry] 覆盖 config.pages 中的 entry 将可能引发错误。

3、vue-cli-service build

用法:vue-cli-service build [options] [entry|pattern]

选项:

  --mode        指定环境模式 (默认值:production)
  --dest        指定输出目录 (默认值:dist)
  --modern      面向现代浏览器带自动回退地构建应用
  --target      app | lib | wc | wc-async (默认值:app)
  --name        库或 Web Components 模式下的名字 (默认值:package.json 中的 "name" 字段或入口文件名)
  --no-clean    在构建项目之前不清除目标目录的内容
  --report      生成 report.html 以帮助分析包内容
  --report-json 生成 report.json 以帮助分析包内容
  --watch       监听文件变化

vue-cli-service build 会在 dist/ 目录产生一个可用于生产环境的包,带有 JS/CSS/HTML 的压缩,和为更好的缓存而做的自动的 vendor chunk splitting。它的 chunk manifest 会内联在 HTML 里。

这里还有一些有用的命令参数:

  • --modern 使用现代模式构建应用,为现代浏览器交付原生支持的 ES2015 代码,并生成一个兼容老浏览器的包用来自动回退。

  • --target 允许你将项目中的任何组件以一个库或 Web Components 组件的方式进行构建。

  • --report 和 --report-json 会根据构建统计生成报告,它会帮助你分析包中包含的模块们的大小。

4、缓存和并行处理

  • cache-loader 会默认为 Vue/Babel/TypeScript 编译开启。文件会缓存在 node_modules/.cache 中——如果你遇到了编译方面的问题,记得先删掉缓存目录之后再试试看。

  • thread-loader 会在多核 CPU 的机器上为 Babel/TypeScript 转译开启。

五、模式和环境变量

1、模式

默认情况下,一个 Vue CLI 项目有三个模式:

  • development 模式用于 vue-cli-service serve
  • test 模式用于 vue-cli-service test:unit
  • production 模式用于 vue-cli-service build 和 vue-cli-service test:e2e

你可以通过传递 --mode 选项参数为命令行覆写默认的模式。

例如,如果你想要在构建命令中使用开发环境变量:

vue-cli-service build --mode development

 2、环境变量

我们可以在项目根目录中放置下列文件来指定环境变量:

.env                # 在所有的环境中被载入
.env.local          # 在所有的环境中被载入,但会被 git 忽略
.env.[mode]         # 只在指定的模式中被载入
.env.[mode].local   # 只在指定的模式中被载入,但会被 git 忽略

请注意,只有 NODE_ENVBASE_URL 和以 VUE_APP_ 开头的变量将通过 webpack.DefinePlugin 静态地嵌入到客户端侧的代码中。这是为了避免意外公开机器上可能具有相同名称的私钥。

只在本地有效的变量 

有的时候可能有一些不应该提交到代码仓库中的变量,尤其是当项目托管在公共仓库时。这种情况下你应该使用一个 .env.local 文件取而代之。本地环境文件默认会被忽略,且出现在 .gitignore 中。

.local 也可以加在指定模式的环境文件上,比如 .env.development.local 将会在 development 模式下被载入,且被 git 忽略。

六、本地预览

vue项目执行打包命令后会自动生成一个dist文件夹,dist 目录需要启动一个 HTTP 服务器来访问 (除非你已经将 publicPath 配置为了一个相对的值),所以以 file:// 协议直接打开 dist/index.html 是不会工作的。

在本地预览生产环境构建最简单的方式就是使用一个 Node.js 静态文件服务器,例如 serve:

npm install -g serve
# -s 参数的意思是将其架设在 Single-Page Application 模式下
# 这个模式会处理即将提到的路由问题
serve -s dist

你可能感兴趣的:(Vue,vue,前端,javascript,html5,vue.js)