vue-cli4.0搭建vue项目(含源码)

本文档详细介绍了如何从Vue CLI 2.0升级到3.0+版本,包括项目的创建过程、环境配置、axios请求封装以及接口管理。在升级过程中,提到了创建新项目、配置环境变量、使用vue.config.js进行代理设置,并展示了如何在项目中封装axios以处理请求和错误。此外,还提供了axios实例、拦截器和接口管理的代码示例。
摘要由CSDN通过智能技术生成

摘要

随着vue-cli脚手架的升级,vue-cli2.0版本与vue-cli3.0+版本搭建出来的vue项目也有了一些变化,下面是整理的个人从脚手架升级到vue项目创建的一个过程。

  • 本项目还会融合axios请求封装,可运行实测;
  • 接口统一管理,以及调用方式使用;
  • 环境区分(开发、生产、预生产、测试);

升级vue脚手架

  • 全局卸载旧版本脚手架(已升级可忽略)
npm uninstall vue-cli -g    或
yarn remove vue-cli -g
  • node安装最近的版本(不必是最新),我本机安装版本v12.16.1
  • 安装最新的vue-cli
npm install -g @vue/cli
  • 查看是否已经安装成功
vue --version 或 vue -V //查看版本号

注意:vue-cli2.0升级后(3.0+以上)如果你还需要遗产vue init功能,可以安装一个全局桥,这样你就可以继续运行你的vue-cli2.X版本的项目以及通过之前的vue init webpack '项目名'来创建项目了,命令行如下:

npm install -g @vue/cli-init

创建项目

  • 开始创建
    vue create '项目名称'
    default是使用默认配置(在这里我们选择Vue 2版本)
    Manually select features 是自定义配置
    这里选择自定义配置,然后回车下一步
    在这里插入图片描述
  • 选择配置(自定义配置),上下箭头选择空格键确认*好代表选中,回车键下一步(此处根据自己项目需要可进行选择安装,也可后续自己安装)
    在这里插入图片描述
    是否使用history模式来创建路由,这里选择否,后期可更改
    在这里插入图片描述
    css预处理这里选择的第一项
    在这里插入图片描述
    您希望Babel, ESLint 配置的存放位置,我们选择在专用的配置文件中
    	In dedicated config files //在专用的配置文件中
    	In package.json //在package.json
    
    在这里插入图片描述
    Save this as a preset for future projects?(y/N) (是否保存配置 我们可以选择Y ,保存后下次构建项目的时候就可以直用这次的配置构建项目)
    在这里插入图片描述
  • 项目创建好后
    cd '项目目录' //进入项目根目录 npm run serve //运行项目
    在这里插入图片描述
  • 然后在浏览器输入http://localhost:8080,就可以看到运行界面了

项目修改

环境配置
  • 根目录创建环境配置文件以及vue.config.js配置文件
    在这里插入图片描述

    vue-cli-service build --mode production    //--mode后面跟的是创建的配置文件的名字
    
  • .env.development文件

    # just a flag 开发环境(默认)
    ENV = 'development'
    
    # base api
    VUE_APP_BASE_API = '/dev-api'
    

    .env.production文件

    # just a flag 线上环境(打包)
    ENV = 'production'
    
    # base api
    VUE_APP_BASE_API = '/prod-api'
    
  • vue.config.js文件,改配置文件中的代理配置是为后面本地测试接口时使用,不然会跨域
    配置详情可参考vue-cli

    // Vue.config.js
    module.exports = {
        publicPath: '/', //基本路径
        outputDir: 'dist', //构建时的输出目录
        assetsDir: 'static', //放置静态资源的目录
        indexPath: 'index.html', //html的输出路径
        productionSourceMap: false, // 生产环境是否生成 sourceMap 文件
        devServer: {
            open: true,
            proxy: {
                '/dev-api': {
                    target: 'http://api.yckindergarten.com.cn',//设置你调用的接口域名和端口号 别忘了加http
                    changeOrigin: true,
                    pathRewrite:{
                        '^/dev-api':''//这里理解成用‘/api’代替target里面的地址,后面组件中我们掉接口时直接用api代替 
                                  //比如我要调用'http://40.00.100.133:3002/user/login',直接写‘/api/user/login’即可
                    }
                }
                // '/foo': {
                //     target: '<other_url>'
                // }
                //...
            }
        }
    }
    
axios封装配置
  • 安装axioselement-ui输入命令 npm install --save element-ui
    引入项目打开 main.js 文件

    import Vue from 'vue'
    import ElementUI from 'element-ui'
    import 'element-ui/lib/theme-chalk/index.css'
    import App from './App.vue'
    import router from './router'
    import store from './store'
    
    Vue.config.productionTip = false
    
    Vue.use(ElementUI)
    
    console.log(process.env.VUE_APP_BASE_API)//测试可查看输出当前环境
    
    new Vue({
      router,//路由
      store,//状态管理
      render: h => h(App)
    }).$mount('#app')
    
  • 安装 axiosqs 命令行输入命令 npm install --save axios qs

  • 在src文件夹下新建http目录,并在http目录下创建三个文件

    config.js独立的数据请求配置文件

    // 接口配置文件
    export default {
        //请求方式
        method: 'post',
        // 基础url前缀
        baseURL: process.env.VUE_APP_BASE_API,//取环境文件中定义的地址
        // 请求头信息
        headers: {
            'Content-Type': 'application/json;charset=UTF-8',
            'Content-Type': 'application/x-www-form-urlencoded',
            'Appid': '123456',
            'Token': ''
        },
        // 参数
        data: {},
        // 设置超时时间
        timeout: 10000,
        // 携带凭证
        withCredentials: false,
        // 返回数据类型
        responseType: 'json'
    }
    

    instance.js请求axios封装、拦截、处理文件

    // axios 封装、拦截、统一请求处理
    import axios from 'axios' //安装后引入
    import config from './config.js' //引入配置文件
    import qs from 'qs' //序列化数据请求
    
    export default function $axios(options) {
       return new Promise((resolve, reject) => {
           const instance = axios.create({
               baseURL: config.baseURL,
               headers: {},
               transformResponse: [function (data) { }]
           })
           // request 拦截器
           instance.interceptors.request.use(
               config => {
                   // Tip: 1
                   // 请求开始的时候可以结合 vuex 开启全屏的 loading 动画
    
                   // Tip: 2 
                   // 带上 token , 可以结合 vuex 或者重 localStorage
                   // if (store.getters.token) {
                   //     config.headers['X-Token'] = getToken() // 让每个请求携带token--['X-Token']为自定义key 请根据实际情况自行修改
                   // } else {
                   //     // 重定向到登录页面    
                   // }
    
                   // Tip: 3
                   // 根据请求方法,序列化传来的参数,根据后端需求是否序列化
                   if (config.method.toLocaleLowerCase() === 'post'
                       || config.method.toLocaleLowerCase() === 'put'
                       || config.method.toLocaleLowerCase() === 'delete') {
    
                       config.data = qs.stringify(config.data)
                   }
                   // console.log(config.data);
                   return config
               },
               error => {
                   // 请求错误时做些事(接口错误、超时等)
                   // Tip: 4
                   // 关闭loadding
                   console.log('request:', error)
    
                   //  1.判断请求超时
                   if (error.code === 'ECONNABORTED' && error.message.indexOf('timeout') !== -1) {
                       console.log('根据你设置的timeout/真的请求超时 判断请求现在超时了,你可以在这里加入超时的处理方案')
                       // return service.request(originalRequest);//例如再重复请求一次
                   }
                   //  2.需要重定向到错误页面
                   const errorInfo = error.response
                   console.log(errorInfo)
                   if (errorInfo) {
                       // error =errorInfo.data//页面那边catch的时候就能拿到详细的错误信息,看最下边的Promise.reject
                       const errorStatus = errorInfo.status; // 404 403 500 ... 等
                       // router.push({
                       //     path: `/error/${errorStatus}`
                       // })
                   }
                   return Promise.reject(error) // 在调用的那边可以拿到(catch)你想返回的错误信息
               }
           )
    
           // response 拦截器
           instance.interceptors.response.use(
               response => {
                   let data;
                   // IE9时response.data是undefined,因此需要使用response.request.responseText(Stringify后的字符串)
                   if (response.data == undefined) {
                       data = response.request.responseText
                   } else {
                       data = response.data
                   }
                   // console.log(response);
                   // 根据返回的code值来做不同的处理(和后端约定)
                   switch (data.code) {
                       case '':
                           break;
                       default:
                   }
                   // 若不是正确的返回code,且已经登录,就抛出错误
                   // const err = new Error(data.description)
    
                   // err.data = data
                   // err.response = response
    
                   // throw err
                   return data
               },
               err => {
                   if (err && err.response) {
                       switch (err.response.status) {
                           case 400:
                               err.message = '请求错误'
                               break
    
                           case 401:
                               err.message = '未授权,请登录'
                               break
    
                           case 403:
                               err.message = '拒绝访问'
                               break
    
                           case 404:
                               err.message = `请求地址出错: ${err.response.config.url}`
                               break
    
                           case 408:
                               err.message = '请求超时'
                               break
    
                           case 500:
                               err.message = '服务器内部错误'
                               break
    
                           case 501:
                               err.message = '服务未实现'
                               break
    
                           case 502:
                               err.message = '网关错误'
                               break
    
                           case 503:
                               err.message = '服务不可用'
                               break
    
                           case 504:
                               err.message = '网关超时'
                               break
    
                           case 505:
                               err.message = 'HTTP版本不受支持'
                               break
    
                           default:
                       }
                   }
                   console.error(err)
                   // 此处我使用的是 element UI 的提示组件
                   // Message.error(`ERROR: ${err}`);
                   return Promise.reject(err) // 返回接口返回的错误信息
               }
           )
           //请求处理
           instance(options)
               .then((res) => {
                   resolve(res)
                   return false
               })
               .catch((error) => {
                   reject(error)
               })
           // 处理结束
       })
    }
    

    api.js接口公共管理文件

    // api接口统一管理
    import axios from './instance'
    // 将所有的接口统一起来便于维护
    // 空气质量接口
    export const airQuality = (data) => {
        return axios({
            url: '/util/getAirData',
            method: 'POST',
            data,
            // handle:true
        })
    }
    
    // 默认全部导出
    // export default {
    //     airQuality
    // }
    
  • 使用,可以在main.js中直接导入,使用时,this.$api.airQuality()

    import api from './http/api.js' //引入接口文件
    Vue.prototype.$api = api; //挂载
    

    调用

    this.$api.airQuality(data).then((res)=>{
    	console.log(JSON.stringify(res));
    }).catch((err)=>{
    	console.log(err);
    });
    

    此方式使用时,项目运行是会一次性加载api文件中的所有接口

  • 方式二,使用时引入

    	<template>
    	</template>
    	
    	<script>
    	import { airQuality } from "@/http/api.js"; //引入使用的接口
    	export default {
    	    data() {
    	        return {
    	        
    	        };
    	    },
    	    created() {
    	        this.airQuality(); //调用接口
    	    },
    	    methods: {
    	        airQuality() {
    	            var data = {};
    	            airQuality(data).then((res) => {
    	                console.log(JSON.stringify(res));
    	            });
    	        }
    	    },
    	};
    	</script>
    
    	<style scoped>
    	</style>
    

结束:至此项目成功配置完毕,执行启动命令,打包命令测试环境输出对应,运行成功,其中如有错误还望大家多多指出,谢谢!

github项目地址github项目地址

vue-cli2.0与vue3.0+创建出的项目具体有什么不一样,本篇中暂未详细说明

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值