完成项目的开发阶段,进入到发布阶段。
1. 添加进度条
给项目添加进度条效果,在项目控制台中,打开依赖,安装nprogress,打开main.js文件中,在axios请求拦截器和响应拦截器中添加如下代码(包括了携带token代码)
// 导入NProgress包对应的css 和js
import NProgress from 'nprogress'
import 'nprogress/nprogress.css'
// axios请求拦截器 请求头中携带token 展示进度条 NProgress.start()
axios.interceptors.request.use(config => {
NProgress.start()
config.headers.Authorization = window.sessionStorage.getItem('token') //Authorization为接口文件要求
return config
});
// axios响应拦截器
axios.interceptors.response.use(config => {
NProgress.done()
return config
});
2. 根据报错修改代码
根据报告中的警告信息查询到具体问题代码
常见问题:
{
"semi": false, // 格式化不加分号
"singleQuote": true,// 格式化以单引号为主
"printWidth": 200 // 格式化每行最多允许字符长度
}
3. 执行build 移除所有console信息
安装插件,在项目控制台中,安装开发依赖babel-plugin-transform-remove-console,在babel.config.js编写如下代码(包含了懒加载插件代码)
// 这是项目发布阶段需要用到的 babel 插件,防止开发阶段的console也被移除
const prodPlugins = []
if (process.env.NODE_ENV === 'production') {
prodPlugins.push('transform-remove-console')
}
module.exports = {
presets: ['@vue/app'],
plugins: [
[
'component',
{
libraryName: 'element-ui',
styleLibraryName: 'theme-chalk'
}
],
// 发布产品时候的插件数组 移除console 懒加载
...prodPlugins,
// 配置路由懒加载
'@babel/plugin-syntax-dynamic-import'
]
}
1. 生成打包报告,使用UI面板查看报告
在UI面板的打包报告中,可以看到打包的详细情况
2. 通过vue.config.js修改webpack的默认配置
新建vue.config.js文件来修改webpack的默认配置,主要是当处于开发模式和发布模式不同情况下做不一样的事情,不用模式配置不同的打包入口文件(即以下3-5步)
3. 为开发模式与发布模式指定不同的打包入口
Vue项目的开发模式和发布模式默认公用一个打包的入口文件,即main.js,但是不同开发模式下,入口文件内容可能会略不同,为了将开发过程和打包过程分离,需要配置不同的入口文件,
先将main.js复制一份并将两份分别命名为main-dev.js和main-prod.js,作为不同模式下的入口文件
4. configureWebpack 和 chainWebpack
配置不同的入口文件需要用这两种节点来定义webpack的打包配置
5. 通过chainWebpack自定义打包入口
这里使用其中一种方法来配置入口文件
具体完整代码(包含发布模式下加载CDN资源和定制首页内容)
module.exports = {
css: {
extract: false
},
chainWebpack: config => {
// 发布模式 设置入口文件目录
config.when(process.env.NODE_ENV === 'production', config => {
config
.entry('app')
.clear()
.add('./src/main-prod.js')
// 加载CDN资源
config.set('externals', {
vue: 'Vue',
'vue-router': 'VueRouter',
axios: 'axios',
lodash: '_',
echarts: 'echarts',
nprogress: 'NProgress',
'vue-quill-editor': 'VueQuillEditor'
})
// 定制首页内容
config.plugin('html').tap(args => {
args[0].isProd = true
return args
})
})
// 开发模式 设置入口文件目录
config.when(process.env.NODE_ENV === 'development', config => {
config
.entry('app')
.clear()
.add('./src/main-dev.js')
// 定制首页内容
config.plugin('html').tap(args => {
args[0].isProd = false
return args
})
})
}
}
6. 通过externals加载外部CDN资源
默认情况下,通过import语法导入的第三方依赖包,最终会被合并到同一个文件中,从而导致打包成功后,文件体积过大问题。
因此为了解决这种问题,可以通过webpack的externals节点,来配置加载外部的CDN资源,凡是声明在externals中的第三方依赖包,都不会被打包。
config.set('externals', {
vue: 'Vue',
'vue-router': 'VueRouter',
axios: 'axios',
lodash: '_',
echarts: 'echarts',
nprogress: 'NProgress',
'vue-quill-editor': 'VueQuillEditor'
})
添加到vue.config.js配置文件中
index.html文件的完整代码(包含Element UI 和定制首页内容)
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width,initial-scale=1.0" />
<link rel="icon" href="<%= BASE_URL %>favicon.ico" />
<title>
<%= htmlWebpackPlugin.options.isProd ? '' : 'dev - ' %>电商后台管理系统</title>
<% if(htmlWebpackPlugin.options.isProd){ %>
<!-- nprogress 的样式表文件 -->
<link rel="stylesheet" href="https://cdn.staticfile.org/nprogress/0.2.0/nprogress.min.css" />
<!-- 富文本编辑器 的样式表文件 -->
<link rel="stylesheet" href="https://cdn.staticfile.org/quill/1.3.4/quill.core.min.css" />
<link rel="stylesheet" href="https://cdn.staticfile.org/quill/1.3.4/quill.snow.min.css" />
<link rel="stylesheet" href="https://cdn.staticfile.org/quill/1.3.4/quill.bubble.min.css" />
<!-- element-ui 的样式表文件 -->
<link rel="stylesheet" href="https://cdn.staticfile.org/element-ui/2.8.2/theme-chalk/index.css" />
<script src="https://cdn.staticfile.org/vue/2.5.22/vue.min.js"></script>
<script src="https://cdn.staticfile.org/vue-router/3.0.1/vue-router.min.js"></script>
<script src="https://cdn.staticfile.org/axios/0.18.0/axios.min.js"></script>
<script src="https://cdn.staticfile.org/lodash.js/4.17.11/lodash.min.js"></script>
<script src="https://cdn.staticfile.org/echarts/4.1.0/echarts.min.js"></script>
<script src="https://cdn.staticfile.org/nprogress/0.2.0/nprogress.min.js"></script>
<!-- 富文本编辑器的 js 文件 -->
<script src="https://cdn.staticfile.org/quill/1.3.4/quill.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/vue-quill-editor.js"></script>
<!-- element-ui 的 js 文件 -->
<script src="https://cdn.staticfile.org/element-ui/2.8.2/index.js"></script>
<% } %>
</head>
<body>
<noscript>
<strong>We're sorry but vue_shop doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
</noscript>
<div id="app"></div>
<!-- built files will be auto injected -->
</body>
</html>
7. 通过externals优化Element UI的打包
8. 首页内容定制
不同的打包环境下,首页内容可能会有所不同,可以通过插件的方式来定制首页内容,例如不同的首页标题title
在vue.config.js文件中对插件进行配置,见第五条中的内容定制代码,
然后在index.html首页中渲染,见第六步中定制内容代码
// 这是项目发布阶段需要用到的 babel 插件
const prodPlugins = []
if (process.env.NODE_ENV === 'production') {
prodPlugins.push('transform-remove-console')
}
module.exports = {
presets: ['@vue/app'],
plugins: [
[
'component',
{
libraryName: 'element-ui',
styleLibraryName: 'theme-chalk'
}
],
// 发布产品时候的插件数组
// 移除发布阶段的console
...prodPlugins,
// 配置路由懒加载
'@babel/plugin-syntax-dynamic-import'
]
}
import Vue from 'vue'
import VueRouter from 'vue-router'
// import Login from './components/Login.vue'
const Login = () =>
import ( /* webpackChunkName: "login_home_welcome" */ '../components/Login.vue')
// import Home from './components/Home.vue'
const Home = () =>
import ( /* webpackChunkName: "login_home_welcome" */ '../components/Home.vue')
// import Welcome from './components/Welcome.vue'
const Welcome = () =>
import ( /* webpackChunkName: "login_home_welcome" */ '../components/Welcome.vue')
// import Users from './components/user/Users.vue'
const Users = () =>
import ( /* webpackChunkName: "Users_Rights_Roles" */ '../components/user/Users.vue')
// import Rights from './components/power/Rights.vue'
const Rights = () =>
import ( /* webpackChunkName: "Users_Rights_Roles" */ '../components/power/Rights.vue')
// import Roles from './components/power/Roles.vue'
const Roles = () =>
import ( /* webpackChunkName: "Users_Rights_Roles" */ '../components/power/Roles.vue')
// import Cate from './components/goods/Cate.vue'
const Cate = () =>
import ( /* webpackChunkName: "Cate_Params" */ '../components/goods/Cate.vue')
// import Params from './components/goods/Params.vue'
const Params = () =>
import ( /* webpackChunkName: "Cate_Params" */ '../components/goods/Params.vue')
// import GoodsList from './components/goods/List.vue'
const GoodsList = () =>
import ( /* webpackChunkName: "GoodsList_Add" */ '../components/goods/List.vue')
// import Add from './components/goods/Add.vue'
const Add = () =>
import ( /* webpackChunkName: "GoodsList_Add" */ '../components/goods/Add.vue')
// import Order from './components/order/Order.vue'
const Order = () =>
import ( /* webpackChunkName: "Order_Report" */ '../components/order/Order.vue')
// import Report from './components/report/Report.vue'
const Report = () =>
import ( /* webpackChunkName: "Order_Report" */ '../components/report/Report.vue')
Vue.use(VueRouter)
const routes = [
{ path: '/', redirect: '/login' },
{ path: '/login', component: Login },
{
path: '/home',
component: Home,
// 进入home时 重定向welcome
redirect: '/welcome',
children: [
{ path: '/welcome', component: Welcome },
{ path: '/users', component: Users },
{ path: '/rights', component: Rights },
{ path: '/roles', component: Roles },
{ path: '/categories', component: Cate },
{ path: '/params', component: Params },
{ path: '/goods', component: GoodsList },
{ path: '/goods/add', component: Add },
{ path: '/orders', component: Order },
{ path: '/reports', component: Report }
]
}
]
const router = new VueRouter({
routes
})
// 挂载路由导航守卫
router.beforeEach((to, from, next) => {
// to 将要访问的路径
// from 代表从哪个路径跳转而来
// next 是一个函数,表示放行
// next()放行 next('/login')强制跳转
if (to.path === '/login') return next()
// 获取token
const tokenStr = window.sessionStorage.getItem('token')
if (!tokenStr) return next('/login');
next()
})
export default router
懒加载总结:
开发依赖中下载懒加载插件,在babel.config.js中配置懒加载插件,将路由文件中的按需修改路由,完成!
1. 通过node创建web服务器
创建文件夹vue_shop_server,
初始化包管理配置文件 npm init -y,
安装express npm i express -S,
将dist文件复制到vue_shop_server文件夹中,
新建文件app.js入口文件内容如下(包含gzip压缩,和配置https服务):
const express = require('express')
const compression = require('compression')
const https = require('https')
const fs = require('fs')
const app = express()
const options = {
cert: fs.readFileSync('./full_chain.pem'),
key: fs.readFileSync('./private.key')
}
// 一定要把这一行代码,写到 静态资源托管之前 gzip压缩
app.use(compression())
app.use(express.static('./dist'))
app.listen(80, () => {
console.log('server running at http://127.0.0.1')
})
// https.createServer(options, app).listen(443)
配置完成,在终端使用node ./app.js运行,在浏览器输入127.0.0.1可以访问
4. 使用pm2管理应用