一、获取用户信息存入vuex
api文件里添加获取用户信息的接口
// 该函数专门用于:根据token获取用户信息
export const reqUserInfo = () => ajax.get('/user/passport/auth/getUserInfo')
store/user.js文件里编写代码获取用户信息
import引入reqUserInfo,将用户信息存入vuex。
二、导航守卫
概念:路由跳转时,在特定的时刻,执行的一些函数
作用:可以在路由跳转时追加特殊逻辑(路由鉴权、获取用户信息等)
导航守卫越早使用越好
分类:
全局守卫(常用)===> 校门口看门的大爷
路由独享守卫===>宿舍楼值班的老师
组件内守卫===>某个班的班主任
项目中用到导航守卫的原因
每次路由跳转、刷新页面时,都要靠守卫,获取用户信息
对某些敏感路由做出访问限制(鉴权)
导航守卫一定要有出口===>next()
找到router/index.js文件配置全局导航守卫,要有一个鉴权名单
// 路由鉴权列表
const authPath = ['/trade']
路由鉴权:在用户没有登录的时候有些路由可以自由访问,会降低隐私权,所以需要路由鉴权
在全局导航守卫中追加几个规则
// 路由鉴权列表
const authPath = ['/trade','/pay','/paysuccess','/center']
细化鉴权:回到routes.js文件中给pay、addcart_success追加路由独享守卫
{
name:'addcart_success',
path:'/addcart_success',
component:AddCartSuccess,
// 只要命中该路由规则,beforeEnter就会执行
// 目标:只有从/detail才能到此处
beforeEnter: (to, from, next) => {
if (from.path.slice(0,7) === '/detail') {
next()
}else{
next('/home')
}
}
},
{
name:'pay',
path:'/pay',
component:Pay,
beforeEnter: (to, from, next) => {
if (from.path === '/trade') {
next()
}else{
next('/home')
}
}
},
到PaySuccess组件文件中追加组件内守卫
// beforeRouteEnter在路由规则匹配后,马上要挂载PaySuccess组件前调用
beforeRouteEnter(to,from,next){
if (from.path === '/pay') {
next()
}else{
next('/home')
}
}
三、交易路由
(一)路由鉴权,已经在全局导航守卫中实现
(二)切换地址
绑定点击事件,传入参数,接着在methods中写回调
// 切换收货地址的回调
changeAddress(id){
this.addressList.forEach((address)=>{
if (address.id === id) {
address.isDefault = '1'
}else{
address.isDefault = '0'
}
})
},
四、支付路由
(一)弹窗+显示二维码
弹窗还是使用element-ui来实现,将支付链接转为二维码(base64格式)
async handlePay(){
try{
// 将支付按钮转接为二维码(base64格式的)
let base64Url = await QRCode.toDataURL(this.payInfo.codeUrl)
// 准备一个html字符串,弹窗中显示
const htmlStr = `<img src="${base64Url}" style="width:200px">`
// 弹窗配置项
const options = {
dangerouslyUseHTMLString: true, //编译html代码
title:'微信扫码支付', //弹窗标题
center:true, //格式居中
showClose:false, //右上角的叉
showCancelButton:true, //取消按钮
cancelButtonText:'支付遇到问题', //取消按钮文本内容
confirmButtonText:'已完成支付' //确认按钮文本内容
}
// 使用element-ui弹窗
this.$alert(htmlStr, {
...options,
callback:async(action) => {
if (action === 'confirm') {
// 停止心跳
clearInterval(this.heartbeatID)
// 询问服务器是否支付成功
const result = await reqPayStatus(this.payInfo.orderId)
if (result.code === 200) {
this.$message.success('支付成功!')
// 支付成功跳转成功
this.$router.push('/paysuccess')
}else{
this.$message.warning('你的订单并未支付成功,请点击立即支付,重新付款!')
}
}else{
// 停止心跳
clearInterval(this.heartbeatID)
// 提示
this.$message.warning('若支付遇到问题,请致电客服解决!')
}
}
});
(二)心跳请求
在用户还未支付时使用心跳请求来发请求,直到用户支付成功或是支付遇到问题停止心跳
// 发起心跳请求
this.heartbeatID = setInterval(async ()=>{
// 联系服务器查看订单状态
const result = await reqPayStatus(this.payInfo.orderId)
// 判断订单状态
if (result.code === 200) {
// 支付成功
// 停止心跳
clearInterval(this.heartbeatID)
// 关闭弹窗
this.$msgbox.close()
// 跳转到支付成功路由
this.$router.push('/paysuccess')
}
},1000)
}catch (error){
this.$message.warning('支付二维码生成失败,请联系管理员!')
}
}
五、vee-validate表单验证
vee-validate是专门用来做表单验证的vue插件
(一)、安装npm install vee-validate@"<3.0.0" --save(vue2专用)
(二)、去src/utils/reg.js中补充几个正则
// 手机号正则
export const phoneReg = /^(13[0-9]|14[01456879]|15[0-35-9]|16[2567]|17[0-8]|18[0-9]|19[0-35-9])\d{8}$/
// 验证码正则
export const codeReg = /^\d{6}$/
// 密码正则
export const pwdReg = /^\w{6,21}$/
(三)、为了方便管理,在utils/validate.js中写规则
import Vue from 'vue';
import VeeValidate, { Validator } from 'vee-validate';
import zh_CN from 'vee-validate/dist/locale/zh_CN';
import { phoneReg,codeReg,pwdReg } from "@/utils/reg";
Vue.use(VeeValidate);
Validator.localize('zh_CN', zh_CN);
// 自定义一个校验手机的正则
Validator.extend('phone_rule',{
getMessage: field => {
return '手机号不合法!'
},
validate: value => {
return phoneReg.test(value)
}
})
// 验证必要性的规则
Validator.extend('required',{
// 验证规则
validate:(value) => { // value你输入的值
return value
},
// 验证失败的回调
getMessage:(field) => {
return field + '必须输入!'
}
})
// 验证码的验证规则
Validator.extend('code_rule',{
// 验证规则
validate:value => codeReg.test(value),
// 验证失败的回调
getMessage:field => '验证码必须为6位数字!',
})
// 密码的验证规则
Validator.extend('pwd_rule',{
// 验证规则
validate:value => pwdReg.test(value),
// 验证失败的回调
getMessage:filed => '密码为6到21位英文、数字、下划线!',
})
// 确认密码的验证规则
Validator.extend('ispwd',{
// 验证规则
validate:(value,args) => value === args[0],
// 验证失败的回调
getMessage:filed => '密码必须一致!',
})
// 协议同意的验证规则
Validator.extend('isagree',{
// 验证规则
validate:value => value,
// 验证失败的回调
getMessage:filed => '协议必须同意!',
})
(四)、在main.js中引入utils/validate.js
import '@/utils/validate'
(五)、验证输入项
<div class="content">
<label>手机号:</label>
<input
v-validate="'required|phone_rule'"
name="手机"
v-model="phone"
type="text"
placeholder="请输入你的手机号"
/>
<span class="error-msg">{{ errors.first('手机') }}</span>
</div>
<div class="content">
<label>验证码:</label>
<input
v-model="code"
type="text"
placeholder="请输入验证码"
v-validate="'required|code_rule'"
name="验证码"
/>
<button class="getcode" @click="getCode">获取验证码</button>
<span class="error-msg">{{ errors.first("验证码") }}</span>
</div>
<div class="content">
<label>登录密码:</label>
<input
v-model="password"
type="text"
placeholder="请输入你的登录密码"
v-validate="{ required: true, pwd_rule: true }"
name="密码"
/>
<span class="error-msg">{{ errors.first("密码") }}</span>
</div>
<div class="content">
<label>确认密码:</label>
<input
type="text"
placeholder="请输入确认密码"
v-model="re_password"
v-validate="{ required: true, ispwd: password }"
name="重复密码"
/>
<span class="error-msg">{{ errors.first("重复密码") }}</span>
</div>
<div class="controls">
<input
v-model="agree"
type="checkbox"
v-validate="{ isagree: true }"
name="协议"
/>
<span>同意协议并注册《优选商城用户协议》</span>
<span class="error-msg">{{ errors.first("协议") }}</span>
</div>
六、懒加载
什么是懒加载?
其实就是延迟加载,即当需要用到的时候再去加载
优点:减少网络开销,节约网络流量
在路由组件中这样引入
图片懒加载
控制台引入npm i vue-lazyload@1
在main.js文件中引入
找到搜索页面将图片位置改为
<img v-lazy="good.defaultImg"/>
结语:今天总算是完成了这个项目,战线拉得蛮长的,在做的过程中查缺补漏,也学到了不少的新东西。一定一定要将基础打好,接下来就开启下一阶段的学习了,加油!