VUE指南-搭建后台管理平台
开发工具:webstorm
一、VUE可视化管理创建项目:
(1)Win + R运行对话框,输入CMD打开命令提示符弹窗,输入vue ui运行vue项目管理器
(2)项目配置
- 点击底部“在此创建新项目按钮”,输入项目名(必须为英文),选择项目预设。(手动基础配置建议选择:Babel/Router/CSS Pre-processors)
- 1.是否需要历史模式,不需要不用管。默认将使用兼容更好的哈希模式路由安装。Use history mode for router?
- 2.Pick a CSS pre-processor:选择Sass/SCSS (with node-sass),(node-sass是自动编译实时的,dart-sass需要保存后才会生效)Pick a CSS pre-processor
- 是否需要保存为项目预设方便下次使用,创建项目不需要保存
(3)插件与依赖安装
- 在插件栏中,点击右上角添加插件,搜索axios并安装。
- 在依赖栏中,点击右上角添加依赖,搜索element-ui并安装。
(4)目录清理
<template> <div id="app"> <router-view/> </div> </template>
(5)启动项目
- 点击任务栏,选择serve运行,点击启动app
二、创建代码托管仓库:(可跳过)
(1)如果没有码云SSH公钥 创建教程:https://gitee.com/help/articles/4181
(2)新建仓库后,上传新增项目到码云中。在项目根目录Terminal中运行:git remote add origin https://gitee.com/Alex_Tian/tstest.git
(3)如果提示码云的账号密码错误,清除账号密码 重新输入 git config --system --unset credential.helper 由于linux输入密码都不反显,输入完成回车就行。
三、配置路由Router
import Vue from 'vue' import VueRouter from 'vue-router' // —————————————————————————————— // 页面进度条 // —————————————————————————————— import NProgress from 'nprogress'//引入nprogress import 'nprogress/nprogress.css' //这个样式必须引入 NProgress.inc(0.1); NProgress.configure({easing: 'ease', speed: 500, showSpinner: false}); // —————————————————————————————— // 路由重复解决 // —————————————————————————————— const originalPush = VueRouter.prototype.push; VueRouter.prototype.push = function push(location) { return originalPush.call(this, location).catch(err => err) }; import Vue from 'vue' import VueRouter from 'vue-router' // —————————————————————————————— // 页面进度条 // —————————————————————————————— import NProgress from 'nprogress'//引入nprogress import 'nprogress/nprogress.css' //这个样式必须引入 NProgress.inc(0.1); NProgress.configure({easing: 'ease', speed: 500, showSpinner: false}); // —————————————————————————————— // 路由重复解决 // —————————————————————————————— const originalPush = VueRouter.prototype.push; VueRouter.prototype.push = function push(location) { return originalPush.call(this, location).catch(err => err) }; // —————————————————————————————— // 创建路由 // —————————————————————————————— /**其他*/ const Dashboard = () => import('../views/dashboard/index'); // 根目录 const Login = () => import('../views/login/index');// 登录 const Welcome = () => import('../views/home/welcome');// 欢迎 Vue.use(VueRouter); const routes = [ /** * redirect: 路由重定向 * */ { path: '/', redirect: '/welcome', }, { path: '/login', name: 'Login', component: Login }, //资源管理 { path: '/swResourceManage', name: '资源管理', component: Dashboard, children: [ { path: '/organization', component: Organization, name: '二级', children: [ { path: '/organizationUpdata', component: OrganizationUpdata, name: '三级', }, ] }, ] }, ]; // —————————————————————————————— // 进入某个路由之前(挂载导航守卫) // —————————————————————————————— router.beforeEach((to, from, next) => { // to 将要访问的路径 // from 从来跳转而来 // next 函数,表示放行 next():放行 next('/'):要强制跳转的路径 // 页面进度条开始 NProgress.start(); // 访问登录页,放行 if (to.path === '/login') return next(); // 访问页面是否有token,有放行,没有跳转登录页 const tokenStr = window.sessionStorage.getItem('accessToken'); if (!tokenStr) return next('/login'); next() }); // —————————————————————————————— // 进入某个路由之后 // —————————————————————————————— router.afterEach((to, from, next) => { console.log(to.meta.title); if (to.meta.title) { document.title = to.meta.title; //在路由里面写入的meta里面的title字段 } // 页面进度条结束 NProgress.done(); // 默认结束回到顶部 window.scrollTo(0, 0) }); export default router
四、封装request.js
- 根目录新增plugins文件夹,创建request.js
/**引入axios、路由、Element的消息提醒*/ import axios from 'axios' import router from '../router' import {Message} from 'element-ui' /**创建一个axios实例*/ const service = axios.create({ baseURL: 'http://******/', // api地址 timeout: 5000 // 请求超时时间 }); /**添加请求拦截器*/ // 在请求或响应被 then 或 catch 处理前拦截它们 // 登陆请求服务器没有发令牌,不能放在登陆中 service.interceptors.request.use(function (config) { // 在发送请求之前做些什么(请求头放入token) config.headers.accessToken = window.sessionStorage.getItem('accessToken'); // 固定写法最后return config return config }, function (error) { // 对请求错误做些什么 return Promise.reject(error) }); /**添加响应拦截器*/ service.interceptors.response.use(response => { // 对响应数据做点什么(如果返回的状态码不是0或是-1 就主动报错) const res = response.data; if (res.code !== 0 || res.code === -1) { Message({ message: res.msg, type: 'warning', duration: 3000 }); // 如果状态码超时,重新登录 if (res.code === 10003) { router.push('/login'); window.sessionStorage.clear() } return Promise.reject(new Error(res.data.msg || 'Error')) } else { return res.data } }, error => { console.log('err' + error) // for debug Message({ message: error.message, type: 'error', duration: 5 * 1000 }) return Promise.reject(error) }) /** 统一封装GET请求*/ export const get = (url, params, config = {}) => { return new Promise((resolve, reject) => { service({ method: 'GET', url, params, ...config }).then(response => { console.log(response) resolve(response) }).catch(error => { reject(error) }) }) }; /** 统一封装POST请求*/ export const post = (url, data, config = {}) => { return new Promise((resolve, reject) => { service({ method: 'POST', url, data, ...config }).then(response => { resolve(response) }).catch(error => { reject(error) }) }) }; export default service
五、配置api接口地址
- 根目录新增api文件夹,创建integration.js
import service from '../plugins/request' // —————————————————————————————— // 控制台 // —————————————————————————————— /** * 数据概览(完成) */ export const getDataOverview = (params) => service.get(`/manage/dataOverview/getDataOverview`, params); /** * 操作日志查询(含分页) */ export const opGetPageAndParam = (data) => service.post(`/manage/operationLog/getPageAndParam`, data);
六、使用Postman测试api接口(可跳过)
- 在postman中输入接口地址,在Headers中填入token(登录除外),在Body中填入参数,在X-WWW 填入键值对的参数,点击send按钮测试接口。
- 如果后台发的是json格式的文档,点击顶部左上角的Import,点击Upload Files按钮导入使用。
七、api接口优化
- 在src根目录下创建api目录,api目录中包含index.js(接口输出)和integration.js(全部接口管理)
- 在main.js中引入index.js
import '@/api/index' // api
- index.js 输入接口
import Vue from 'vue' import integration from './integration' Vue.prototype.$api = { integration };
- integration.js 接口管理
import request from '../plugins/request' // —————————————————————————————— // 登录相关 // —————————————————————————————— /** * 获取当前登录的菜单权限 * @params username 账号 默认admin * @params password 账号 默认123456 */ const userLogin = (data) => request({ url: '/manage/admin/login', method: 'post', data }); /** * 获取当前登录的菜单权限 * @params username type 默认传1 */ const getUserMenuList = (params) => request({ url: '/manage/userMenuResource/getUserMenuList', method: 'GET', params }); export default { userLogin, getUserMenuList }
八、vue.config.js 配置
const path = require('path'); const BundleAnalyzerPlugin = require('webpack-bundle-analyzer').BundleAnalyzerPlugin; //导入可视化打包分析 module.exports = { /** * productionSourceMap: * 如果你不需要生产环境的 source map,可以将其设置为 false 以加速生产环境构建。 * */ productionSourceMap:false, /** * runtimeCompiler:是否使用包含运行时编译器的 Vue 构建版本。 * 设置为 true 后你就可以在 Vue 组件中使用 template 选项了,但是这会让你的应用额外增加 10kb 左右。 * */ runtimeCompiler: true, /** * publicPath; 设置部署应用包时的基本URL * 这个值也可以被设置为空字符串 ('') 或是相对路径 ('./'), * 这样所有的资源都会被链接为相对路径,这样打出来的包可以被部署在任意路径。 * */ publicPath: './', /** * lintOnSave:是否在保存的时候使用 `eslint-loader` 进行检查 * 当设置为 `"error"` 时,检查出的错误会触发编译失败。 * */ lintOnSave: false, /** * configureWebpack:如果这个值是一个对象,则会通过 webpack-merge 合并到最终的配置中。 * 如果这个值是一个函数,则会接收被解析的配置作为参数。 * 该函数及可以修改配置并不返回任何东西,也可以返回一个被克隆或合并过的配置版本。 * */ configureWebpack: { plugins: [ // webpack-bundle-analyzer 是否使用可视化打包分析 /* new BundleAnalyzerPlugin({ analyzerMode: 'static', analyzerPort: 8091, // 运行后的端口号 可以修改 generateStatsFile: true, statsOptions: {source: false} })*/ ], // 别名配置 resolve: { alias: { '@': path.resolve(__dirname, './src'), 'assets': path.resolve(__dirname, './src/assets/images'), 'api': path.resolve(__dirname, './src/api'), } }, }, /** * devServer:所有 webpack-dev-server 的选项都支持。 * 当设置为 `"error"` 时,检查出的错误会触发编译失败。 * */ devServer: { port: 8080, // 端口 https: false, // 启用https // proxy:如果你的前端应用和后端 API 服务器没有运行在同一个主机上,你需要在开发环境下将 API 请求代理到 API 服务器。 proxy: { '/api': { target: `http://118.25.80.211:8080/`, changeOrigin: true, // 允许跨域 ws: true, pathRewrite: { '^/api': '/' } } } }, };
九、页面根目录结构与封装
- 页面结构