詳解vue微信網(wǎng)頁授權(quán)最終解決方案
vue微信網(wǎng)頁授權(quán),基于vue-cli3.0+webpack 4+vant ui + sass+ rem適配方案+axios,開發(fā)的微信授權(quán)方案。項目地址:vue-wechat-auth
參考了[vue-wechat-login],思路有些不同,本文基于進入所有頁面都必須先授權(quán)的操作。
與之前寫的授權(quán)不同之處
這次的邏輯全部在router的beforeEach進行,相較更加簡潔明。之前是在一個中間頁author.vue中,加上微信授權(quán)要跳轉(zhuǎn)很多次
在這里你能找到
微信網(wǎng)頁授權(quán)前端解決方案,官方文檔
如何使用Natapp(ngrok)進行微信本地開發(fā)調(diào)試,官方文檔
如何配置微信開發(fā)測試賬號
關(guān)于測試賬號和本地開發(fā)設(shè)置
由于文章過長這里[微信測試賬號和本地開發(fā)調(diào)試]記得回來哦~
微信網(wǎng)頁授權(quán)
都設(shè)置好了那就開始微信網(wǎng)頁開發(fā)第一步也是最重要的一步,微信網(wǎng)頁授權(quán)
關(guān)于授權(quán)你首先要清楚的是,服務(wù)端要用到的是微信openid還是微信unionid,這兩者的區(qū)別是,如果你要的是unionid,那么你需要在[微信開放平臺]去綁定測試賬號。測試號的appId和appsecret在微信公眾平臺的測試號里找。微信公眾號后臺->開發(fā)者工具->公眾平臺測試帳號->進入
如果你不需要unionid,那這個你就可以省略, 如果服務(wù)端是需要unionid的那不綁定的話授權(quán)會把報錯的。記得問一下服務(wù)端開發(fā)人員哦。
開發(fā)
首先我們看下微信授權(quán)的流程圖,關(guān)于微信網(wǎng)頁授權(quán)
前端需要做的是
第一步:用戶同意授權(quán),獲取code,拼接微信授權(quán)地址,redirect_uri就是你的當前地址,關(guān)于appid有些人是通過接口獲取的,我這里就直接寫在項目全局變量里了VUE_APP_WECHAT_APPID,用戶授權(quán)成功后微信會攜帶code和status跳回來
https://open.weixin.qq.com/connect/oauth2/authorize?appid=${this.appid}&redirect_uri=${this.redirect_uri}&response_type=code&scope=${ this.scope}&state=${this.state}#wechat_redirect
第二步,訪問登錄接口,將code傳給服務(wù)端,小哥哥進行一系列的操作,通過code換取網(wǎng)頁授權(quán)access_token,拉取用戶信息(需scope為 snsapi_userinfo),返回是否登錄成功,成功后返回用戶信息和登錄令牌 token
在permission.js中路由攔截進行這一系列操作,代碼注釋很詳細了
permission.js
import router from './router' import store from './store' import getPageTitle from '@/utils/get-page-title' import wechatAuth from './plugins/wechatAuth' // 微信登錄插件 const qs = require('qs') router.beforeEach((to, from, next) => { const loginStatus = Number(store.getters.loginStatus) console.log('loginStatus=' + loginStatus) console.log('token=' + store.getters.token) // 頁面標題 document.title = getPageTitle(to.meta.title) if (loginStatus === 0) { // 微信未授權(quán)登錄跳轉(zhuǎn)到授權(quán)登錄頁面 const url = window.location.href // 解決重復(fù)登錄url添加重復(fù)的code與state問題 const parseUrl = qs.parse(url.split('?')[1]) let loginUrl if (parseUrl.code && parseUrl.state) { delete parseUrl.code delete parseUrl.state loginUrl = `${url.split('?')[0]}?${qs.stringify(parseUrl)}` } else { loginUrl = url } // 設(shè)置微信授權(quán)回調(diào)地址 wechatAuth.redirect_uri = loginUrl // 無論拒絕還是授權(quán)都設(shè)置成1 store.dispatch('user/setLoginStatus', 1) // 跳轉(zhuǎn)到微信授權(quán)頁面 window.location.href = wechatAuth.authUrl } else if (loginStatus === 1) { // 用戶已授權(quán),獲取code try { // 通過回調(diào)鏈接設(shè)置code status wechatAuth.returnFromWechat(to.fullPath) } catch (err) { // 失敗,設(shè)置狀態(tài)未登錄,刷新頁面 store.dispatch('user/setLoginStatus', 0) location.reload() } // 同意授權(quán) to.fullPath 攜帶code參數(shù),拒絕授權(quán)沒有code參數(shù) const code = wechatAuth.code if (code) { // 拿到code 訪問服務(wù)端的登錄接口 store .dispatch('user/loginWechatAuth', code) .then(res => { // 成功設(shè)置已登錄狀態(tài) store.dispatch('user/setLoginStatus', 2) next() }) .catch(() => { // 失敗,設(shè)置狀態(tài)未登錄,刷新頁面 store.dispatch('user/setLoginStatus', 0) location.reload() }) } else { store.dispatch('user/setLoginStatus', 0) location.reload() } } else { // 已登錄直接進入 next() } })
登錄成功后存用戶信息,token。訪問所有的接口的時候都會在header攜帶token,如果token失效了,服務(wù)端會返回401,做退出操作,刪除登錄狀態(tài),用戶信息,token,刷新頁面重新進入。
request.js
// 登錄超時,重新登錄 if (res.status === 401) { store.dispatch('user/fedLogOut').then(() => { location.reload() }) }
用戶登錄后將token和用戶信息存入storage中,登錄狀態(tài)設(shè)置到cookie里,store user中主要是進行用戶信息存貯獲取刪除的操作
store/modules/user.js
import { loginByCode } from '@/api/user' import { saveToken, saveLoginStatus, saveUserInfo, removeToken, removeUserInfo, removeLoginStatus, loadLoginStatus, loadToken, loadUserInfo } from '@/utils/cache' const state = { loginStatus: loadLoginStatus(), // 登錄狀態(tài) token: loadToken(), // token userInfo: loadUserInfo() // 用戶登錄信息 } const mutations = { SET_USERINFO: (state, userInfo) => { state.userInfo = userInfo }, SET_LOGIN_STATUS: (state, loginStatus) => { state.loginStatus = loginStatus }, SET_TOKEN: (state, token) => { state.token = token } } const actions = { // 登錄相關(guān),通過code獲取token和用戶信息 loginWechatAuth({ commit }, code) { const data = { code: code } return new Promise((resolve, reject) => { loginByCode(data) .then(res => { // 存用戶信息,token commit('SET_USERINFO', saveUserInfo(res.data.user)) commit('SET_TOKEN', saveToken(res.data.token)) resolve(res) }) .catch(error => { reject(error) }) }) }, // 設(shè)置狀態(tài) setLoginStatus({ commit }, query) { if (query === 0 || query === 1) { // 上線打開注釋,本地調(diào)試注釋掉,保持信息最新 removeToken() removeUserInfo() } // 設(shè)置不同的登錄狀態(tài) commit('SET_LOGIN_STATUS', saveLoginStatus(query)) }, // 登出 fedLogOut() { // 刪除token,用戶信息,登陸狀態(tài) removeToken() removeUserInfo() removeLoginStatus() } } export default { namespaced: true, state, mutations, actions }
在根目錄下.env開頭的三個文件中設(shè)置微信appID
VUE_APP_WECHAT_APPID='12345678'復(fù)制代碼
授權(quán)再也難不住我了,如果哪里有問題希望大家給我留言糾正,互相學習
以上就是本文的全部內(nèi)容,希望對大家的學習有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
移動端底部導(dǎo)航固定配合vue-router實現(xiàn)組件切換功能
經(jīng)常遇到這樣的需求,移動端中的導(dǎo)航并不是在頂部也不是在底部,而是在最底部且是固定的,當我們點擊該導(dǎo)航項時會切換到對應(yīng)的組件。這篇文章主要介紹了移動端底部導(dǎo)航固定配合vue-router實現(xiàn)組件切換功能,需要的朋友可以參考下2019-06-06vue3使用自定義指令實現(xiàn)el dialog拖拽功能示例詳解
這篇文章主要為大家介紹了vue3使用自定義指令實現(xiàn)el dialog拖拽功能示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪2022-09-09vue elementUI table 自定義表頭和行合并的實例代碼
這篇文章主要介紹了vue elementUI table 自定義表頭和行合并的實例代碼,本文通過實例代碼給大家介紹的非常詳細,具有一定的參考借鑒價值,需要的朋友可以參考下2019-05-05解決vue無法加載文件D:\Program Files\nodejs\node_global\vue.ps1,
這篇文章主要給大家介紹了關(guān)于解決vue無法加載文件D:\Program Files\nodejs\node_global\vue.ps1,因為在此系統(tǒng)上禁止運行腳本的相關(guān)資料,這個報錯是由于在系統(tǒng)上禁止運行腳本導(dǎo)致的,文中通過圖文介紹的非常詳細,需要的朋友可以參考下2024-01-01詳解基于Vue2.0實現(xiàn)的移動端彈窗(Alert, Confirm, Toast)組件
這篇文章主要介紹了詳解基于Vue2.0實現(xiàn)的移動端彈窗(Alert, Confirm, Toast)組件,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧2018-08-08