(1)退出功能實現
在NavHeader.vue中:
<div class="topbar-user">
<a href="javascript:;" v-if="username">{{username}}</a>
<a href="javascript:;" v-if="!username" @click="login">登錄</a>
<a href="javascript:;" v-if="username" @click="logout">登錄</a>
<a href="javascript:;" v-if="username">我的訂單</a>
<a href="javascript:;" class="my-cart">
<span class="icon-cart" @click="goToCart"></span> 購物車({{cartCount}})
</a>
</div>
<script>
export default {
methods: {
logout() {
this.axios.post('/user/logout').then(() => {
this.$message.success("退出成功");
this.$cookie.set('userId', '', {expires: '-1'}); //清空cookie中的信息
this.$store.dispatch('saveUserName', '') //清除頁面中的用戶名
this.$store.dispatch('saveCartCount', '0') // 清空購物車數量
})
},
}
}
</script>
(2)解決一個問題:
-
問題:在退出後,再次登錄後,發現購物車數量爲0,不是用戶購物車中該有的數量。
-
原因:雖然之前在App.vue中寫過代碼:
<script> export default { mounted() { this.getUser(); this.getCartCount(); }, methods: { getUser() { this.axios.get('/user').then((res = {}) => { this.$store.dispatch('saveUserName', res.username); }) }, getCartCount() { this.axios.get('/carts/products/sum').then((res = 0) => { this.$store.dispatch('saveCartCount', res); }) } } } </script>
但當時這麼寫的原因:Vuex是在內存中存儲數據的,但我們頁面刷新時,內存中數據會自動消失,爲保持數據一致性,所以需要重新獲取數據,並存儲在Vuex中。
但在單頁面應用中,但我們重新退出再登錄時,頁面並沒有重新刷新,所以這個過程中並沒有重新調用App.vue。(App.vue只在第一次進入時調用,在之前頁面跳轉時不會調用)
-
解決方法:我們需要在NavHeader.vue中再次獲取購物車數量:
<script> export default { mounted() { this.getCartCount(); }, methods: { getCartCount() { this.axios.get('/carts/products/sum').then((res = 0) => { this.$store.dispatch('saveCartCount', res); }) } } } </script>
(3)然而,上面的解決方法還會存在一個問題:
-
問題:如果我們刷新後,會重複兩次獲取購物車數量,存在資源浪費。
-
解決方法:在NavHeader.vue中做個判斷:只有從登陸頁面中跳轉過來的才獲取購物車數量。
如何判斷是從登陸跳轉過來的呢?可以通過導航守衛。或在登陸頁面中做參數跳轉。
下面用在登陸頁面中做參數跳轉來解決問題:
在登陸頁面做參數跳轉方式有很多:query傳參、parmas傳參或直接在路由上通過?拼接,加入參數。
下面在NavHeader.vue通過parmas傳參:
<script> export default { mounted() { this.getProductList(); let params = this.$router.push.params; if (params && params.from == 'login') { this.getCartCount() } } } </script>
(4)接口優化
解決了上面的問題,但是有個問題:如果用戶沒有登錄的話,那在App.vue中就沒必要去獲取購物車的值。所以在App.vue中做個優化:屏蔽不需要調用的接口。
<script>
export default {
mounted() {
if (this.$cookie.get('userId')) {
this.getUser();
this.getCartCount();
}
}
}
</script>
在login.vue中把cookie改成會話級別的:(會話級別的意思是當瀏覽器退出後,會話才消失)
<script>
export default {
methods: {
login() {
let {username, password} = this;
this.axios.post('/user/login', {
username,
password
}).then((res) => {
this.$cookie.set('userId', res.id, {expires:'Session'}); //更改爲Session
this.$store.dispatch('saveUserName', res.username);
this.$router.push('/index')
})
}
}
}
</script>