缘起

我无聊想试试如果登陆的时候填一些奇怪的东西进去,我的后端会不会爆炸。(别问我为什么现在才想起来测这个)

结果后端没爆炸(后面才知道),前端爆炸了。

image-20240108224555234

而且登陆失败的时候没有提示错误信息,因为想的是前端有一个统一的响应式拦截,应该会提示的,然而实际上并没有。

排查

查看请求,响应正常。

image-20240108231552374

使用无痕模式,正常访问(未登录)。

image-20240108231711382

使用Apifox测试后端,也正常响应。

那么可以肯定的是,后端没有问题。

那么肯定是前端的代码中存在问题。

于是大概猜到了(并且看了一下),响应中的为nullresult赋给了userInfo,并存到local storage中,然后发送请求,然后就寄了。

image-20240108233413398

还记得前面说过的前端有一个统一的响应式拦截吗?理论上如果有问题,拦截了,那么nullresult是不会赋给userInfo的。这个拦截是有用的嗷,之前后端返回401的响应是能够拦截并弹出错误信息的。《理论上》

然后我一看这个状态代码

image-20240108231420735

《200 OK》

噔 噔 咚

哈哈,怪不得不会被拦截呢

解决

原因找到了,那就很好解决了。这里选择的是改前端的代码,因为后端都是统一用一个Result类去封装响应信息的,然后所有的Controller都是用Result类中的success或者error方法封装信息,改后端不太现实,牵一发而动全身了属于是。

修改 userStore

修改登陆用到的getUserInfo方法,根据res.result是否为空判断登录是否成功(用res.code效果一样):

if(res.result!=null){
userInfo.value=res.result
// 合并购物车
await mergeCartAPI(cartStore.cartList.map(item=>{
return{
skuId:item.skuId,
selected:item.selected,
count:item.count
}
}))
await cartStore.updateNewList()
}
else {
ElMessage({
type:'warning',
message:res.message
})
}

修改登录页面的script

还有登录页面的doLogin方法:

if (userStore.userInfo.value!=null){
ElMessage({ type: 'success', message: '登录成功' })
await router.replace({path: '/'})
}

完成!

image-20240108233322607

userInfo也是正常存储。

image-20240108233455050

参考链接