Преглед изворни кода

增加全屏loading,以及放开request的timeout时间

刘洋 пре 2 година
родитељ
комит
251dd544c0
8 измењених фајлова са 378 додато и 348 уклоњено
  1. 1 0
      components.d.ts
  2. 9 1
      src/App.vue
  3. 3 0
      src/pages/subjects-manage/index.vue
  4. 100 100
      src/plugins/request.ts
  5. 23 11
      src/store/main.ts
  6. 227 222
      types/project.d.ts
  7. 7 7
      types/store.d.ts
  8. 8 7
      vite.config.ts

+ 1 - 0
components.d.ts

@@ -18,6 +18,7 @@ declare module '@vue/runtime-core' {
     ARadioGroup: typeof import('ant-design-vue/es')['RadioGroup']
     ASelect: typeof import('ant-design-vue/es')['Select']
     ASelectOption: typeof import('ant-design-vue/es')['SelectOption']
+    ASpin: typeof import('ant-design-vue/es')['Spin']
     ATable: typeof import('ant-design-vue/es')['Table']
     ATextarea: typeof import('ant-design-vue/es')['Textarea']
     ATooltip: typeof import('ant-design-vue/es')['Tooltip']

+ 9 - 1
src/App.vue

@@ -1,10 +1,18 @@
 <template>
-  <router-view></router-view>
+  <a-spin
+    style="z-index: 100000"
+    :tip="mainStore.loading.message"
+    :spinning="mainStore.loading.status"
+  >
+    <router-view></router-view>
+  </a-spin>
 </template>
 
 <script setup lang="ts" name="App">
 import { getUserInfoHttp } from "@api/user";
 import { getLoginResult } from "@/utils/auth";
+import { useMainStore } from "@/store/main";
+const mainStore: any = useMainStore();
 if (getLoginResult()) {
   getUserInfoHttp(true);
 }

+ 3 - 0
src/pages/subjects-manage/index.vue

@@ -514,11 +514,14 @@ const onImport = async () => {
       uploadQuery.fileList?.forEach((file: any) => {
         formData.append("file", file);
       });
+      mainStore.switchLoading(true, "上传中...");
       await ImportDownloadApi[uploadQuery.type].upload(formData);
       querySubjectsList();
       showImportModal.value = false;
+      mainStore.switchLoading();
     }
   } catch (error) {
+    mainStore.switchLoading();
     return Promise.reject(error);
   }
 };

+ 100 - 100
src/plugins/request.ts

@@ -1,100 +1,100 @@
-import axios, { AxiosError } from "axios";
-import { message } from "ant-design-vue";
-import { loadProgressBar } from "axios-progress-bar";
-import { signToken } from "@/plugins/signToken";
-import { filterConfigEmpty } from "@/plugins/configFilter";
-import { downloadBlob,exitLogin } from "@/utils/common";
-
-const request = axios.create({
-  baseURL: import.meta.env.VITE_APP_API_HOST,
-  withCredentials: true,
-  timeout: 20000,
-  method: "post",
-  transformRequest: [],
-});
-
-request.interceptors.request.use(
-  (config) => {
-    if (!config.url) {
-      throw new AxiosError(
-        "request must should a url parameter",
-        "REQUEST_PARAMETER_ERROR",
-        config
-      );
-    }
-    config.headers = config.headers || {};
-    if (!config.noAuth) {
-      const { token, timestamp } = signToken(config.url, config.method);
-      config.headers["Authorization"] = token;
-      config.headers["time"] = timestamp;
-    }
-    config.headers["Content-Type"] =
-      config.headers["Content-Type"] || "application/x-www-form-urlencoded";
-    if (!config.headers["Content-Type"]?.toString().includes("multipart")) {
-      config.transformRequest = (d) => new URLSearchParams(d);
-    }
-    if (config.download) {
-      config.responseType = config.responseType || "blob";
-    }
-    filterConfigEmpty(config);
-    return config;
-  },
-  (error: AxiosError) => {
-    if (!error.config.noToast) {
-      message.error(error.message || error.name || error.code);
-    }
-    return Promise.reject(error);
-  }
-);
-
-request.interceptors.response.use(
-  (response) => {
-    if (response.config.download) {
-      downloadBlob(response);
-      return response;
-    }
-    if (response.data.hasError) {
-      const errMsg = response.data?.errMsg?.join("\n");
-      message.error(errMsg);
-      return Promise.reject(response.data);
-    }
-    return response.data;
-  },
-  async (error: AxiosError<any>) => {
-    if (error.isAxiosError && !error.config.noToast) {
-      if (
-        error.response &&
-        ([401, 403].includes(error.response.status) ||
-          error.response.data?.code?.toString()?.startsWith("401"))
-      ) {
-        exitLogin(false)
-        message.error({content:"登录状态已过期",key:'token-valid'});
-        return Promise.reject(error);
-      }
-      let msg = "";
-      if (error.config?.responseType === "blob") {
-        try {
-          const e = JSON.parse(await error?.response?.data?.text());
-          msg = e.message || e.error || e;
-        } catch (error) {
-          console.error(error);
-        }
-      }
-      if (!msg) {
-        msg =
-          error?.response?.data?.message ||
-          error.message ||
-          error.name ||
-          error.code;
-      }
-      message.error(msg);
-    } else if (!error.isAxiosError) {
-      error.message && message.error(error.message);
-    }
-    return Promise.reject(error);
-  }
-);
-
-loadProgressBar(null, request);
-
-export default request;
+import axios, { AxiosError } from "axios";
+import { message } from "ant-design-vue";
+import { loadProgressBar } from "axios-progress-bar";
+import { signToken } from "@/plugins/signToken";
+import { filterConfigEmpty } from "@/plugins/configFilter";
+import { downloadBlob, exitLogin } from "@/utils/common";
+
+const request = axios.create({
+  baseURL: import.meta.env.VITE_APP_API_HOST,
+  withCredentials: true,
+  timeout: 180000,
+  method: "post",
+  transformRequest: [],
+});
+
+request.interceptors.request.use(
+  (config) => {
+    if (!config.url) {
+      throw new AxiosError(
+        "request must should a url parameter",
+        "REQUEST_PARAMETER_ERROR",
+        config
+      );
+    }
+    config.headers = config.headers || {};
+    if (!config.noAuth) {
+      const { token, timestamp } = signToken(config.url, config.method);
+      config.headers["Authorization"] = token;
+      config.headers["time"] = timestamp;
+    }
+    config.headers["Content-Type"] =
+      config.headers["Content-Type"] || "application/x-www-form-urlencoded";
+    if (!config.headers["Content-Type"]?.toString().includes("multipart")) {
+      config.transformRequest = (d) => new URLSearchParams(d);
+    }
+    if (config.download) {
+      config.responseType = config.responseType || "blob";
+    }
+    filterConfigEmpty(config);
+    return config;
+  },
+  (error: AxiosError) => {
+    if (!error.config.noToast) {
+      message.error(error.message || error.name || error.code);
+    }
+    return Promise.reject(error);
+  }
+);
+
+request.interceptors.response.use(
+  (response) => {
+    if (response.config.download) {
+      downloadBlob(response);
+      return response;
+    }
+    if (response.data.hasError) {
+      const errMsg = response.data?.errMsg?.join("\n");
+      message.error(errMsg);
+      return Promise.reject(response.data);
+    }
+    return response.data;
+  },
+  async (error: AxiosError<any>) => {
+    if (error.isAxiosError && !error.config.noToast) {
+      if (
+        error.response &&
+        ([401, 403].includes(error.response.status) ||
+          error.response.data?.code?.toString()?.startsWith("401"))
+      ) {
+        exitLogin(false);
+        message.error({ content: "登录状态已过期", key: "token-valid" });
+        return Promise.reject(error);
+      }
+      let msg = "";
+      if (error.config?.responseType === "blob") {
+        try {
+          const e = JSON.parse(await error?.response?.data?.text());
+          msg = e.message || e.error || e;
+        } catch (error) {
+          console.error(error);
+        }
+      }
+      if (!msg) {
+        msg =
+          error?.response?.data?.message ||
+          error.message ||
+          error.name ||
+          error.code;
+      }
+      message.error(msg);
+    } else if (!error.isAxiosError) {
+      error.message && message.error(error.message);
+    }
+    return Promise.reject(error);
+  }
+);
+
+loadProgressBar(null, request);
+
+export default request;

+ 23 - 11
src/store/main.ts

@@ -1,11 +1,23 @@
-import { defineStore } from "pinia";
-
-export const useMainStore = defineStore<"main", Store.MainStoreState>("main", {
-  state() {
-    return {
-      loginResult: null,
-      systemUserInfo: null,
-    };
-  },
-});
-
+import { defineStore } from "pinia";
+
+export const useMainStore: any = defineStore<"main", Store.MainStoreState>(
+  "main",
+  {
+    state() {
+      return {
+        loginResult: null,
+        systemUserInfo: null,
+        loading: {
+          status: false,
+          message: "加载中...",
+        },
+      };
+    },
+    actions: {
+      switchLoading(bool?: boolean, message?: any) {
+        this.loading.status = bool || false;
+        this.loading.message = message || "加载中...";
+      },
+    },
+  }
+);

+ 227 - 222
types/project.d.ts

@@ -1,222 +1,227 @@
-declare module "axios-progress-bar";
-
-interface MenuItem {
-  path?: string;
-  label: string;
-  iconName?: string;
-  children?: MenuItem[];
-}
-
-/** 分页数据 */
-type MultiplePageData<T> = {
-  pageCount?: number;
-  pageNumber?: number;
-  pageSize?: number;
-  totalCount: number;
-  result: T[];
-};
-
-interface LoginModel {
-  loginName: string;
-  password: string;
-}
-
-/** 登录结果 */
-type LoginResult = {
-  accessToken: string;
-  name: string;
-  role: string;
-  schoolId: number;
-  schoolName: string;
-  sessionId: string;
-};
-
-/** 用户信息 */
-type SystemUserInfo = {
-  /** 科目代码集合 */
-  courseCodes: string[];
-  /** 科目名称 */
-  courseNames: string[];
-  createTime: string;
-  /** 启用/禁用 */
-  enable: boolean;
-  /** 用户ID */
-  id: number;
-  /** 登录名 */
-  loginName: string;
-  /** 姓名 */
-  name: string;
-  /** 角色 code */
-  role: string
-  /** 角色ID */
-  roleId: number;
-  /** 角色名称 */
-  roleName: string
-  /** 学校ID */
-  schoolId: number;
-  /** 学校名称 */
-  schoolName: string;
-  updateTime: string;
-};
-
-interface BaseMutPageQuery {
-  pageNumber: number;
-  pageSize: number;
-}
-
-/** 查询学校列表参数 */
-interface FetchSchoolListQuery extends BaseMutPageQuery {
-  /** 学校名称 */
-  name?: string;
-}
-
-interface BaseSchoolInfo {
-  /** 学校编码 */
-  code?: string;
-  /** 负责人 */
-  contacts: string;
-  id?: number;
-  /** 学校名称 */
-  name: string;
-  /** 区域 */
-  region: string;
-  /** 联系方式 */
-  telephone: string;
-  /** 启用/禁用 */
-  enable: boolean;
-}
-
-/** 学校列表信息 */
-interface SchoolListInfo extends Required<BaseSchoolInfo> {
-  createTime: string;
-  creatorId: number;
-  /** 二维码 */
-  qrCode: string;
-  updateTime: string;
-  updaterId: number;
-}
-
-/** 查询用户列表参数 */
-interface FetchUserListQuery extends BaseMutPageQuery {
-  /** 用户名称 */
-  loginName?: string;
-  /** 用户角色 */
-  role?: "SUPER_ADMIN" | "SCHOOL_ADMIN" | "SECTION_LEADER";
-  /** 学校ID */
-  schoolId?: string | number;
-}
-
-interface BaseUserInfo {
-  /** 学校ID */
-  schoolId: string;
-  /** 启用/禁用 */
-  enable?: boolean;
-  /** 用户ID */
-  id?: number;
-  /** 登录名 */
-  loginName: string;
-  /** 姓名 */
-  name: string;
-  /** 角色ID */
-  roleId: string;
-}
-
-/** 用户信息 */
-interface UserInfo extends Required<BaseUserInfo> {
-  /** 科目代码集合 */
-  courseCodes: string[];
-  /** 科目名称 */
-  courseNames: string[];
-  createTime: string;
-  /** 学校名称 */
-  schoolName: string;
-  updateTime: string;
-  /** 角色CODE */
-  role: string,
-  /** 角色名称 */
-  roleName: string
-}
-
-type EditUserInfo = Omit<BaseUserInfo, "roleId"> & {
-  /** 用户角色 */
-  role?: "SUPER_ADMIN" | "SCHOOL_ADMIN" | "SECTION_LEADER";
-  /** 用户密码 */
-  passwd?: string;
-  /** 科目代码集合 */
-  course: string;
-};
-
-interface FetchExamListQuery extends BaseMutPageQuery {
-  /** 考试名称 */
-  name?: string;
-  /** 学校ID */
-  schoolId?: number | string;
-}
-
-interface BaseExamInfo {
-  /** 考试状态,可用值:EDIT,FINISH,CLOSE */
-  examStatus?: string;
-  /** 考试ID */
-  id?: number;
-  /** 考试名称 */
-  name?: string;
-  /** 学校ID */
-  schoolId?: string;
-}
-
-/** 考试列表信息 */
-
-interface ExamListInfo extends Required<BaseExamInfo> {
-  /** 考试编码 */
-  code: string;
-  createTime: string;
-  /** 科目数量 */
-  paperCount: number;
-  updateTime: string;
-}
-
-/** 科目查询参数 */
-interface FetchSubjectsListQuery extends BaseMutPageQuery {
-  /** 科目代码 */
-  courseCode: string;
-  courseName: string;
-  /** 考试id */
-  examId: string;
-  /** 	分组状态 */
-  groupFinish?: boolean;
-  /** 学校id */
-  schoolId: number | string;
-  /** 总分截止值 */
-  totalScoreMax: string;
-  /** 总分起始值 */
-  totalScoreMin: string;
-}
-
-/** 科目列表信息 */
-interface SubjectsListInfo {
-  /** 科目代码 */
-  courseCode: string;
-  /** 科目ID */
-  courseId: number;
-  /** 科目名称 */
-  courseName: string;
-  createTime: string;
-  /** 考试ID */
-  examId: number;
-  /** 考试名称 */
-  examName: string;
-  /** 分组数量 */
-  groupCount: number;
-  /** 分组是否完成 */
-  groupFinish: boolean;
-  id: number;
-  /** 学校ID */
-  schoolId: number;
-  /** 试卷结构是否提交 */
-  structFinish: boolean;
-  /** 主观题总分 */
-  subjectiveScore: number;
-  /** 试卷总分 */
-  totalScore: number;
-  updateTime: string;
-}
+declare module "axios-progress-bar";
+
+interface ScreenLoading {
+  status: boolean;
+  message: string;
+}
+
+interface MenuItem {
+  path?: string;
+  label: string;
+  iconName?: string;
+  children?: MenuItem[];
+}
+
+/** 分页数据 */
+type MultiplePageData<T> = {
+  pageCount?: number;
+  pageNumber?: number;
+  pageSize?: number;
+  totalCount: number;
+  result: T[];
+};
+
+interface LoginModel {
+  loginName: string;
+  password: string;
+}
+
+/** 登录结果 */
+type LoginResult = {
+  accessToken: string;
+  name: string;
+  role: string;
+  schoolId: number;
+  schoolName: string;
+  sessionId: string;
+};
+
+/** 用户信息 */
+type SystemUserInfo = {
+  /** 科目代码集合 */
+  courseCodes: string[];
+  /** 科目名称 */
+  courseNames: string[];
+  createTime: string;
+  /** 启用/禁用 */
+  enable: boolean;
+  /** 用户ID */
+  id: number;
+  /** 登录名 */
+  loginName: string;
+  /** 姓名 */
+  name: string;
+  /** 角色 code */
+  role: string;
+  /** 角色ID */
+  roleId: number;
+  /** 角色名称 */
+  roleName: string;
+  /** 学校ID */
+  schoolId: number;
+  /** 学校名称 */
+  schoolName: string;
+  updateTime: string;
+};
+
+interface BaseMutPageQuery {
+  pageNumber: number;
+  pageSize: number;
+}
+
+/** 查询学校列表参数 */
+interface FetchSchoolListQuery extends BaseMutPageQuery {
+  /** 学校名称 */
+  name?: string;
+}
+
+interface BaseSchoolInfo {
+  /** 学校编码 */
+  code?: string;
+  /** 负责人 */
+  contacts: string;
+  id?: number;
+  /** 学校名称 */
+  name: string;
+  /** 区域 */
+  region: string;
+  /** 联系方式 */
+  telephone: string;
+  /** 启用/禁用 */
+  enable: boolean;
+}
+
+/** 学校列表信息 */
+interface SchoolListInfo extends Required<BaseSchoolInfo> {
+  createTime: string;
+  creatorId: number;
+  /** 二维码 */
+  qrCode: string;
+  updateTime: string;
+  updaterId: number;
+}
+
+/** 查询用户列表参数 */
+interface FetchUserListQuery extends BaseMutPageQuery {
+  /** 用户名称 */
+  loginName?: string;
+  /** 用户角色 */
+  role?: "SUPER_ADMIN" | "SCHOOL_ADMIN" | "SECTION_LEADER";
+  /** 学校ID */
+  schoolId?: string | number;
+}
+
+interface BaseUserInfo {
+  /** 学校ID */
+  schoolId: string;
+  /** 启用/禁用 */
+  enable?: boolean;
+  /** 用户ID */
+  id?: number;
+  /** 登录名 */
+  loginName: string;
+  /** 姓名 */
+  name: string;
+  /** 角色ID */
+  roleId: string;
+}
+
+/** 用户信息 */
+interface UserInfo extends Required<BaseUserInfo> {
+  /** 科目代码集合 */
+  courseCodes: string[];
+  /** 科目名称 */
+  courseNames: string[];
+  createTime: string;
+  /** 学校名称 */
+  schoolName: string;
+  updateTime: string;
+  /** 角色CODE */
+  role: string;
+  /** 角色名称 */
+  roleName: string;
+}
+
+type EditUserInfo = Omit<BaseUserInfo, "roleId"> & {
+  /** 用户角色 */
+  role?: "SUPER_ADMIN" | "SCHOOL_ADMIN" | "SECTION_LEADER";
+  /** 用户密码 */
+  passwd?: string;
+  /** 科目代码集合 */
+  course: string;
+};
+
+interface FetchExamListQuery extends BaseMutPageQuery {
+  /** 考试名称 */
+  name?: string;
+  /** 学校ID */
+  schoolId?: number | string;
+}
+
+interface BaseExamInfo {
+  /** 考试状态,可用值:EDIT,FINISH,CLOSE */
+  examStatus?: string;
+  /** 考试ID */
+  id?: number;
+  /** 考试名称 */
+  name?: string;
+  /** 学校ID */
+  schoolId?: string;
+}
+
+/** 考试列表信息 */
+
+interface ExamListInfo extends Required<BaseExamInfo> {
+  /** 考试编码 */
+  code: string;
+  createTime: string;
+  /** 科目数量 */
+  paperCount: number;
+  updateTime: string;
+}
+
+/** 科目查询参数 */
+interface FetchSubjectsListQuery extends BaseMutPageQuery {
+  /** 科目代码 */
+  courseCode: string;
+  courseName: string;
+  /** 考试id */
+  examId: string;
+  /** 	分组状态 */
+  groupFinish?: boolean;
+  /** 学校id */
+  schoolId: number | string;
+  /** 总分截止值 */
+  totalScoreMax: string;
+  /** 总分起始值 */
+  totalScoreMin: string;
+}
+
+/** 科目列表信息 */
+interface SubjectsListInfo {
+  /** 科目代码 */
+  courseCode: string;
+  /** 科目ID */
+  courseId: number;
+  /** 科目名称 */
+  courseName: string;
+  createTime: string;
+  /** 考试ID */
+  examId: number;
+  /** 考试名称 */
+  examName: string;
+  /** 分组数量 */
+  groupCount: number;
+  /** 分组是否完成 */
+  groupFinish: boolean;
+  id: number;
+  /** 学校ID */
+  schoolId: number;
+  /** 试卷结构是否提交 */
+  structFinish: boolean;
+  /** 主观题总分 */
+  subjectiveScore: number;
+  /** 试卷总分 */
+  totalScore: number;
+  updateTime: string;
+}

+ 7 - 7
types/store.d.ts

@@ -1,7 +1,7 @@
-
-namespace Store {
-  interface MainStoreState {
-    systemUserInfo: SystemUserInfo | null;
-    loginResult: LoginResult | null;
-  }
-}
+namespace Store {
+  interface MainStoreState {
+    systemUserInfo: SystemUserInfo | null;
+    loginResult: LoginResult | null;
+    loading: ScreenLoading;
+  }
+}

+ 8 - 7
vite.config.ts

@@ -4,7 +4,7 @@ import vue from "@vitejs/plugin-vue";
 import vueJsx from "@vitejs/plugin-vue-jsx";
 import Components from "unplugin-vue-components/vite";
 import { AntDesignVueResolver } from "unplugin-vue-components/resolvers";
-import vueSetupExtend from 'unplugin-vue-setup-extend-plus/vite'
+import vueSetupExtend from "unplugin-vue-setup-extend-plus/vite";
 import { createSvgIconsPlugin } from "vite-plugin-svg-icons";
 
 const resolvePath = (...args: any[]) => {
@@ -22,7 +22,7 @@ export default defineConfig({
       symbolId: "icon-[dir]-[name]",
       customDomId: "__svg__icons__dom__",
     }),
-    vueSetupExtend()
+    vueSetupExtend(),
   ],
   resolve: {
     extensions: [".vue", ".js", ".ts", ".jsx", ".tsx", ".json"],
@@ -54,9 +54,10 @@ export default defineConfig({
   },
   server: {
     proxy: {
-      '^/api': {
-        target: 'http://192.168.10.39:7100'
-      }
-    }
-  }
+      "^/api": {
+        // target: 'http://192.168.10.39:7100'
+        target: "http://test.markingtool.cn",
+      },
+    },
+  },
 });