theme: condensed-night-purple
highlight: a11y-dark
这是我参与「第五届青训营 」伴学笔记创作活动的第 12 天
前端开发
安装模块
- axios
- vuex
- vue-router
- sass 简化写css的复杂性 快速入门:https://www.cnblogs.com/hu308830232/p/14929143.html
- element-ui UI库
wangeditor 富文本编辑器
npm install @vue/[email protected] -g vue create client
npm install axios npm install [email protected] --save npm install [email protected] --save npm install sass npm i element-ui -S npm install @wangeditor/editor-for-vue --save
引入 main.js
```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 './routers/index' // import store from './store' import axios from 'axios'
Vue.use(ElementUI); axios.defaults.baseURL = 'http://localhost:8080' ```
路由
可以根据routes做侧边栏
<router-view></router-view>
占位
// 懒加载 const Test = () => import('../views/Test')
登录页面
数据库断开连接:8小时无通信,myslq就会自动关闭数据;
提交信息
js submitForm() { let params = { account : this.admin.account, password : this.admin.pass } this.$api.login.login(params) .then(res => { console.log(res.data); }) }
保存token ---使用vuex
看Login.vue代码
问题
1. 封装好axios,发送post请求无法传递data
post请求 数据需要序列化 使用qs插件:qs 是一个增加了一些安全性的查询字符串解析和序列化字符串的库。 qs.parse()是将URL解析成对象的形式 qs.stringify()是将对象序列化成URL的形式,以&进行拼接
封装axios后,发送请求的Content-Type 与直接axios不同,为application/x-www-form-urlencoded,服务端接收不到数据 判定为未登录 解决方法: 直接使用params 将请求头设置为'multipart/form-data' 或者 'application/json'
js return instance.post( 'http://localhost:8080/admin/login', // qs.stringify(params), // 数据序列化 params, { // headers:{'Content-Type': 'multipart/form-data'} headers:{'Content-Type':'application/json'} } )
2.问题:eslint-plugin-vue 报错
解决方法:在设置中搜索 Vetur>Validation:Template ,将这一项的勾选去掉即可 参考
封装api
1. 封装axios
2. 封装各种接口
3. 将所有接口封装到 api.js 里
后台管理系统
导航菜单
点击导航栏,显示对应组件 js toPage (menu) { if(menu.herf == 'logout') { this.$router.push('/login') } else { this.$router.push(menu.herf) } }
分类页面
使用表格展示数据
从后端拿数据,展示到表格内 参考
- 在 data 里定义 tableData 存放表格数据
- 在 生命周期函数 mounted 里执行定义的方法
- 定义方法showList,发送请求,获取分类数据 this.tableData = res.data.rows
- 在表格上使用 prop 获取数据
添加分类
使用Dialog 对话框, 设置 isShowDialog 属性来控制dialog的显示。 通过 input 获取添加的分类名称,发送请求,携带token。 后端返回状态,添加成功再次调用this.showList()
刷新页面,添加失败弹出提示, 然后设置 dialog 的显示 this.isShowDialog = false
token
设置请求拦截器 js const token = store.state.token; token && (config.headers.token = token); return config;
删除分类
要实现这一功能需要拿到该行的数据,那么如何获取表格的某一行数据呢? 这里我们使用 template中的作用域插槽,它的作用是在外部获取组件内的数据。 为了获取这一行的数据,我们让 slot-scope 值为scope
,那么由scope.row
就可以得到数据了
修改分类
和添加相同,使用Dialog 对话框,点击修改按钮弹出dialog,输入修改名称,发送请求, 修改成功调用this.showList()
刷新页面,修改失败弹出提示, 然后设置 dialog 的显示 this.isUpdateDialog = false
文章管理
添加文章
使用 wangeditor 富文本编辑器 按照demo,使用
1. 在 Article 里获取富文本中写入的值 ----- 使用 父子组件通信
- 父传子:props
- 子传父:自定义事件
自定义事件的流程∶ 在子组件中,通过$emit()
来触发事件。 在父组件中,通过v-on
来监听子组件事件。
父组件在使用子组件时自定义一个事件,值为父组件的 methods,函数的默认参数为$emit
传入的参数, 子组件定义方法,使用this.$emit('父组件的自定义事件名称',参数)
2. 初始化,将 Article 里的 content 在富文本中显示 ----- 使用 nextTick方法
如果content初始值不为空,想要在富文本中显示,这里使用 nextTick方法
Vue.nextTick用于延迟执行一段代码,它接受2个参数(回调函数和执行回调函数的上下文环境),如果没有提供回调函数,那么将返回promise对象。
在下次DOM更新循环结束之后执行延迟回调。在修改数据之后立即使用这个方法,获取更新后的DOM nexttick()已实现 dom更新之后对新dom进行延迟操作 具体的解释就是说Vue的DOM更新并不是在数据变化之后立即进行的,而是它会在数据变化之后开启一个异步更新的队列,需要等队列中所有的数据更新都完成之后,才会进行统一的更新。如果我们在一次事件循环中频繁修改同一个数据,它只会最后一次修改完成之后去更新DOM,最终呈现的结果是最后一次更新之后的结果。
应用场景: - 在Vue生命周期的created()钩子函数进行的DOM操作一定要放在Vue.nextTick()的回调函数中 - 在数据变化后要执行的某个操作,而这个操作需要使用随数据改变而改变的DOM结构的时候,这个操作都应该放进Vue.nextTick()的回调函数中。
参考: - 简单理解Vue中的nextTick - 简单易懂 关于nextTick()的理解
图片上传功能
进行富文本配置 js MENU_CONF: { uploadImage : { // 上传图片 完整的服务端地址 server: this.$store.state.serve_url + '/upload/rich_editor_upload', // 小于该值就插入 base64 格式(而不上传),默认为 0 base64LimitSize: 5 * 1024 // 5kb }, insertImage : { parseImageSrc:(src) => { if(src.indexOf('http') !== 0 ){ return `${this.$store.state.serve_url}${src}` } return src } } },
屏蔽视频上传
toolbarConfig.excludeKeys = [ 'uploadVideo' ]
选择分类
从后端获取数据成功,但是选择器不显示数据
必须先写标题,此时选择分类成功???WHY
添加文章
添加成功后文本框置空