This commit is contained in:
fanxb 2022-03-21 17:06:52 +08:00
parent ff87689671
commit 40290e6ac8
12 changed files with 516 additions and 483 deletions

View File

@ -8,7 +8,7 @@
"lint": "vue-cli-service lint" "lint": "vue-cli-service lint"
}, },
"dependencies": { "dependencies": {
"ant-design-vue": "^1.6.3", "ant-design-vue": "^1.7.8",
"axios": "^0.21.1", "axios": "^0.21.1",
"babel-plugin-import": "^1.13.0", "babel-plugin-import": "^1.13.0",
"clipboard": "^2.0.6", "clipboard": "^2.0.6",

View File

@ -7,10 +7,6 @@
<script> <script>
export default { export default {
name: "App", name: "App",
async created(){
//
await this.$store.dispatch("globalConfig/refreshServerConfig");
}
}; };
</script> </script>

View File

@ -56,3 +56,5 @@ window.vueInstance = new Vue({
store, store,
render: h => h(App) render: h => h(App)
}).$mount("#app"); }).$mount("#app");

View File

@ -1,7 +1,8 @@
import Vue from "vue"; import Vue from "vue";
import VueRouter from "vue-router"; import VueRouter from "vue-router";
import vuex from "../store/index.js"; import * as vuex from "../store/index.js";
import { GLOBAL_CONFIG, SUPPORT_NO_LOGIN, TOKEN } from "@/store/modules/globalConfig"; import { GLOBAL_CONFIG, SUPPORT_NO_LOGIN, TOKEN } from "@/store/modules/globalConfig";
import { checkJwtValid } from "@/util/UserUtil";
Vue.use(VueRouter); Vue.use(VueRouter);
@ -11,7 +12,7 @@ const routes = [
path: "/manage", path: "/manage",
component: () => import("@/views/manage/index"), component: () => import("@/views/manage/index"),
children: [ children: [
{ path: "/bookmarkTree", component: () => import("@/views/manage/bookmarkTree/index") }, { path: "bookmarkTree", component: () => import("@/views/manage/bookmarkTree/index") },
{ path: "personSpace/userInfo", component: () => import("@/views/manage/personSpace/index") }, { path: "personSpace/userInfo", component: () => import("@/views/manage/personSpace/index") },
] ]
}, },
@ -37,10 +38,14 @@ const router = new VueRouter({
/** /**
* 在此进行登录信息判断以及重定向到登录页面 * 在此进行登录信息判断以及重定向到登录页面
*/ */
router.beforeEach((to, from, next) => { router.beforeEach(async (to, from, next) => {
//进入主页面/管理页面时,确认已经进行初始化操作
if (to.path === '/' || to.path.startsWith("/manage")) {
await vuex.loginInit();
}
let supportNoLogin = to.path === '/' || to.path.startsWith("/public"); let supportNoLogin = to.path === '/' || to.path.startsWith("/public");
vuex.commit(GLOBAL_CONFIG + "/" + SUPPORT_NO_LOGIN, supportNoLogin); vuex.default.commit(GLOBAL_CONFIG + "/" + SUPPORT_NO_LOGIN, supportNoLogin);
if (!supportNoLogin && !checkJwtValid()) { if (!supportNoLogin && !checkJwtValid(vuex.default.state[GLOBAL_CONFIG][TOKEN])) {
//如不支持未登录进入切jwt已过期直接跳转到登录页面 //如不支持未登录进入切jwt已过期直接跳转到登录页面
next({ next({
path: "/public/login?to=" + btoa(location.href), path: "/public/login?to=" + btoa(location.href),
@ -51,23 +56,6 @@ router.beforeEach((to, from, next) => {
} }
}) })
/**
* 检查jwt是否有效
*/
function checkJwtValid () {
let token = vuex.state[GLOBAL_CONFIG][TOKEN];
try {
if (token && token.trim().length > 0) {
//检查token是否还有效
let content = window.atob(token.split(".")[1]);
if (content.exp > Date.now() / 1000) {
return true;
}
}
} catch (err) {
console.error(err);
}
return false;
}
export default router; export default router;

View File

@ -1,16 +1,55 @@
import Vue from "vue"; import Vue from "vue";
import Vuex from "vuex"; import Vuex from "vuex";
import globalConfig from "./modules/globalConfig"; import * as globalConfig from "./modules/globalConfig";
import treeData from "./modules/treeData"; import * as treeData from "./modules/treeData";
import { checkJwtValid } from "@/util/UserUtil";
Vue.use(Vuex); Vue.use(Vuex);
export default new Vuex.Store({ let store = new Vuex.Store({
state: {}, state: {},
mutations: {}, mutations: {},
actions: {}, actions: {},
modules: { modules: {
globalConfig, [globalConfig.GLOBAL_CONFIG]: globalConfig.store,
treeData [treeData.TREE_DATA]: treeData.store
} }
}); });
let noLoginFinish = false;
//执行各自的非登陆初始化
(async () => {
await store.dispatch(globalConfig.GLOBAL_CONFIG + "/" + globalConfig.noLoginInit);
await store.dispatch(treeData.TREE_DATA + "/" + treeData.noLoginInit);
noLoginFinish = true;
})();
/**
* 执行各模块的登陆后初始化
*/
export async function loginInit () {
if (!noLoginFinish) {
await finishNoLogin();
}
console.log(store.state[globalConfig.GLOBAL_CONFIG][globalConfig.TOKEN]);
if (checkJwtValid(store.state[globalConfig.GLOBAL_CONFIG][globalConfig.TOKEN])) {
await store.dispatch(globalConfig.GLOBAL_CONFIG + "/" + globalConfig.loginInit);
await store.dispatch(treeData.TREE_DATA + "/" + treeData.loginInit);
}
}
async function finishNoLogin () {
return new Promise((resolve) => {
let timer = setInterval(() => {
if (noLoginFinish) {
clearInterval(timer);
resolve();
}
}, 100);
})
}
export default store;

View File

@ -1,11 +1,15 @@
import localforage from "localforage"; import localforage from "localforage";
import HttpUtil from "../../util/HttpUtil"; import HttpUtil from "../../util/HttpUtil";
export const GLOBAL_CONFIG = "globalConfig"; export const GLOBAL_CONFIG = "globalConfig";
export const USER_INFO = "userInfo"; export const USER_INFO = "userInfo";
export const TOKEN = "token"; export const TOKEN = "token";
export const SERVER_CONFIG = "serverConfig"; export const SERVER_CONFIG = "serverConfig";
export const SUPPORT_NO_LOGIN = "supportNoLogin"; export const SUPPORT_NO_LOGIN = "supportNoLogin";
export const IS_INIT = "isInit";
export const noLoginInit = "noLoginInit";
export const loginInit = "loginInit";
/** /**
* 存储全局配置 * 存储全局配置
*/ */
@ -13,7 +17,7 @@ const state = {
/** /**
* 用户信息 * 用户信息
*/ */
[USER_INFO]: {}, [USER_INFO]: null,
/** /**
* token,null说明未获取登录凭证 * token,null说明未获取登录凭证
*/ */
@ -21,11 +25,11 @@ const state = {
/** /**
* 是否已经初始化完成,避免多次重复初始化 * 是否已经初始化完成,避免多次重复初始化
*/ */
isInit: false, [IS_INIT]: false,
/** /**
* 是否移动端 * 是否移动端
*/ */
isPhone: false, isPhone: /Android|webOS|iPhone|iPod|BlackBerry/i.test(navigator.userAgent),
/** /**
* 是否支持未登录进入页面 * 是否支持未登录进入页面
*/ */
@ -39,63 +43,47 @@ const state = {
const getters = {}; const getters = {};
const actions = { const actions = {
//未登录需要进行的初始化
async [noLoginInit] ({ commit }) {
commit(SERVER_CONFIG, await HttpUtil.get("/common/config/global"));
let token = await localforage.getItem(TOKEN);
if (token) {
commit(TOKEN, token);
window.jwtToken = token;
}
},
//登陆后的,初始化数据 //登陆后的,初始化数据
async init (context) { async [loginInit] (context) {
if (context.state.isInit) { if (context.state.isInit) {
return; return;
} }
const token = await localforage.getItem(TOKEN);
await context.dispatch("setToken", token);
let userInfo = await localforage.getItem(USER_INFO);
if (userInfo) {
context.commit(USER_INFO, userInfo);
}
try {
await context.dispatch("refreshUserInfo");
} catch (err) {
console.error(err);
}
context.commit("isInit", true);
context.commit("isPhone", /Android|webOS|iPhone|iPod|BlackBerry/i.test(navigator.userAgent));
},
async refreshUserInfo ({ commit }) {
let userInfo = await HttpUtil.get("/user/currentUserInfo"); let userInfo = await HttpUtil.get("/user/currentUserInfo");
await localforage.setItem(USER_INFO, userInfo); context.commit(USER_INFO, userInfo);
commit(USER_INFO, userInfo); context.commit(IS_INIT, true);
}, },
async setToken ({ commit }, token) { async setToken ({ commit }, token) {
await localforage.setItem(TOKEN, token); await localforage.setItem(TOKEN, token);
window.jwtToken = token;
commit(TOKEN, token); commit(TOKEN, token);
}, },
//登出清除数据 //登出清除数据
async clear (context) { async clear (context) {
await localforage.removeItem("userInfo"); await localforage.removeItem(TOKEN);
await localforage.removeItem("token");
context.commit(USER_INFO, null); context.commit(USER_INFO, null);
context.commit(TOKEN, null); context.commit(TOKEN, null);
context.commit("isInit", false); context.commit(IS_INIT, false);
}, },
/**
* 从服务器读取全局配置
*/
async refreshServerConfig ({ commit }) {
commit(SERVER_CONFIG, await HttpUtil.get("/common/config/global"));
}
}; };
const mutations = { const mutations = {
userInfo (state, userInfo) { [USER_INFO] (state, userInfo) {
state.userInfo = userInfo; state[USER_INFO] = userInfo;
}, },
token (state, token) { [TOKEN] (state, token) {
state.token = token; state[TOKEN] = token;
}, },
isInit (state, isInit) { [IS_INIT] (state, isInit) {
state.isInit = isInit; state[IS_INIT] = isInit;
},
isPhone (state, status) {
state.isPhone = status;
}, },
[SERVER_CONFIG] (state, serverConfig) { [SERVER_CONFIG] (state, serverConfig) {
state[SERVER_CONFIG] = serverConfig; state[SERVER_CONFIG] = serverConfig;
@ -106,7 +94,7 @@ const mutations = {
}; };
export default { export const store = {
namespaced: true, namespaced: true,
state, state,
getters, getters,

View File

@ -1,8 +1,26 @@
import localforage from "localforage"; import localforage from "localforage";
import { } from "ant-design-vue";
import HttpUtil from "../../util/HttpUtil"; import HttpUtil from "../../util/HttpUtil";
const TOTAL_TREE_DATA = "totalTreeData"; export const TREE_DATA = "treeData";
const VERSION = "version"; export const TOTAL_TREE_DATA = "totalTreeData";
export const VERSION = "version";
export const SHOW_REFRESH_TOAST = "showRefreshToast";
export const IS_INIT = "isInit";
export const IS_INITING = "isIniting";
export const noLoginInit = "noLoginInit";
export const loginInit = "loginInit";
/**
* 版本检查定时调度
*/
let timer = null;
/**
* 刷新书签确认弹窗是否展示
*/
let toastShow = false;
/** /**
* 书签树相关配置 * 书签树相关配置
@ -10,12 +28,14 @@ const VERSION = "version";
const state = { const state = {
//全部书签数据 //全部书签数据
[TOTAL_TREE_DATA]: {}, [TOTAL_TREE_DATA]: {},
//版本
[VERSION]: null, [VERSION]: null,
isInit: false, //是否已经初始化书签数据
/** [IS_INIT]: false,
* 是否正在加载数据 // 是否正在加载数据
*/ [IS_INITING]: false,
isIniting: false //是否展示刷新书签数据弹窗
[SHOW_REFRESH_TOAST]: false
}; };
const getters = { const getters = {
@ -36,46 +56,40 @@ const getters = {
}; };
const actions = { const actions = {
//登陆后的,从缓存初始化数据 async [noLoginInit] () {
async init(context) {
},
async [loginInit] (context) {
if (context.state.isInit || context.state.isIniting) { if (context.state.isInit || context.state.isIniting) {
return; return;
} }
try { context.commit(IS_INITING, true);
context.commit("isIniting", true); context.commit(TOTAL_TREE_DATA, await localforage.getItem(TOTAL_TREE_DATA));
let realVersion = await HttpUtil.get("/user/version"); context.commit(VERSION, await localforage.getItem(VERSION));
let data = await localforage.getItem(TOTAL_TREE_DATA); await treeDataCheck(context, true);
let version = await localforage.getItem(VERSION); context.commit(IS_INIT, true);
if (!data || realVersion > version) { context.commit(IS_INITING, false);
await context.dispatch("refresh"); timer = setInterval(treeDataCheck, 5 * 60 * 1000);
} else {
context.commit(TOTAL_TREE_DATA, data);
context.commit(VERSION, version);
}
context.commit("isInit", true);
} finally {
context.commit("isIniting", false);
}
}, },
/** /**
* 确保数据加载完毕 * 确保数据加载完毕
*/ */
ensureDataOk(context) { ensureDataOk (context) {
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
let timer = setInterval(() => { let timer = setInterval(() => {
try { try {
if (context.state.isInit && context.state.isIniting == false) { if (context.state[IS_INIT] && context.state[IS_INITING] == false) {
clearInterval(timer); clearInterval(timer);
resolve(); resolve();
} }
} catch (err) { } catch (err) {
reject(err); reject(err);
} }
}, 100); }, 50);
}); });
}, },
//刷新缓存数据 //刷新缓存数据
async refresh(context) { async refresh (context) {
let treeData = await HttpUtil.get("/bookmark/currentUser"); let treeData = await HttpUtil.get("/bookmark/currentUser");
if (!treeData[""]) { if (!treeData[""]) {
treeData[""] = []; treeData[""] = [];
@ -93,9 +107,10 @@ const actions = {
await localforage.setItem(TOTAL_TREE_DATA, treeData); await localforage.setItem(TOTAL_TREE_DATA, treeData);
}, },
//清除缓存数据 //清除缓存数据
async clear(context) { async clear (context) {
context.commit(TOTAL_TREE_DATA, null); context.commit(TOTAL_TREE_DATA, null);
context.commit(VERSION, null); context.commit(VERSION, null);
context.commit(SHOW_REFRESH_TOAST, false);
context.commit("isInit", false); context.commit("isInit", false);
context.commit("isIniting", false); context.commit("isIniting", false);
await localforage.removeItem(TOTAL_TREE_DATA); await localforage.removeItem(TOTAL_TREE_DATA);
@ -104,7 +119,7 @@ const actions = {
/** /**
* 移动节点 * 移动节点
*/ */
async moveNode(context, info) { async moveNode (context, info) {
let data = context.state[TOTAL_TREE_DATA]; let data = context.state[TOTAL_TREE_DATA];
const target = info.node.dataRef; const target = info.node.dataRef;
const current = info.dragNode.dataRef; const current = info.dragNode.dataRef;
@ -175,14 +190,14 @@ const actions = {
/** /**
* 更新版本数据 * 更新版本数据
*/ */
async updateVersion({ commit, state }, version) { async updateVersion ({ commit, state }, version) {
commit(VERSION, version == null ? state[VERSION] + 1 : version); commit(VERSION, version == null ? state[VERSION] + 1 : version);
await localforage.setItem(VERSION, state[VERSION]); await localforage.setItem(VERSION, state[VERSION]);
}, },
/** /**
* 新增书签文件夹 * 新增书签文件夹
*/ */
async addNode(context, { sourceNode, targetNode }) { async addNode (context, { sourceNode, targetNode }) {
if (sourceNode === null) { if (sourceNode === null) {
if (context.state[TOTAL_TREE_DATA][""] === undefined) { if (context.state[TOTAL_TREE_DATA][""] === undefined) {
context.state[TOTAL_TREE_DATA][""] = []; context.state[TOTAL_TREE_DATA][""] = [];
@ -207,7 +222,7 @@ const actions = {
/** /**
* 删除节点数据 * 删除节点数据
*/ */
async deleteData(context, { pathList, bookmarkIdList }) { async deleteData (context, { pathList, bookmarkIdList }) {
//待删除的书签 //待删除的书签
let bookmarkIdSet = new Set(); let bookmarkIdSet = new Set();
bookmarkIdList.forEach(item => bookmarkIdSet.add(item)); bookmarkIdList.forEach(item => bookmarkIdSet.add(item));
@ -235,7 +250,7 @@ const actions = {
/** /**
* 编辑书签节点 * 编辑书签节点
*/ */
async editNode({ dispatch, state, commit }, { node, newName, newUrl, newIcon }) { async editNode ({ dispatch, state, commit }, { node, newName, newUrl, newIcon }) {
node.name = newName; node.name = newName;
node.url = newUrl; node.url = newUrl;
node.icon = newIcon; node.icon = newIcon;
@ -249,22 +264,58 @@ const mutations = {
[TOTAL_TREE_DATA]: (state, totalTreeData) => { [TOTAL_TREE_DATA]: (state, totalTreeData) => {
state.totalTreeData = totalTreeData; state.totalTreeData = totalTreeData;
}, },
isInit(state, isInit) { [IS_INIT] (state, isInit) {
state.isInit = isInit; state.isInit = isInit;
}, },
isIniting(state, isIniting) { [IS_INITING] (state, isIniting) {
state.isIniting = isIniting; state.isIniting = isIniting;
}, },
[VERSION]: (state, version) => { [VERSION]: (state, version) => {
state[VERSION] = version; state[VERSION] = version;
},
[SHOW_REFRESH_TOAST]: (state, val) => {
state[SHOW_REFRESH_TOAST] = val;
} }
}; };
export default {
async function treeDataCheck (context, isFirst) {
if (toastShow) {
return;
}
let realVersion = await HttpUtil.get("/user/version");
if (realVersion !== context.state[VERSION]) {
if (SHOW_REFRESH_TOAST && !isFirst) {
//如果在书签管理页面需要弹窗提示
window.vueInstance.$confirm({
title: "书签数据有更新,是否立即刷新?",
cancelText: "稍后提醒",
closable: false,
keyboard: false,
maskClosable: false,
onOk () {
toastShow = false;
return new Promise(async (resolve) => {
await context.dispatch("treeData/clear");
resolve();
});
},
afterClose () {
toastShow = false;
},
});
toastShow = true;
} else {
await context.dispatch("refresh");
}
}
}
export const store = {
namespaced: true, namespaced: true,
state, state,
getters, getters,
actions, actions,
mutations mutations
}; };

View File

@ -12,14 +12,14 @@ import router from "../router/index";
* @param {*} redirect 接口返回未认证是否跳转到登陆 * @param {*} redirect 接口返回未认证是否跳转到登陆
* @returns 数据 * @returns 数据
*/ */
async function request(url, method, params, body, isForm, redirect) { async function request (url, method, params, body, isForm, redirect) {
let options = { let options = {
url, url,
baseURL: "/bookmark/api", baseURL: "/bookmark/api",
method, method,
params, params,
headers: { headers: {
"jwt-token": vuex.state.globalConfig.token "jwt-token": window.jwtToken
} }
}; };
//如果是表单类型的请求,添加请求头 //如果是表单类型的请求,添加请求头
@ -65,7 +65,7 @@ async function request(url, method, params, body, isForm, redirect) {
* @param {*} params url参数 * @param {*} params url参数
* @param {*} redirect 未登陆是否跳转到登陆页 * @param {*} redirect 未登陆是否跳转到登陆页
*/ */
async function get(url, params = null, redirect = true) { async function get (url, params = null, redirect = true) {
return request(url, "get", params, null, false, redirect); return request(url, "get", params, null, false, redirect);
} }
@ -77,7 +77,7 @@ async function get(url, params = null, redirect = true) {
* @param {*} isForm 是否表单数据 * @param {*} isForm 是否表单数据
* @param {*} redirect 是否重定向 * @param {*} redirect 是否重定向
*/ */
async function post(url, params, body, isForm = false, redirect = true) { async function post (url, params, body, isForm = false, redirect = true) {
return request(url, "post", params, body, isForm, redirect); return request(url, "post", params, body, isForm, redirect);
} }
@ -89,7 +89,7 @@ async function post(url, params, body, isForm = false, redirect = true) {
* @param {*} isForm 是否表单数据 * @param {*} isForm 是否表单数据
* @param {*} redirect 是否重定向 * @param {*} redirect 是否重定向
*/ */
async function put(url, params, body, isForm = false, redirect = true) { async function put (url, params, body, isForm = false, redirect = true) {
return request(url, "put", params, body, isForm, redirect); return request(url, "put", params, body, isForm, redirect);
} }
@ -99,7 +99,7 @@ async function put(url, params, body, isForm = false, redirect = true) {
* @param {*} params url参数 * @param {*} params url参数
* @param {*} redirect 是否重定向 * @param {*} redirect 是否重定向
*/ */
async function deletes(url, params = null, redirect = true) { async function deletes (url, params = null, redirect = true) {
return request(url, "delete", params, null, redirect); return request(url, "delete", params, null, redirect);
} }

View File

@ -2,13 +2,31 @@ const TOKEN = "token";
/** /**
* 本地获取用户信息 * 本地获取用户信息
*/ */
export async function getUesrInfo() { export async function getUesrInfo () {
return window.vueInstance.$store.state.globalConfig.userInfo; return window.vueInstance.$store.state.globalConfig.userInfo;
} }
/** /**
* 从服务器获取用户信息 * 从服务器获取用户信息
*/ */
export async function getOnlineUserInfo() { export async function getOnlineUserInfo () {
return null; return null;
} }
/**
* 检查jwt是否有效
*/
export function checkJwtValid (token) {
try {
if (token && token.trim().length > 0) {
//检查token是否还有效
let content = JSON.parse(window.atob(token.split(".")[1]));
if (content.exp > Date.now() / 1000) {
return true;
}
}
} catch (err) {
console.error(err);
}
return false;
}

View File

@ -9,7 +9,9 @@ export default {
components: { components: {
header, header,
}, },
data() {}, data() {
return {};
},
methods: {}, methods: {},
}; };
</script> </script>

View File

@ -92,10 +92,11 @@
import AddBookmark from "@/components/main/things/AddBookmark.vue"; import AddBookmark from "@/components/main/things/AddBookmark.vue";
import Search from "@/components/main/Search.vue"; import Search from "@/components/main/Search.vue";
import HttpUtil from "@/util/HttpUtil.js"; import HttpUtil from "@/util/HttpUtil.js";
import { mapState, mapActions } from "vuex"; import { mapState } from "vuex";
import { downloadFile } from "@/util/FileUtil"; import { downloadFile } from "@/util/FileUtil";
import ClipboardJS from "clipboard"; import ClipboardJS from "clipboard";
import moment from "moment"; import moment from "moment";
import { TREE_DATA, SHOW_REFRESH_TOAST } from "@/store/modules/treeData";
export default { export default {
name: "BookmarkManage", name: "BookmarkManage",
components: { AddBookmark, Search }, components: { AddBookmark, Search },
@ -130,6 +131,7 @@ export default {
...mapState("globalConfig", ["isPhone"]), ...mapState("globalConfig", ["isPhone"]),
}, },
async mounted() { async mounted() {
this.$store.commit(TREE_DATA + "/" + SHOW_REFRESH_TOAST, true);
await this.$store.dispatch("treeData/ensureDataOk"); await this.$store.dispatch("treeData/ensureDataOk");
this.treeData = this.totalTreeData[""]; this.treeData = this.totalTreeData[""];
this.loading = false; this.loading = false;
@ -144,7 +146,8 @@ export default {
e.clearSelection(); e.clearSelection();
}); });
}, },
destroyed() { beforeDestroy() {
this.$store.commit(TREE_DATA + "/" + SHOW_REFRESH_TOAST, false);
if (this.copyBoard != null) { if (this.copyBoard != null) {
this.copyBoard.destroy(); this.copyBoard.destroy();
} }
@ -165,11 +168,21 @@ export default {
resolve(); resolve();
}); });
}, },
/**
* 刷新书签数据
*/
async refresh(deleteCache) { async refresh(deleteCache) {
if (deleteCache) { if (deleteCache) {
this.loading = true; this.loading = true;
await this.$store.dispatch("treeData/refresh"); await this.$store.dispatch("treeData/refresh");
} }
this.resetData();
this.loading = false;
},
/**
* 重置当前data中书签相关数据
*/
resetData() {
this.treeData = this.totalTreeData[""]; this.treeData = this.totalTreeData[""];
this.expandedKeys = []; this.expandedKeys = [];
this.checkedKeys = []; this.checkedKeys = [];
@ -178,6 +191,9 @@ export default {
this.currentSelect = null; this.currentSelect = null;
this.loading = false; this.loading = false;
}, },
/**
* 树节点展开
*/
expand(expandedKeys, { expanded, node }) { expand(expandedKeys, { expanded, node }) {
if (expanded) { if (expanded) {
const item = node.dataRef; const item = node.dataRef;

View File

@ -13,76 +13,9 @@ import Content from "@/layout/manage/Content.vue";
import Bottom from "@/layout/manage/Bottom.vue"; import Bottom from "@/layout/manage/Bottom.vue";
import Top from "@/layout/manage/Top.vue"; import Top from "@/layout/manage/Top.vue";
import httpUtil from "../../util/HttpUtil";
export default { export default {
name: "Home", name: "Home",
components: { Top, Content, Bottom }, components: { Top, Content, Bottom },
data() {
return {
timer: null,
//
count: 0,
//
total: 1,
//
isOpen: false,
};
},
async mounted() {
//
await this.$store.dispatch("globalConfig/init");
console.log("globalConfig加载完毕");
await this.$store.dispatch("treeData/init");
console.log("treeData加载完毕");
console.log("state数据:", this.$store.state);
//
this.timer = setInterval(this.checkVersion, 5 * 60 * 1000);
},
destroyed() {
if (this.timer != null) {
clearInterval(this.timer);
}
},
methods: {
/**
* 检查当前页面版本是否和服务器版本一致
*/
async checkVersion() {
this.count++;
if (this.count < this.total || this.isOpen) {
return;
}
this.count = 0;
let version = await httpUtil.get("/user/version");
const _this = this;
if (this.$store.state.treeData.version < version) {
this.isOpen = true;
this.$confirm({
title: "书签数据有更新,是否立即刷新?",
content: "点击确定将刷新整个页面,请注意!",
cancelText: "稍后提醒",
closable: false,
keyboard: false,
maskClosable: false,
onOk() {
_this.isOpen = false;
return new Promise(async (resolve) => {
await _this.$store.dispatch("treeData/clear");
window.location.reload();
resolve();
});
},
onCancel() {
_this.isOpen = false;
_this.total = 5;
},
afterClose() {
_this.isOpen = false;
},
});
}
},
},
}; };
</script> </script>