zhangjie 2 سال پیش
والد
کامیت
d04380afc5

+ 130 - 0
src/components/UploadFetchFile.vue

@@ -0,0 +1,130 @@
+<template>
+  <div class="upload-file-view">
+    <el-input
+      :style="{ width: inputWidth }"
+      v-model.trim="attachmentName"
+      placeholder="文件名称"
+      readonly
+    ></el-input>
+    <el-upload
+      action="upload-url"
+      :on-change="handleFileChange"
+      :show-file-list="false"
+      :auto-upload="false"
+      :disabled="disabled"
+      style="display:inline-block;margin: 0 10px;"
+      ref="UploadComp"
+    >
+      <el-button type="primary" :disabled="disabled" :loading="loading"
+        >选择</el-button
+      >
+    </el-upload>
+  </div>
+</template>
+
+<script>
+import { fileMD5 } from "@/plugins/md5";
+
+export default {
+  name: "upload-file-view",
+  props: {
+    inputWidth: {
+      type: String,
+      default: "200px"
+    },
+    format: {
+      type: Array,
+      default() {
+        return ["xls", "xlsx"];
+      }
+    },
+    maxSize: {
+      type: Number,
+      default: 20 * 1024 * 1024
+    },
+    disabled: {
+      type: Boolean,
+      default: false
+    }
+  },
+  data() {
+    return {
+      attachmentName: "",
+      canUpload: false,
+      loading: false,
+      res: {}
+    };
+  },
+  methods: {
+    checkFileFormat(fileType) {
+      const _file_format = fileType
+        .split(".")
+        .pop()
+        .toLocaleLowerCase();
+      return this.format.some(
+        item => item.toLocaleLowerCase() === _file_format
+      );
+    },
+    async handleFileChange(file) {
+      console.log(file);
+      this.attachmentName = file.name;
+      this.canUpload = file.status === "ready";
+
+      if (file.size > this.maxSize) {
+        this.handleExceededSize();
+        return Promise.reject();
+      }
+
+      if (!this.checkFileFormat(file.name)) {
+        this.handleFormatError();
+        return Promise.reject();
+      }
+      this.$emit("valid-change", { success: true });
+
+      const md5 = await fileMD5(file.raw);
+
+      this.$emit("file-change", {
+        md5,
+        filename: file.name,
+        file: file.raw
+      });
+    },
+    // upload(options) {
+    //   let formData = new FormData();
+    //   Object.entries(options.data).forEach(([k, v]) => {
+    //     formData.append(k, v);
+    //   });
+    //   formData.append("file", options.file);
+    //   this.$emit("uploading");
+
+    //   return $post(options.action, formData, { headers: options.headers });
+    // },
+    handleFormatError() {
+      const content = "只支持文件格式为" + this.format.join("/");
+      this.res = {
+        success: false,
+        message: content
+      };
+      this.$emit("valid-change", this.res);
+    },
+    handleExceededSize() {
+      const content =
+        "文件大小不能超过" + Math.floor(this.maxSize / 1024) + "M";
+      this.res = {
+        success: false,
+        message: content
+      };
+      this.$emit("valid-change", this.res);
+    },
+    setAttachmentName(name) {
+      this.attachmentName = name;
+    }
+  }
+};
+</script>
+
+<style scoped>
+.upload-file-view {
+  display: inline-block;
+}
+</style>

+ 9 - 3
src/constants/adminNavs.js

@@ -8,23 +8,29 @@ const navs = [
   {
     id: "2",
     parentId: "1",
+    name: "学校管理",
+    url: "SchoolManage"
+  },
+  {
+    id: "3",
+    parentId: "1",
     name: "用户管理",
     url: "AdminUserManage"
   },
   {
-    id: "3",
+    id: "4",
     parentId: "1",
     name: "系统角色管理",
     url: "SystemRoleManage"
   },
   {
-    id: "4",
+    id: "5",
     parentId: "1",
     name: "权限管理",
     url: "PrivilegeManage"
   },
   {
-    id: "5",
+    id: "6",
     parentId: "1",
     name: "授权配置",
     url: "AuthSet"

+ 11 - 0
src/constants/enumerate.js

@@ -13,6 +13,17 @@ export const BOOLEAN_TYPE = {
   1: "是"
 };
 
+export const OPEN_STATUS = [
+  {
+    label: "开启",
+    value: true
+  },
+  {
+    label: "关闭",
+    value: false
+  }
+];
+
 export const CURRENT_TYPE = {
   0: "非应届",
   1: "应届"

+ 24 - 0
src/modules/admin/api.js

@@ -44,3 +44,27 @@ export const exportDeviceInfo = () => {
     }
   );
 };
+
+// school-manage
+export const schoolList = () => {
+  return $postParam("/api/admin/common/school/list", {});
+};
+export const schoolSync = () => {
+  return $postParam("/api/admin/common/school/sync", {});
+};
+export const updateSchool = datas => {
+  let formData = new FormData();
+  Object.keys(datas).forEach(k => {
+    formData.append(k, datas[k]);
+  });
+  return $post("/api/admin/common/school/update", formData);
+};
+
+export const schoolSetSyncInfo = schoolId => {
+  return $postParam("/api/report/set/sync/select", {
+    schoolId
+  });
+};
+export const schoolSetSyncUpdate = datas => {
+  return $post("/api/report/set/sync/save", datas);
+};

+ 188 - 0
src/modules/admin/components/ModifySchool.vue

@@ -0,0 +1,188 @@
+<template>
+  <el-dialog
+    class="modify-school"
+    :visible.sync="modalIsShow"
+    :title="title"
+    top="10vh"
+    width="600px"
+    :close-on-click-modal="false"
+    :close-on-press-escape="false"
+    append-to-body
+    @opened="visibleChange"
+  >
+    <el-form
+      ref="modalFormComp"
+      :model="modalForm"
+      :rules="rules"
+      :key="modalForm.id"
+      label-width="100px"
+    >
+      <el-form-item prop="code" label="学校代码:">
+        {{ modalForm.code }}
+      </el-form-item>
+      <el-form-item prop="name" label="学校名称:">
+        <el-input
+          v-model.trim="modalForm.name"
+          placeholder="请输入名称"
+          clearable
+        ></el-input>
+      </el-form-item>
+      <!-- <el-form-item prop="code" label="学校域名">
+        <el-input
+          v-model.trim="modalForm.code"
+          placeholder="请输入编码"
+          clearable
+        ></el-input>
+      </el-form-item> -->
+      <el-form-item prop="logo" label="学校logo:">
+        <UploadFetchFile
+          ref="UploadFetchFile"
+          input-width="340px"
+          :disabled="isSubmit"
+          :format="['png', 'jpg']"
+          @file-change="logoChange"
+          @valid-change="validChange"
+        />
+        <div class="mt-1">
+          <p class="tips-info">logo会展示在登录页及内页;</p>
+          <p class="tips-info">
+            文件必须是 jpg 或 png 格式的图片,不超过 2M 尺寸:160*40px。
+          </p>
+        </div>
+        <div class="logo-image" v-if="imgSrc">
+          <img class="logo-view" :src="imgSrc" alt="logo" />
+        </div>
+      </el-form-item>
+    </el-form>
+    <div slot="footer">
+      <el-button type="danger" @click="cancel" plain>取消</el-button>
+      <el-button type="primary" :disabled="isSubmit" @click="submit"
+        >确认</el-button
+      >
+    </div>
+  </el-dialog>
+</template>
+
+<script>
+import { updateSchool } from "../api";
+import UploadFetchFile from "../../../components/UploadFetchFile.vue";
+
+const initModalForm = {
+  id: "",
+  name: "",
+  code: "",
+  logo: "",
+  logoMd5: ""
+};
+
+export default {
+  name: "modify-school",
+  components: { UploadFetchFile },
+  props: {
+    instance: {
+      type: Object,
+      default() {
+        return {};
+      }
+    }
+  },
+  computed: {
+    isEdit() {
+      return !!this.instance.id;
+    },
+    title() {
+      return (this.isEdit ? "编辑" : "新增") + "学校";
+    }
+  },
+  data() {
+    return {
+      modalIsShow: false,
+      isSubmit: false,
+      modalForm: { ...initModalForm },
+      imgSrc: "",
+      logoValidInfo: {},
+      rules: {
+        name: [
+          {
+            required: true,
+            message: "请输入学校名称",
+            trigger: "change"
+          }
+        ],
+        code: [
+          {
+            required: true,
+            message: "请输入学校代码",
+            trigger: "change"
+          }
+        ],
+        logo: [
+          {
+            validator: (rule, value, callback) => {
+              if (!this.logoValidInfo.success && this.logoValidInfo.message) {
+                return callback(new Error(this.logoValidInfo.message));
+              }
+
+              callback();
+            }
+          }
+        ]
+      }
+    };
+  },
+  methods: {
+    initData(val) {
+      if (val.id) {
+        this.modalForm = this.$objAssign(initModalForm, val);
+        this.imgSrc = val.logo || "";
+        this.modalForm.logo = "";
+        this.modalForm.logoMd5 = "";
+      } else {
+        this.imgSrc = "";
+        this.modalForm = { ...initModalForm };
+      }
+      this.$refs.modalFormComp.clearValidate();
+      this.$nextTick(() => {
+        this.$refs.UploadFetchFile.setAttachmentName("");
+      });
+    },
+    visibleChange() {
+      this.initData(this.instance);
+    },
+    cancel() {
+      this.modalIsShow = false;
+    },
+    open() {
+      this.modalIsShow = true;
+    },
+    logoChange({ file, md5 }) {
+      let uRl = window.URL || window.webkitURL;
+      this.imgSrc = uRl.createObjectURL(file);
+      this.modalForm.logo = file;
+      this.modalForm.logoMd5 = md5;
+    },
+    validChange(res) {
+      this.logoValidInfo = res;
+      this.$refs.modalFormComp.validateField("logo", () => {});
+    },
+    async submit() {
+      const valid = await this.$refs.modalFormComp.validate();
+      if (!valid) return;
+
+      if (this.isSubmit) return;
+      this.isSubmit = true;
+      let datas = { ...this.modalForm };
+      const data = await updateSchool(datas).catch(() => {
+        this.isSubmit = false;
+      });
+
+      if (!data) return;
+
+      this.isSubmit = false;
+      this.$message.success(this.title + "成功!");
+      this.$emit("modified");
+      this.cancel();
+    }
+  }
+};
+</script>

+ 110 - 0
src/modules/admin/components/ModifySchoolSet.vue

@@ -0,0 +1,110 @@
+<template>
+  <el-dialog
+    class="modify-school-set page-dialog"
+    :visible.sync="modalIsShow"
+    :title="title"
+    :close-on-click-modal="false"
+    :close-on-press-escape="false"
+    append-to-body
+    fullscreen
+    @opened="visibleChange"
+  >
+    <div class="mb-4 tab-btns">
+      <el-button
+        v-for="tab in tabs"
+        :key="tab.val"
+        size="medium"
+        :type="curTab == tab.val ? 'primary' : 'default'"
+        @click="selectMenu(tab.val)"
+        >{{ tab.name }}
+      </el-button>
+    </div>
+
+    <div v-if="modalIsShow" class="part-box part-box-pad">
+      <component :is="compName" :school="school"></component>
+    </div>
+
+    <div slot="footer"></div>
+  </el-dialog>
+</template>
+
+<script>
+// import SchoolSetCheck from "./school/SchoolSetCheck.vue";
+// import SchoolSetData from "./school/SchoolSetData.vue";
+// import SchoolSetMenu from "./school/SchoolSetMenu.vue";
+// import SchoolSetPaper from "./school/SchoolSetPaper.vue";
+// import SchoolSetRole from "./school/SchoolSetRole.vue";
+import SchoolSetSync from "./school/SchoolSetSync.vue";
+
+export default {
+  name: "modify-school-set",
+  components: {
+    // SchoolSetCheck,
+    // SchoolSetData,
+    // SchoolSetMenu,
+    // SchoolSetPaper,
+    // SchoolSetRole,
+    SchoolSetSync
+  },
+  props: {
+    school: {
+      type: Object,
+      default() {
+        return {};
+      }
+    }
+  },
+  data() {
+    return {
+      modalIsShow: false,
+      curTab: "sync",
+      tabs: [
+        // {
+        //   name: "用户验证配置",
+        //   val: "check"
+        // },
+        // {
+        //   name: "菜单管理",
+        //   val: "menu"
+        // },
+        // {
+        //   name: "角色管理",
+        //   val: "role"
+        // },
+        // {
+        //   name: "试卷规格配置",
+        //   val: "paper"
+        // },
+        {
+          name: "同步配置",
+          val: "sync"
+        }
+        // {
+        //   name: "数据还原",
+        //   val: "data"
+        // }
+      ]
+    };
+  },
+  computed: {
+    compName() {
+      return `school-set-${this.curTab}`;
+    },
+    title() {
+      return `学校设置--${this.school.name}`;
+    }
+  },
+  methods: {
+    visibleChange() {},
+    cancel() {
+      this.modalIsShow = false;
+    },
+    open() {
+      this.modalIsShow = true;
+    },
+    selectMenu(tab) {
+      this.curTab = tab;
+    }
+  }
+};
+</script>

+ 83 - 0
src/modules/admin/components/school/SchoolSetCheck.vue

@@ -0,0 +1,83 @@
+<template>
+  <div class="school-set-check">
+    <el-form ref="modalFormComp" label-width="240px">
+      <el-form-item
+        v-for="field in fields"
+        :key="field.code"
+        :prop="field.code"
+        :label="field.name + ':'"
+      >
+        <el-radio-group v-if="field.isBoolean" v-model="field.value">
+          <el-radio
+            v-for="item in OPEN_STATUS"
+            :key="item.value"
+            :label="item.value"
+            >{{ item.label }}</el-radio
+          >
+        </el-radio-group>
+        <el-input
+          v-else
+          v-model="field.value"
+          :placeholder="`请输入${field.name}`"
+          clearable
+        >
+        </el-input>
+      </el-form-item>
+      <el-form-item>
+        <el-button type="primary" :loading="loading" @click="confirm"
+          >保存</el-button
+        >
+      </el-form-item>
+    </el-form>
+  </div>
+</template>
+
+<script>
+import { OPEN_STATUS } from "../../../../constants/enumerate";
+import { schoolSetCheckInfo, schoolSetCheckUpdate } from "../../api";
+
+export default {
+  name: "school-set-check",
+  props: {
+    school: {
+      type: Object,
+      default() {
+        return {};
+      }
+    }
+  },
+  data() {
+    return {
+      loading: false,
+      fields: [],
+      OPEN_STATUS
+    };
+  },
+  mounted() {
+    this.initData();
+  },
+  methods: {
+    async initData() {
+      const data = await schoolSetCheckInfo(this.school.id);
+      this.fields = data.result || [];
+      this.fields.forEach(field => {
+        field.isBoolean =
+          typeof field.value === "boolean" ||
+          ["true", "false"].includes(field.value);
+        if (field.isBoolean && ["true", "false"].includes(field.value))
+          field.value = field.value === "true";
+      });
+    },
+    async confirm() {
+      if (this.loading) return;
+      this.loading = true;
+      const datas = { param: this.fields, schoolId: this.school.id };
+      const res = await schoolSetCheckUpdate(datas).catch(() => {});
+      this.loading = false;
+      if (!res) return;
+
+      this.$message.success("修改成功!");
+    }
+  }
+};
+</script>

+ 62 - 0
src/modules/admin/components/school/SchoolSetData.vue

@@ -0,0 +1,62 @@
+<template>
+  <div class="school-set-data">
+    <el-button type="primary" :loading="loading" @click="confirm"
+      >清除基础数据</el-button
+    >
+    <p class="tips-info tips-error">
+      注意:执行该操作,会将该单位下配置的基础数据全部清除,进入初始状态,请谨慎操作,该操作不可恢复!
+    </p>
+  </div>
+</template>
+
+<script>
+import { schoolSetDataBackup } from "../../api";
+
+export default {
+  name: "school-set-data",
+  props: {
+    school: {
+      type: Object,
+      default() {
+        return {};
+      }
+    }
+  },
+  data() {
+    return {
+      loading: false
+    };
+  },
+  methods: {
+    async confirm() {
+      let confirm = await this.$confirm(
+        `确定要清除当前学校的基础数据集吗?`,
+        "提示",
+        {
+          type: "warning"
+        }
+      ).catch(() => {});
+      if (confirm !== "confirm") return;
+
+      confirm = await this.$confirm(
+        `确定要清除当前学校的基础数据集吗?`,
+        "提示",
+        {
+          type: "warning"
+        }
+      ).catch(() => {});
+      if (confirm !== "confirm") return;
+
+      if (this.loading) return;
+      this.loading = true;
+
+      const res = await schoolSetDataBackup(this.school.id).catch(() => {});
+      this.loading = false;
+
+      if (!res) return;
+
+      this.$message.success("操作成功!");
+    }
+  }
+};
+</script>

+ 92 - 0
src/modules/admin/components/school/SchoolSetMenu.vue

@@ -0,0 +1,92 @@
+<template>
+  <div class="school-set-menu">
+    <privilege-set
+      v-if="menus && menus.length"
+      ref="PrivilegeSet"
+      :menus="menus"
+    ></privilege-set>
+
+    <el-button type="primary" :loading="loading" @click="confirm"
+      >保存</el-button
+    >
+  </div>
+</template>
+
+<script>
+import {
+  sysCustomMenuList,
+  schoolSetMenuInfo,
+  schoolSetMenuUpdate
+} from "../../api";
+import PrivilegeSet from "../../../base/components/PrivilegeSet";
+
+export default {
+  name: "school-set-menu",
+  components: { PrivilegeSet },
+  props: {
+    school: {
+      type: Object,
+      default() {
+        return {};
+      }
+    }
+  },
+  data() {
+    return {
+      menus: [],
+      privilegeIds: [],
+      dataPermissionInfo: [],
+      loading: false
+    };
+  },
+  mounted() {
+    this.initData();
+  },
+  methods: {
+    async initData() {
+      await this.getPrivileges();
+      await this.getSchoolMenuInfo();
+      this.$nextTick(() => {
+        this.$refs.PrivilegeSet.buildTableData(
+          this.privilegeIds,
+          this.dataPermissionInfo
+        );
+      });
+    },
+    async getPrivileges() {
+      const needHideModules = ["common", "customer"];
+      const data = await sysCustomMenuList();
+      const menus = data.customPrivilegeList || [];
+
+      this.menus = menus
+        .filter(item => !needHideModules.includes(item.url))
+        .map(item => {
+          item.parentId = null;
+          return item;
+        });
+    },
+    async getSchoolMenuInfo() {
+      const data = await schoolSetMenuInfo(this.school.id);
+      this.privilegeIds = data.privilegeIdList || [];
+      this.dataPermissionInfo = data.dataPermissionInfo || [];
+    },
+    async confirm() {
+      if (this.loading) return;
+      this.loading = true;
+      const {
+        privilegeIds,
+        dataPermissionInfo
+      } = this.$refs.PrivilegeSet.getSelectedPrivileges();
+      const res = await schoolSetMenuUpdate({
+        schoolId: this.school.id,
+        privilegeIds,
+        dataPermissionInfo
+      }).catch(() => {});
+      this.loading = false;
+      if (!res) return;
+
+      this.$message.success("修改成功!");
+    }
+  }
+};
+</script>

+ 96 - 0
src/modules/admin/components/school/SchoolSetPaper.vue

@@ -0,0 +1,96 @@
+<template>
+  <div class="school-set-paper">
+    <el-form
+      ref="modalFormComp"
+      :model="modalForm"
+      :rules="rules"
+      label-width="180px"
+    >
+      <el-form-item prop="pdfSize" label="允许上传试卷规格:">
+        <el-checkbox-group v-model="modalForm.pdfSize">
+          <el-checkbox v-for="item in sysPdfSize" :key="item" :label="item">{{
+            item
+          }}</el-checkbox>
+        </el-checkbox-group>
+      </el-form-item>
+      <el-form-item>
+        <el-button type="primary" :loading="loading" @click="confirm"
+          >保存</el-button
+        >
+      </el-form-item>
+    </el-form>
+  </div>
+</template>
+
+<script>
+import {
+  sysPaperSizeList,
+  schoolSetPaperInfo,
+  schoolSetPaperUpdate
+} from "../../api";
+
+export default {
+  name: "school-set-paper",
+  props: {
+    school: {
+      type: Object,
+      default() {
+        return {};
+      }
+    }
+  },
+  data() {
+    return {
+      loading: false,
+      modalForm: {
+        pdfSize: []
+      },
+      sysPdfSize: [],
+      paperInfo: [],
+      rules: {
+        pdfSize: [
+          {
+            required: true,
+            validator: (rule, value, callback) => {
+              if (!value || !value.length) {
+                return callback(new Error(`请选择允许上传试卷规格`));
+              }
+
+              callback();
+            },
+            trigger: "change"
+          }
+        ]
+      }
+    };
+  },
+  mounted() {
+    this.initData();
+  },
+  methods: {
+    async initData() {
+      const paperData = await sysPaperSizeList();
+      this.sysPdfSize = paperData.result[0].value;
+      const data = await schoolSetPaperInfo(this.school.id);
+      this.paperInfo = data.result;
+      this.modalForm.pdfSize = data.result[0].value;
+    },
+    async confirm() {
+      const valid = await this.$refs.modalFormComp.validate();
+      if (!valid) return;
+
+      if (this.loading) return;
+      this.loading = true;
+
+      this.paperInfo[0].value = this.modalForm.pdfSize;
+      let datas = { param: this.paperInfo, schoolId: this.school.id };
+      const res = await schoolSetPaperUpdate(datas).catch(() => {});
+      this.loading = false;
+
+      if (!res) return;
+
+      this.$message.success("修改成功!");
+    }
+  }
+};
+</script>

+ 99 - 0
src/modules/admin/components/school/SchoolSetRole.vue

@@ -0,0 +1,99 @@
+<template>
+  <div class="school-set-role">
+    <el-form
+      ref="modalFormComp"
+      :model="modalForm"
+      :rules="rules"
+      label-width="140px"
+    >
+      <el-form-item prop="roleIds" label="系统角色管理:">
+        <el-checkbox-group v-model="modalForm.roleIds">
+          <el-checkbox
+            v-for="item in roleList"
+            :key="item.id"
+            :label="item.id"
+            >{{ item.name }}</el-checkbox
+          >
+        </el-checkbox-group>
+      </el-form-item>
+      <el-form-item>
+        <el-button type="primary" :loading="loading" @click="confirm"
+          >保存</el-button
+        >
+      </el-form-item>
+    </el-form>
+  </div>
+</template>
+
+<script>
+import {
+  sysCustomRoleList,
+  schoolSetRoleInfo,
+  schoolSetRoleUpdate
+} from "../../api";
+
+export default {
+  name: "school-set-role",
+  props: {
+    school: {
+      type: Object,
+      default() {
+        return {};
+      }
+    }
+  },
+  data() {
+    return {
+      loading: false,
+      modalForm: {
+        roleIds: []
+      },
+      roleList: [],
+      rules: {
+        roleIds: [
+          {
+            required: true,
+            validator: (rule, value, callback) => {
+              if (!value || !value.length) {
+                return callback(new Error(`请选择系统角色管理`));
+              }
+
+              callback();
+            },
+            trigger: "change"
+          }
+        ]
+      }
+    };
+  },
+  mounted() {
+    this.initData();
+  },
+  methods: {
+    async initData() {
+      const roleData = await sysCustomRoleList();
+      this.roleList = roleData || [];
+      const data = await schoolSetRoleInfo(this.school.id);
+      this.modalForm.roleIds = data.roleIdList;
+    },
+    async confirm() {
+      const valid = await this.$refs.modalFormComp.validate();
+      if (!valid) return;
+
+      if (this.loading) return;
+      this.loading = true;
+
+      let datas = {
+        roleIds: this.modalForm.roleIds,
+        schoolId: this.school.id
+      };
+      const res = await schoolSetRoleUpdate(datas).catch(() => {});
+      this.loading = false;
+
+      if (!res) return;
+
+      this.$message.success("修改成功!");
+    }
+  }
+};
+</script>

+ 108 - 0
src/modules/admin/components/school/SchoolSetSync.vue

@@ -0,0 +1,108 @@
+<template>
+  <div class="school-set-sync">
+    <el-form
+      v-if="fields.length"
+      ref="modalFormComp"
+      :model="modalForm"
+      :rules="rules"
+      label-width="120px"
+    >
+      <el-form-item
+        v-for="field in fields"
+        :key="field.code"
+        :prop="field.prop"
+        :label="field.name + ':'"
+      >
+        <el-radio-group v-model="field.enable" @change="resetVal(field)">
+          <el-radio
+            v-for="item in OPEN_STATUS"
+            :key="item.value"
+            :label="item.value"
+            >{{ item.label }}</el-radio
+          >
+        </el-radio-group>
+        <br />
+        <el-input
+          v-if="field.enable"
+          v-model="field.value"
+          placeholder="请输入调用地址"
+          clearable
+        >
+        </el-input>
+      </el-form-item>
+      <el-form-item>
+        <el-button type="primary" :loading="loading" @click="confirm"
+          >保存</el-button
+        >
+      </el-form-item>
+    </el-form>
+  </div>
+</template>
+
+<script>
+import { schoolSetSyncInfo, schoolSetSyncUpdate } from "../../api";
+import { OPEN_STATUS } from "../../../../constants/enumerate";
+
+export default {
+  name: "school-set-sync",
+  props: {
+    school: {
+      type: Object,
+      default() {
+        return {};
+      }
+    }
+  },
+  data() {
+    return {
+      loading: false,
+      OPEN_STATUS,
+      modalForm: {},
+      fields: [],
+      rules: {}
+    };
+  },
+  mounted() {
+    this.initData();
+  },
+  methods: {
+    async initData() {
+      const data = await schoolSetSyncInfo(this.school.id);
+      this.fields = data.result || [];
+      this.fields.forEach(field => {
+        field.prop = field.code.split(".").join("_");
+        this.$set(this.modalForm, field.prop, field.value);
+
+        this.rules[field.prop] = [
+          {
+            validator: (rule, value, callback) => {
+              if (!field.value && field.enable) {
+                return callback(new Error(`请输入${field.name}请求地址`));
+              }
+
+              callback();
+            },
+            trigger: "change"
+          }
+        ];
+      });
+    },
+    resetVal(field) {
+      if (!field.enable) field.value = "";
+    },
+    async confirm() {
+      const valid = await this.$refs.modalFormComp.validate().catch(() => {});
+      if (!valid) return;
+
+      if (this.loading) return;
+      this.loading = true;
+      const datas = { param: this.fields, schoolId: this.school.id };
+      const res = await schoolSetSyncUpdate(datas).catch(() => {});
+      this.loading = false;
+      if (!res) return;
+
+      this.$message.success("修改成功!");
+    }
+  }
+};
+</script>

+ 6 - 0
src/modules/admin/router.js

@@ -1,6 +1,7 @@
 import AdminUserManage from "./views/AdminUserManage.vue";
 import PrivilegeManage from "./views/PrivilegeManage.vue";
 import SystemRoleManage from "./views/SystemRoleManage.vue";
+import SchoolManage from "./views/SchoolManage.vue";
 import AuthSet from "./views/AuthSet.vue";
 import Admin from "./views/Admin.vue";
 
@@ -24,6 +25,11 @@ export default {
       name: "SystemRoleManage",
       component: SystemRoleManage
     },
+    {
+      path: "school-manage",
+      name: "SchoolManage",
+      component: SchoolManage
+    },
     {
       path: "auth-set",
       name: "AuthSet",

+ 145 - 0
src/modules/admin/views/SchoolManage.vue

@@ -0,0 +1,145 @@
+<template>
+  <div class="school-manage">
+    <div class="part-box part-box-filter part-box-flex">
+      <el-form ref="FilterForm" label-position="left" label-width="85px" inline>
+        <el-form-item label="启用/禁用:" label-width="90px">
+          <el-select
+            v-model="filter.schoolId"
+            placeholder="选择学校"
+            filterable
+            clearable
+          >
+            <el-option
+              v-for="item in schools"
+              :key="item.id"
+              :value="item.id"
+              :label="item.name"
+            ></el-option>
+          </el-select>
+        </el-form-item>
+
+        <el-form-item label-width="0px">
+          <el-button type="primary" @click="filterSchool">查询</el-button>
+        </el-form-item>
+      </el-form>
+      <div class="part-box-action">
+        <el-button
+          type="primary"
+          icon="el-icon-refresh"
+          :loading="loading"
+          @click="toSyncSchool"
+          >机构同步</el-button
+        >
+      </div>
+    </div>
+
+    <div class="part-box part-box-pad">
+      <el-table ref="TableList" :data="dataList">
+        <el-table-column type="index" label="序号" width="70"></el-table-column>
+        <el-table-column
+          prop="name"
+          label="学校名称"
+          min-width="200"
+        ></el-table-column>
+        <el-table-column
+          prop="code"
+          label="学校代码"
+          min-width="100"
+        ></el-table-column>
+        <el-table-column
+          prop="code"
+          label="学校域名"
+          min-width="100"
+        ></el-table-column>
+        <el-table-column class-name="action-column" label="操作" width="120">
+          <template slot-scope="scope">
+            <el-button
+              class="btn-primary"
+              type="text"
+              @click="toEdit(scope.row)"
+              >编辑</el-button
+            >
+            <el-button class="btn-primary" type="text" @click="toSet(scope.row)"
+              >设置</el-button
+            >
+          </template>
+        </el-table-column>
+      </el-table>
+    </div>
+
+    <!-- ModifySchool -->
+    <modify-school
+      ref="ModifySchool"
+      :instance="curSchool"
+      @modified="getSchools"
+    ></modify-school>
+    <!-- ModifySchoolSet -->
+    <modify-school-set
+      ref="ModifySchoolSet"
+      :school="curSchool"
+    ></modify-school-set>
+  </div>
+</template>
+
+<script>
+import { schoolList, schoolSync } from "../api";
+import ModifySchool from "../components/ModifySchool.vue";
+import ModifySchoolSet from "../components/ModifySchoolSet.vue";
+
+export default {
+  name: "school-manage",
+  components: { ModifySchool, ModifySchoolSet },
+  data() {
+    return {
+      schools: [],
+      dataList: [],
+      filter: {
+        schoolId: null
+      },
+      curSchool: {},
+      loading: false
+    };
+  },
+  mounted() {
+    this.getSchools();
+  },
+  methods: {
+    async getSchools() {
+      const data = await schoolList();
+      this.schools = data || [];
+      this.dataList = this.schools;
+    },
+    filterSchool() {
+      if (!this.filter.schoolId) {
+        this.dataList = this.schools;
+        return;
+      }
+
+      this.dataList = this.schools.filter(
+        item => item.id === this.filter.schoolId
+      );
+    },
+    async toSyncSchool() {
+      if (this.loading) return;
+      this.loading = true;
+
+      const res = await schoolSync().catch(() => {});
+      this.loading = false;
+
+      if (!res) return;
+
+      this.$message.success("操作成功");
+      this.filter.schoolId = null;
+      this.getSchools();
+    },
+    toEdit(row) {
+      this.curSchool = row;
+      this.$refs.ModifySchool.open();
+    },
+    toSet(row) {
+      this.curSchool = row;
+      this.$refs.ModifySchoolSet.open();
+    }
+  }
+};
+</script>