Bläddra i källkod

Merge tag 'Hotfix-mo-1' into develop

Finish Hotfix-mo-1

# Conflicts:
#	src/views/merchant/create_account.vue
莫绍宝 3 år sedan
förälder
incheckning
0c93dba470

+ 13 - 3
package-lock.json

@@ -9566,7 +9566,8 @@
           "dev": true,
           "optional": true,
           "requires": {
-            "bindings": "^1.5.0"
+            "bindings": "^1.5.0",
+            "nan": "^2.12.1"
           }
         },
         "normalize-path": {
@@ -10999,6 +11000,13 @@
         "thenify-all": "^1.0.0"
       }
     },
+    "nan": {
+      "version": "2.16.0",
+      "resolved": "https://registry.npmmirror.com/nan/-/nan-2.16.0.tgz",
+      "integrity": "sha512-UdAqHyFngu7TfQKsCBgAA6pWDkT8MAO7d0jyOecVhN5354xbLqdn8mV9Tat9gepAupm0bt2DbeaSC8vS52MuFA==",
+      "dev": true,
+      "optional": true
+    },
     "nanomatch": {
       "version": "1.2.13",
       "resolved": "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.13.tgz",
@@ -16251,7 +16259,8 @@
           "dev": true,
           "optional": true,
           "requires": {
-            "bindings": "^1.5.0"
+            "bindings": "^1.5.0",
+            "nan": "^2.12.1"
           }
         },
         "glob-parent": {
@@ -16624,7 +16633,8 @@
           "dev": true,
           "optional": true,
           "requires": {
-            "bindings": "^1.5.0"
+            "bindings": "^1.5.0",
+            "nan": "^2.12.1"
           }
         },
         "glob-parent": {

+ 90 - 0
src/api/merchant.js

@@ -66,4 +66,94 @@ export function editTemplate(params) {
     method: 'post',
     data: params
   })
+}
+
+// 获取部门列表
+export function getDepartmentList(params) {
+  return request({
+    url: '/admin/websit/tree',
+    method: 'get',
+    params
+  })
+}
+
+// 添加部门
+export function addDepartment(params) {
+  return request({
+    url: '/admin/websit/add',
+    method: 'post',
+    data: params
+  })
+}
+
+// 修改部门
+export function editDepartment(params) {
+  return request({
+    url: '/admin/websit/update',
+    method: 'post',
+    data: params
+  })
+}
+
+// 删除部门
+export function deleteDepartment(params) {
+  return request({
+    url: '/admin/websit/delete',
+    method: 'post',
+    params
+  })
+}
+
+// 获取区域列表
+export function getAreaList(params) {
+  return request({
+    url: '/admin/websit/zone/list',
+    method: 'get',
+    params
+  })
+}
+
+// 获取成员列表
+export function getMemberList(params) {
+  return request({
+    url: '/wechat/enterprise/list',
+    method: 'get',
+    params
+  })
+}
+
+// 添加成员
+export function addMember(params) {
+  return request({
+    url: '/wechat/enterprise/add',
+    method: 'post',
+    params
+  })
+}
+
+// 修改成员
+export function editMember(params) {
+  return request({
+    url: '/wechat/enterprise/update',
+    method: 'post',
+    params
+  })
+}
+
+// 删除成员
+export function deleteMember(params) {
+  return request({
+    url: '/wechat/enterprise/delete',
+    method: 'post',
+    params
+  })
+}
+
+// 获取成员详情
+export function getMemberDetail(params) {
+  return request({
+    url: '/wechat/enterprise/detail',
+    method: 'get',
+    params
+  })
 }

+ 1 - 1
src/layout/components/Sidebar/Logo.vue

@@ -25,7 +25,7 @@ export default {
   },
   data() {
     return {
-      title: '商城管理系统',
+      title: '供应链管理系统',
       logo: '@/assets/logo.png'
     }
   }

+ 1 - 50
src/permission.js

@@ -247,53 +247,4 @@ function buildThirdRoute(route, p_url) {
   item.hidden = hidden
   item.children = []
   return item
-}
-
-function mapIconFun(code) {
-  const mapIcon = {
-    dashboard: 'el-icon-s-home', // 首页
-    goods_manage: 'el-icon-s-goods', // 商品管理
-    goods_list: 'el-icon-s-goods', // 商品列表
-    category_manage: 'el-icon-menu', // 分类管理
-    explain: 'el-icon-s-management', // 说明管理
-    order_manage: 'el-icon-s-order', // 订单管理
-    order_list: 'el-icon-s-order', // 订单列表
-    order_pr: 'el-icon-s-release', // 维权订单
-    ticket: 'el-icon-s-ticket', // 开发票
-    comment_tag: 'el-icon-s-flag', // 评价标签
-    promotion: 'el-icon-s-opportunity', // 活动管理
-    groupbuy_index: 'el-icon-s-goods', // 团购活动
-    promotion_ms: 'el-icon-s-help', // 秒杀活动
-    discode_index: 'el-icon-s-grid', // 优惠码
-    promotion_coupon: 'el-icon-s-ticket', // 优惠券设置
-    vip_manage: 'el-icon-s-custom', // 会员管理
-    member_index: 'el-icon-s-custom', // 会员列表
-    salesman_apply: 'el-icon-s-check', // 业务员申请
-    wxcustomer: 'el-icon-s-custom', // 企微客户管理
-    settle_manage: 'el-icon-s-check', // 结算管理
-    delivery_manage: 'el-icon-s-cooperation', // 配送管理
-    stockpile_manage: 'el-icon-s-shop', // 仓储管理
-    msg: 'el-icon-message-solid', // 消息列表
-    tag_manage: 'el-icon-s-flag', // 消息列表
-
-    setting: 'el-icon-s-tools', // 系统设置
-    account: 'el-icon-s-promotion', // 帐号管理
-    authority: 'el-icon-s-flag', // 权限管理
-    log: 'el-icon-s-order', // 操作日志
-    carousel: 'el-icon-picture', // 轮播图设置
-    profile: 'el-icon-user-solid', // 个人信息
-    noticebar: 'el-icon-warning', // 通告管理
-    offline: 'el-icon-s-help', // 线下数据
-    offline_index: 'el-icon-s-marketing', // 线下数据
-    sales_index: 'el-icon-s-marketing', // 线下数据
-
-    merchant: 'el-icon-s-shop', // 商户管理
-    merchant_list: 'el-icon-s-shop', // 商户列表
-    create_account: 'el-icon-circle-plus', // 开通账号
-
-    marketing: 'el-icon-s-marketing', // 营销活动
-    material: 'el-icon-picture', // 营销素材
-    spu_list: 'el-icon-s-claim', // 个人SOP
-  }
-  return mapIcon[code]
-}
+}

+ 1 - 1
src/store/modules/user.js

@@ -96,7 +96,7 @@ const actions = {
         commit('SET_PHONE', userName)
         // commit("SET_MENUS", menus) // 触发vuex SET_MENUS 保存路由表到vuex
 
-        localStorage.setItem("greemall_user", JSON.stringify(data));
+        localStorage.setItem("supply_user", JSON.stringify(data));
 
         resolve(data)
       }).catch(error => {

+ 0 - 0
src/styles/element-ui.scss


+ 25 - 0
src/styles/index.scss

@@ -233,4 +233,29 @@ div:focus {
 
 .el-menu-item, .el-submenu__title {
   font-weight: 600 !important;
+}
+
+.page-footer {
+  height: 70px;
+  .footer {
+    position: fixed;
+    bottom: 0;
+    left: 0;
+    z-index: 1;
+    width: 100%;
+    background: #fff;
+    padding: 15px 40px;
+    box-sizing: border-box;
+    transition: all 0.28s;
+    text-align: right;
+    box-shadow: 0 2px 5px 0 rgb(0 0 0 / 50%), 0 2px 5px 0 rgb(0 0 0 / 10%);
+    &.hideSidebar {
+      margin-left: 54px;
+      width: calc(100vw - 54px);
+    }
+    &.openSidebar {
+      margin-left: 210px;
+      width: calc(100vw - 210px);
+    }
+  }
 }

+ 0 - 0
src/styles/mixin.scss


+ 0 - 0
src/styles/sidebar.scss


+ 0 - 0
src/styles/transition.scss


+ 0 - 0
src/styles/variables.scss


+ 2 - 2
src/utils/auth.js

@@ -1,7 +1,7 @@
 import Cookies from 'js-cookie'
 
-const TokenKey = 'greemall_token'
-const UseridKey = 'greemall_userid'
+const TokenKey = 'supply_token'
+const UseridKey = 'supply_userid'
 
 export function getToken() {
   return Cookies.get(TokenKey)

+ 8 - 10
src/views/login/index.vue

@@ -12,9 +12,7 @@
         <div class="empty-height" />
         <div class="form-container">
 
-          <div class="title">
-            格匠商城后台管理
-          </div>
+          <div class="title">供应链管理系统</div>
 <!--      <div class="logo">-->
 <!--        <img src="@/assets/login/logo.png" alt="">-->
 <!--      </div>-->
@@ -140,8 +138,8 @@ export default {
   },
   created() {
     // 获取缓存信息
-    if(localStorage.getItem("greemall_login")) {
-      let storageData = JSON.parse(localStorage.getItem("greemall_login"));
+    if(localStorage.getItem("supply_login")) {
+      let storageData = JSON.parse(localStorage.getItem("supply_login"));
       this.loginForm.username = storageData.username;
       this.isRemenberPw = storageData.isRemenberPw;
     }
@@ -202,7 +200,7 @@ export default {
         username: this.loginForm.username,
         isRemenberPw: this.isRemenberPw
       }
-      localStorage.setItem("greemall_login", JSON.stringify(storageData));
+      localStorage.setItem("supply_login", JSON.stringify(storageData));
 
       if(this.isRemenberPw) {
         this.setCookie(this.loginForm.username, this.loginForm.password, 7);
@@ -214,8 +212,8 @@ export default {
       var exdate = new Date(); //获取时间
       exdate.setTime(exdate.getTime() + 24 * 60 * 60 * 1000 * exdays); //保存的天数
       //字符串拼接cookie
-      window.document.cookie = "greemall_username" + "=" + c_name + ";path=/;expires=" + exdate.toGMTString();
-      window.document.cookie = "greemall_password" + "=" + c_pwd + ";path=/;expires=" + exdate.toGMTString();
+      window.document.cookie = "supply_username" + "=" + c_name + ";path=/;expires=" + exdate.toGMTString();
+      window.document.cookie = "supply_password" + "=" + c_pwd + ";path=/;expires=" + exdate.toGMTString();
     },
 
     //读取cookie
@@ -225,9 +223,9 @@ export default {
         for (var i = 0; i < arr.length; i++) {
           var arr2 = arr[i].split('='); //再次切割
           //判断查找相对应的值
-          if (arr2[0] == 'greemall_username') {
+          if (arr2[0] == 'supply_username') {
             this.loginForm.username = arr2[1]; //保存到保存数据的地方
-          } else if (arr2[0] == 'greemall_password') {
+          } else if (arr2[0] == 'supply_password') {
             this.loginForm.password = arr2[1];
           }
         }

+ 377 - 0
src/views/merchant/create_account.vue

@@ -0,0 +1,377 @@
+<template>
+  <div class="app-container">
+    <div v-show="step == 1">
+      <div class="setting_title">开通账号</div>
+      <el-divider></el-divider>
+      <div class="tips">说明:开通商户账号是指开通商城后台管理系统的总登录账号。</div>
+
+      <el-card shadow="never" class="my-card">
+        <el-form class="my-form" ref="step1Form" :model="step1Form" :rules="step1FormRules" label-width="100px" label-position="right">
+          <el-form-item label="商户账号" prop="account">
+            <el-input v-model="step1Form.account" autocomplete="off" placeholder="请输入商户账号"></el-input>
+            <el-popover
+              class="question"
+              placement="right-start"
+              title="账号设置"
+              width="260"
+              trigger="hover"
+              content="账号设置需按数字、字母组合设置至少12位账号">
+              <svg-icon icon-class="question" slot="reference" />
+            </el-popover>
+          </el-form-item>
+          <el-form-item label="账户昵称" prop="nickName">
+            <el-input v-model="step1Form.nickName" autocomplete="off" placeholder="请输入账户昵称"></el-input>
+          </el-form-item>
+          <el-form-item label="小程序名称" prop="appName">
+            <el-input v-model="step1Form.appName" autocomplete="off" placeholder="请输入小程序名称"></el-input>
+          </el-form-item>
+          <el-form-item label="负责人" prop="chargePerson">
+            <el-input v-model="step1Form.chargePerson" autocomplete="off" placeholder="请输入负责人"></el-input>
+          </el-form-item>
+          <el-form-item label="联系电话" prop="phone">
+            <el-input v-model="step1Form.phone" autocomplete="off" placeholder="请输入联系电话"></el-input>
+          </el-form-item>
+          <el-form-item label="电子邮箱" prop="email">
+            <el-input v-model="step1Form.email" autocomplete="off" placeholder="请输入电子邮箱"></el-input>
+          </el-form-item>
+          <el-form-item label="地址" prop="address">
+            <el-input v-model="step1Form.address" autocomplete="off" placeholder="请输入地址"></el-input>
+          </el-form-item>
+          <el-form-item label="登录密码" prop="newPassword">
+            <el-input v-model="step1Form.newPassword" ref="password1" autocomplete="off" placeholder="请输入登录密码" :type="passwordType1"></el-input>
+            <span class="show-pwd" @click="showPwd(1)">
+              <svg-icon :icon-class="passwordType1 === 'password' ? 'eye' : 'eye-open'" />
+            </span>
+            <el-popover
+              class="question"
+              placement="right-start"
+              title="密码设置"
+              width="260"
+              trigger="hover"
+              content="密码设置需按数字、字母组合设置至少12位密码">
+              <svg-icon icon-class="question" slot="reference" />
+            </el-popover>
+          </el-form-item>
+          <el-form-item label="确认密码" prop="confirmPassword">
+            <el-input v-model="step1Form.confirmPassword" ref="password2" autocomplete="off" placeholder="请再次输入密码" :type="passwordType2"></el-input>
+            <span class="show-pwd" @click="showPwd(2)">
+              <svg-icon :icon-class="passwordType2 === 'password' ? 'eye' : 'eye-open'" />
+            </span>
+            <el-popover
+              class="question"
+              placement="right-start"
+              title="密码设置"
+              width="260"
+              trigger="hover"
+              content="确认密码需要和登录密码保持一致">
+              <svg-icon icon-class="question" slot="reference" />
+            </el-popover>
+          </el-form-item>
+        </el-form>
+      </el-card>
+    </div>
+
+    <div class="page-footer">
+      <div class="footer" :class="classObj">
+        <el-button type="primary" @click="clickSubmitForm" :loading="formLoading">{{ formLoading ? '提交中 ...' : '提 交' }}</el-button>
+        <el-popconfirm
+          title="确定关闭吗?"
+          @onConfirm="goBack"
+          style="margin-left: 10px;"
+        >
+          <el-button slot="reference">关 闭</el-button>
+        </el-popconfirm>
+      </div>
+    </div>
+    
+  </div>
+</template>
+
+<script>
+import { getToken } from '@/utils/auth'
+import { addAccount } from "@/api/merchant";
+
+export default {
+  data() {
+    var validateAccount = (rule, value, callback) => {
+      if (value === '') {
+        callback(new Error('请输入商户账号'));
+      } else if (value.length < 12) {
+        callback(new Error('账号长度至少12位'));
+      } else if (/[A-Za-z].*[0-9]|[0-9].*[A-Za-z]/.test(value) == false) {
+        callback(new Error('账号必须包含数字和字母'));
+      } else {
+        callback();
+      }
+    };
+    var validatePass3 = (rule, value, callback) => {
+      if (value === '') {
+        callback(new Error('请输入登录密码'));
+      } else if (value.length < 12) {
+        callback(new Error('密码长度至少12位'));
+      } else if (/[A-Za-z].*[0-9]|[0-9].*[A-Za-z]/.test(value) == false) {
+        callback(new Error('密码必须包含数字和字母'));
+      } else {
+        if (this.step1Form.confirmPassword !== '') {
+          this.$refs.step1Form.validateField('confirmPassword');
+        }
+        callback();
+      }
+    };
+    var validatePass4 = (rule, value, callback) => {
+      if (value === '') {
+        callback(new Error('请再次输入密码'));
+      } else if (value !== this.step1Form.newPassword) {
+        callback(new Error('两次输入密码不一致'));
+      } else {
+        callback();
+      }
+    };
+    return {
+      baseURL: process.env.VUE_APP_BASE_API,
+      myHeaders: {'x-token': getToken()},
+      step: 1,
+      step1Form: {
+        account: '', // 账号
+        nickName: '', // 用户名
+        appName: '', // 小程序名称
+        chargePerson: '', // 负责人
+        phone: '', // 联系电话
+        email: '', // 电子邮箱
+        address: '', // 地址
+        newPassword: '', // 登录密码
+        confirmPassword: '', // 确认密码
+      },
+      step1FormRules: {
+        account: [
+          { required: true, validator: validateAccount, trigger: 'blur' }
+        ],
+        nickName: [
+          { required: true, message: '请输入用户名', trigger: 'blur' }
+        ],
+        appName: [
+          { required: true, message: '请输入用户名', trigger: 'blur' }
+        ],
+        chargePerson: [
+          { required: true, message: '请输入负责人', trigger: 'blur' }
+        ],
+        phone: [
+          { required: true, message: '请输入联系电话', trigger: 'blur' }
+        ],
+        newPassword: [
+          { required: true, validator: validatePass3, trigger: 'blur' }
+        ],
+        confirmPassword: [
+          { required: true, validator: validatePass4, trigger: 'blur' }
+        ],
+      },
+      passwordType1: 'password',
+      passwordType2: 'password',
+
+      formLoading: false,
+    }
+  },
+  computed: {
+    sidebar() {
+      return this.$store.state.app.sidebar
+    },
+    classObj() {
+      return {
+        hideSidebar: !this.sidebar.opened,
+        openSidebar: this.sidebar.opened
+      }
+    },
+  },
+  methods: {
+    goBack() {
+      this.$router.go(-1);
+    },
+
+    // 显示隐藏密码
+    showPwd(num) {
+      if(num == 1) {
+        if (this.passwordType1 === 'password') {
+          this.passwordType1 = ''
+        } else {
+          this.passwordType1 = 'password'
+        }
+        this.$nextTick(() => {
+          this.$refs.password1.focus()
+        })
+      }
+      if(num == 2) {
+        if (this.passwordType2 === 'password') {
+          this.passwordType2 = ''
+        } else {
+          this.passwordType2 = 'password'
+        }
+        this.$nextTick(() => {
+          this.$refs.password2.focus()
+        })
+      }
+    },
+
+    // 点击 提交表单
+    clickSubmitForm() {
+      this.$refs.step1Form.validate((valid) => {
+        if (valid) {
+          this.submitForm();
+        }
+      })
+    },
+
+    // 提交表单
+    submitForm() {
+      this.formLoading = true;
+      let params = {
+        type: 1,
+        userName: this.step1Form.account,
+        nickName: this.step1Form.nickName,
+        minAppName: this.step1Form.appName,
+        linkName: this.step1Form.chargePerson,
+        linkPhone: this.step1Form.phone,
+        email: this.step1Form.email,
+        address: this.step1Form.address,
+        password: this.step1Form.confirmPassword,
+      }
+      addAccount(params).then(res => {
+        this.$successMsg('开通成功');
+        setTimeout(() => {
+          this.goBack();
+        }, 1500)
+      }).finally(res => {
+        this.formLoading = false;
+      })
+    }
+  }
+}
+</script>
+
+<style lang="scss" scoped>
+  .setting_title {
+    padding-left: 0;
+  }
+  .tips {
+    font-size: 14px;
+  }
+  .my-card {
+    margin-top: 20px;
+    .box {
+      background: rgb(235, 240, 249);
+      padding: 10px;
+      font-size: 14px;
+      margin: 20px 0;
+      line-height: 18px;
+      ::v-deep .el-link {
+        vertical-align: unset;
+      }
+    }
+  }
+  .my-form {
+    width: 450px;
+    margin: 0 auto;
+  }
+  .show-pwd {
+    position: absolute;
+    right: 15px;
+    top: 0;
+    font-size: 16px;
+    cursor: pointer;
+    user-select: none;
+  }
+  .question {
+    position: absolute;
+    right: -30px;
+    top: 0;
+    font-size: 20px;
+    cursor: pointer;
+    user-select: none;
+  }
+  .my-form2 {
+    ::v-deep input {
+      width: 400px;
+    }
+  }
+  .tips {
+    margin-top: 10px;
+    span {
+      display: inline-block;
+      width: 300px;
+      text-align: center;
+      line-height: 32px;
+      background: #ffefef;
+      font-size: 14px;
+      color: #f66460;
+    }
+  }
+  .images {
+    display: flex;
+    flex-wrap: wrap;
+    .main-img {
+      display: flex;
+      flex-direction: column;
+      justify-content: center;
+      align-items: center;
+      width: 120px;
+      margin-right: 20px;
+      .img {
+        border: 1px dashed #eaeaea;
+        border-radius: 5px;
+        overflow: hidden;
+        position: relative;
+        .el-image {
+          display: block;
+        }
+        .mask {
+          position: absolute;
+          left: 0;
+          top: 0;
+          width: 120px;
+          height: 120px;
+          background: rgba($color: #000000, $alpha: 0.3);
+          display: flex;
+          align-items: center;
+          justify-content: center;
+          i {
+            font-size: 20px;
+            color: #ffffff;
+            cursor: pointer;
+            margin: 0 8px;
+          }
+        }
+      }
+      .text {
+        font-size: 14px;
+        color: #666666;
+      }
+    }
+    .add {
+      width: 120px;
+      height: 120px;
+      border: 1px dashed #eaeaea;
+      border-radius: 5px;
+      cursor: pointer;
+      display: flex;
+      align-items: center;
+      justify-content: center;
+      i {
+        font-size: 30px;
+        color: #999;
+      }
+    }
+    .tmp-img {
+      position: relative;
+      .tmp {
+        position: absolute;
+        left: 0;
+        top: 0;
+        line-height: 20px;
+        padding: 0 8px;
+        background: #f66460;
+        border-radius: 0 0 10px 0;
+        font-size: 12px;
+        color: #ffffff;
+      }
+    }
+  }
+</style>

+ 736 - 0
src/views/merchant/department.vue

@@ -0,0 +1,736 @@
+<template>
+  <div class="app-container">
+    <div class="tree-container">
+      <div style="padding: 10px; display: flex;">
+        <el-button icon="el-icon-refresh-right" size="small" @click="refreshDepartment()" style="padding: 9px 10px; margin-right: 6px"></el-button>
+        <el-input
+          placeholder="输入关键字进行过滤"
+          size="small"
+          clearable
+          v-model="filterText">
+        </el-input>
+      </div>
+      <el-tree
+        :data="departmentList"
+        :props="defaultProps"
+        default-expand-all
+        highlight-current
+        :expand-on-click-node="false"
+        :filter-node-method="filterNode"
+        @node-click="handleNodeClick"
+        node-key="id"
+        ref="tree">
+        <div class="custom-tree-node" slot-scope="{ node, data }">
+          <i :class="data.children && data.children.length > 0 ? 'el-icon-folder-opened':'el-icon-document-remove'"></i><span>{{ node.label }}</span>
+        </div>
+      </el-tree>
+    </div>
+    <div class="mymain-container">
+      <div class="screen-container">
+        <!-- <div class="top clearfix">
+          <div class="title fl">条件筛选</div>
+        </div> -->
+        <el-form ref="screenForm" :model="screenForm" label-width="70px" size="small" label-position="left">
+          <el-row :gutter="20">
+            <el-col :xs="24" :sm="12" :lg="12">
+              <el-form-item label="成员名称" prop="name">
+                <el-input v-model="screenForm.name" placeholder="请输入成员名称"></el-input>
+              </el-form-item>
+            </el-col>
+            <el-col :xs="24" :sm="12" :lg="12" class="tr">
+              <el-form-item label="">
+                <el-button size="small" @click="resetScreenForm">清空</el-button>
+                <el-button size="small" type="primary" @click="submitScreenForm">搜索</el-button>
+              </el-form-item>
+            </el-col>
+          </el-row>
+        </el-form>
+      </div>
+      <div class="btn-group clearfix" style="margin-top: 20px">
+        <div class="fl">
+          <el-button size="small" type="primary" @click="openDepartmentForm('add')">添加部门</el-button>
+          <el-button size="small" type="primary" @click="openDepartmentForm('edit')">编辑部门</el-button>
+          <el-divider direction="vertical"></el-divider>
+          <el-button size="small" type="primary" @click="openMemberForm('add')">添加成员</el-button>
+           
+          <el-button size="small" type="danger" @click="batchDeleteMember()">删除成员</el-button>
+
+            <el-button size="small" type="danger" @click="delHandleDownload" v-if="checkBtnRole('download')">下载导入删除模板</el-button>
+          <el-upload
+            class="import-btn2"
+            style="display: inline-block; margin-left: 10px"
+            :action="baseURL + 'student/import'"
+            :http-request="handleImport2"
+            :file-list="importFileList2"
+            v-if="checkBtnRole('import')"
+          >
+            <el-button size="small" type="danger" :loading="importLoading2">{{ importLoading2 ? '导入中...' : '导入删除成员' }}</el-button>
+          </el-upload>
+        </div>
+        <div class="fr">
+          <el-upload
+            class="import-btn"
+            style="height: 0; width: 0; overflow: hidden;"
+            :action="baseURL + 'student/import'"
+            :http-request="handleImport"
+            :file-list="importFileList"
+            v-if="checkBtnRole('import')"
+          >
+            <el-button size="small" type="primary" :loading="importLoading">{{ importLoading ? '导入中...' : '导入' }}</el-button>
+          </el-upload>
+
+          <el-button size="small" type="primary" @click="handleExport">导出</el-button>
+
+          <el-button size="small" type="primary" :loading="importLoading" @click="clickImport">{{ importLoading ? '导入中...' : '导入' }}</el-button>
+          
+          <el-button size="small" @click="handleDownload" v-if="checkBtnRole('download')">下载导入模板</el-button>
+        </div>
+      </div>
+
+      <div class="table">
+        <el-table v-loading="listLoading" :data="dataList" element-loading-text="Loading" border fit highlight-current-row stripe @selection-change="handleTableSelection">
+          <el-table-column align="center" type="selection" width="55" fixed></el-table-column>
+          <el-table-column align="center" label="操作" min-width="110" fixed>
+            <template slot-scope="scope">
+              <el-button type="text" @click="openMemberForm('edit', scope.row.id)" v-if="checkBtnRole('edit')">编辑</el-button>
+              <el-popconfirm style="margin-left: 10px;" title="确定删除吗?" @onConfirm="deleteMember(scope.row.id)" v-if="checkBtnRole('del')">
+                <el-button slot="reference" type="text">删除</el-button>
+              </el-popconfirm>
+            </template>
+          </el-table-column>
+          <el-table-column align="center" label="姓名" prop="name" min-width="100" show-overflow-tooltip></el-table-column>
+          <el-table-column align="center" label="性别" prop="gender" min-width="100">
+            <template slot-scope="scope">
+              <span v-if="scope.row.gender == 1">男</span>
+              <span v-else-if="scope.row.gender == 2">女</span>
+              <span v-else>未知</span>
+            </template>
+          </el-table-column>
+          <el-table-column align="center" label="账号" prop="wechatUserId" min-width="140" show-overflow-tooltip></el-table-column>
+          <el-table-column align="center" label="部门" prop="departmentName" min-width="180" show-overflow-tooltip>
+            <template slot-scope="scope">
+              {{ scope.row.departmentName }}
+            </template>
+          </el-table-column>
+          <el-table-column align="center" label="职务" prop="position" min-width="140" show-overflow-tooltip></el-table-column>
+          <el-table-column align="center" label="手机号码" prop="mobile" min-width="140"></el-table-column>
+          <el-table-column align="center" label="邮箱" prop="email" min-width="160" show-overflow-tooltip></el-table-column>
+          <el-table-column align="center" label="创建时间" prop="createTime" min-width="160"></el-table-column>
+        </el-table>
+      </div>
+      
+      <div class="pagination clearfix">
+        <div class="fr">
+          <el-pagination
+            @size-change="handleSizeChange"
+            @current-change="handleCurrentChange"
+            :current-page="currentPage"
+            :page-sizes="[10, 20, 30, 50]"
+            :page-size="10"
+            layout="total, sizes, prev, pager, next, jumper"
+            :total="listTotal">
+          </el-pagination>
+        </div>
+      </div>
+    </div>
+    
+    <!-- 添加编辑部门 -->
+    <el-dialog :title="departmentFormType == 'add' ? '添加部门':'编辑部门'" :visible.sync="departmentFormVisible" :show-close="false" width="40%" :close-on-click-modal="false">
+      <el-form ref="departmentForm" :model="departmentForm" :rules="departmentFormRules" label-position="right" label-width="80px">
+        <el-form-item label="部门名称" prop="name">
+          <el-input placeholder="请输入部门名称" v-model="departmentForm.name"></el-input>
+        </el-form-item>
+        <el-form-item label="部门编号" prop="code">
+          <el-input placeholder="请输入部门编号" v-model="departmentForm.code"></el-input>
+        </el-form-item>
+        <el-form-item label="选择区域" prop="area">
+          <el-select v-model="departmentForm.area" placeholder="请选择区域" style="width: 100%">
+            <el-option
+              v-for="item in areaList"
+              :key="item.id"
+              :label="item.zoneName"
+              :value="item.id">
+            </el-option>
+          </el-select>
+        </el-form-item>
+      </el-form>
+      <div slot="footer" class="dialog-footer">
+        <el-button @click="cancelDepartmentForm">取 消</el-button>
+        <el-button type="primary" @click="submitDepartmentForm">确 定</el-button>
+      </div>
+    </el-dialog>
+
+    <!-- 添加编辑成员 -->
+    <el-dialog :title="memberFormType == 'add' ? '添加成员':'编辑成员'" :visible.sync="memberFormVisible" :show-close="false" width="60%" :close-on-click-modal="false">
+      <el-form ref="memberForm" :model="memberForm" :rules="memberFormRules" label-position="left" label-width="50px" size="small">
+        <el-row :gutter="20">
+          <el-col :xs="24" :sm="12" :lg="12">
+            <el-form-item label="姓名" prop="name">
+              <el-input placeholder="请输入姓名" v-model="memberForm.name"></el-input>
+            </el-form-item>
+          </el-col>
+          <el-col :xs="24" :sm="12" :lg="12" style="height: 51px;">
+            <el-form-item label="性别" prop="sex">
+              <el-radio-group v-model="memberForm.sex">
+                <el-radio :label="1">男</el-radio>
+                <el-radio :label="2">女</el-radio>
+              </el-radio-group>
+            </el-form-item>
+          </el-col>
+          <el-col :xs="24" :sm="12" :lg="12">
+            <el-form-item label="账号" prop="account">
+              <el-input placeholder="请输入账号" v-model="memberForm.account" :disabled="memberFormType === 'edit'"></el-input>
+            </el-form-item>
+          </el-col>
+          <el-col :xs="24" :sm="12" :lg="12">
+            <el-form-item label="部门" prop="department">
+              <el-input placeholder="请输入部门" v-model="memberForm.department" disabled></el-input>
+            </el-form-item>
+          </el-col>
+          <el-col :xs="24" :sm="12" :lg="12">
+            <el-form-item label="职务" prop="post">
+              <el-input placeholder="请输入职务" v-model="memberForm.post"></el-input>
+            </el-form-item>
+          </el-col>
+          <el-col :xs="24" :sm="12" :lg="12">
+            <el-form-item label="手机" prop="phone">
+              <el-input placeholder="请输入手机" v-model="memberForm.phone"></el-input>
+            </el-form-item>
+          </el-col>
+          <el-col :xs="24" :sm="12" :lg="12">
+            <el-form-item label="邮箱" prop="email">
+              <el-input placeholder="请输入邮箱" v-model="memberForm.email"></el-input>
+            </el-form-item>
+          </el-col>
+        </el-row>
+      </el-form>
+      <div slot="footer" class="dialog-footer">
+        <el-button @click="cancelMemberForm">取 消</el-button>
+        <el-button type="primary" @click="submitMemberForm">确 定</el-button>
+      </div>
+    </el-dialog>
+
+  </div>
+</template>
+
+<script>
+import { 
+  getDepartmentList, addDepartment, editDepartment, deleteDepartment, getAreaList,
+  getMemberList, addMember, editMember, deleteMember, getMemberDetail
+  } from '@/api/merchant'
+import { findElem, downloadFiles, handleImport } from '@/utils/util'
+
+export default {
+  data() {
+    return {
+      baseURL: process.env.VUE_APP_BASE_API,
+      dataList: null, // 列表数据
+      moduleList: null, // 模块列表
+      listLoading: true, // 列表加载loading
+      screenForm: { // 筛选表单数据
+        name: '', // 名称
+      },
+      currentPage: 1, // 当前页码
+      pageSize: 10, // 每页数量
+      listTotal: 0, // 列表总数
+
+      departmentFormType: 'add',
+      departmentFormVisible: false,
+      departmentForm: {
+        name: '',
+        code: '',
+        area: '',
+      },
+      departmentFormRules: {
+        name: [
+          { required: true, message: '请填写部门名称', trigger: 'blur' },
+        ],
+        code: [
+          { required: true, message: '请填写部门编号', trigger: 'blur' }
+        ]
+      },
+      selectDepartment: null, // 选中的部门
+
+      memberFormType: 'add',
+      memberFormVisible: false,
+      memberForm: {
+        name: '',
+        sex: 1,
+        account: '',
+        department: '',
+        departmentId: '',
+        post: '',
+        phone: '',
+        email: '',
+      },
+      memberFormRules: {
+        name: [
+          { required: true, message: '请填写姓名', trigger: 'blur' },
+        ],
+        sex: [
+          { required: true, message: '请选择性别', trigger: 'change' }
+        ],
+        account: [
+          { required: true, validator: function(rule, value, callback) {
+            if (value === '') {
+              callback(new Error('请填写账号'));
+            } else if (value.length > 0 && value.match(/[\x01-\xFF]*/) == false) {
+              callback(new Error('账号不能填写中文'));
+            }else {
+              callback();
+            }
+          }, trigger: 'blur' },
+        ],
+        department: [
+          { required: true, message: '请填写部门', trigger: 'blur' },
+        ],
+        post: [
+          { required: true, message: '请填写职务', trigger: 'blur' },
+        ],
+        phone: [
+          { required: true, validator: function(rule, value, callback) {
+            if (value === '') {
+              callback(new Error('请填写手机号'));
+            } else if (value.length > 0 && /^[1][3,4,5,6,7,8,9][0-9]{9}$/.test(value) == false) {
+              callback(new Error('请填写正确的手机号'));
+            }else {
+              callback();
+            }
+          }, trigger: 'blur' },
+        ],
+        email: [
+          { validator: function(rule, value, callback) {
+            if (value && value.length > 0 && /^[a-zA-Z0-9_-]+@[a-zA-Z0-9_-]+(\.[a-zA-Z0-9_-]+)+$/.test(value) == false) {
+              callback(new Error('请填写正确的邮箱'));
+            }else {
+              callback();
+            }
+          }, trigger: 'blur' },
+        ],
+      },
+      editMemberId: null, 
+
+      filterText: '',
+      departmentList: [],
+      defaultProps: {
+        children: 'children',
+        label: 'name'
+      },
+
+      areaList: [],
+      tableSelection: [],
+
+      importLoading: false, // 导入加载loading
+      importFileList: [], // 导入列表
+
+      importLoading2: false, // 导入加载loading
+      importFileList2: [], // 导入列表
+    }
+  },
+  watch: {
+    filterText(val) {
+      this.$refs.tree.filter(val);
+    }
+  },
+  created() {
+    this.getTree();
+    this.getList();
+    this.getAreaList();
+  },
+  methods: {
+    // 查询按钮权限
+    checkBtnRole(value) {
+      console.log(value)
+      // let btnRole = this.$route.meta.roles;
+      // if(!btnRole) {return true}
+      // let index = btnRole.indexOf(value);
+      // return index >= 0 ? true : false;
+      return true;
+    },
+
+    // 获取部门列表
+    getTree() {
+      getDepartmentList().then(res => {
+        this.departmentList = res.data;
+      })
+    },
+
+    // 获取成员列表
+    getList() {
+      this.listLoading = true;
+
+      let params = {
+        pageNo: this.currentPage,
+        pageSize: this.pageSize,
+        adminWebsitId: this.selectDepartment ? this.selectDepartment.id : '',
+        websitId: this.selectDepartment ? this.selectDepartment.websitId : '',
+        keyword: this.screenForm.name
+      };
+
+      getMemberList(params).then(res => {
+        this.dataList = res.data.records;
+        this.listTotal = res.data.total;
+        this.listLoading = false;
+      })
+    },
+
+    // 获取区域列表
+    getAreaList() {
+      getAreaList().then(res => {
+        this.areaList = res.data;
+      })
+    },
+
+    // 更改每页数量
+    handleSizeChange(val) {
+      this.pageSize = val;
+      this.currentPage = 1;
+      this.getList();
+    },
+
+    // 更改当前页
+    handleCurrentChange(val) {
+      this.currentPage = val;
+      this.getList();
+    },
+
+    // 提交筛选表单
+    submitScreenForm() {
+      this.currentPage = 1;
+      this.getList();
+    },
+
+    // 重置筛选表单
+    resetScreenForm() {
+      this.$refs.screenForm.resetFields();
+      this.currentPage = 1;
+      this.getList();
+    },
+
+    // 筛选部门
+    filterNode(value, data) {
+      if (!value) return true;
+      return data.name.indexOf(value) !== -1;
+    },
+
+    // 选择部门
+    handleNodeClick(data) {
+      console.log(data);
+      if(this.selectDepartment && data.websitId === this.selectDepartment.websitId) {
+        this.$refs.tree.setCurrentKey(null);
+        this.selectDepartment = null;
+      }else {
+        this.selectDepartment = data;
+      }
+      this.getList();
+    },
+
+    // 刷新部门
+    refreshDepartment() {
+      this.$refs.tree.setCurrentKey(null);
+      this.selectDepartment = null;
+      this.getTree();
+      this.getList();
+    },
+
+    // 打开 新增编辑 部门表单
+    openDepartmentForm(type) {
+      this.departmentFormType = type;
+      if(!this.selectDepartment) {
+        return this.$errorMsg('请选择部门');
+      }
+      if(type == 'edit') {
+        this.departmentForm = {
+          name: this.selectDepartment.name,
+          code: this.selectDepartment.websitNumber,
+          area: this.selectDepartment.zoneId,
+        }
+      }
+      this.departmentFormVisible = true;
+    },
+
+    // 取消 新增编辑 部门表单
+    cancelDepartmentForm(){
+      this.departmentFormVisible = false;
+      this.$refs.departmentForm.resetFields();
+      this.departmentForm = {
+        name: '',
+        code: '',
+        area: '',
+      }
+    },
+
+    // 提交 部门表单
+    submitDepartmentForm() {
+      this.$refs.departmentForm.validate((valid) => {
+        if (valid) {
+          let params = {
+            name: this.departmentForm.name,
+            websitNumber: this.departmentForm.code,
+          }
+          if(this.departmentForm.area) {
+            params.zoneId = this.departmentForm.area;
+            params.areaName = this.areaList[findElem(this.areaList, 'id', this.departmentForm.area)].zoneName;
+          }
+          if(this.departmentFormType == 'edit') {
+            params.id = this.selectDepartment.id;
+            params.websitId = this.selectDepartment.websitId;
+            params.parentId = this.selectDepartment.parentId;
+            editDepartment(params).then(res => {
+              this.cancelDepartmentForm();
+              this.getTree();
+              this.getList();
+              this.$successMsg('编辑成功');
+            })
+          }else {
+            params.parentId = this.selectDepartment ? this.selectDepartment.websitId : 0;
+            addDepartment(params).then(res => {
+              this.cancelDepartmentForm();
+              this.getTree();
+              this.getList();
+              this.$successMsg('添加成功');
+            })
+          }
+        }
+      })
+    },
+
+    // 打开 新增编辑 成员表单
+    openMemberForm(type, id) {
+      if(type == 'add') {
+        if(!this.selectDepartment) {
+          return this.$errorMsg('请选择部门');
+        }
+        this.memberForm.department = this.selectDepartment.name;
+        this.memberForm.departmentId = this.selectDepartment.websitId;
+      }
+      if(type == 'edit') {
+        this.editMemberId = id;
+        getMemberDetail({id: id}).then(res => {
+          this.memberForm = {
+            name: res.data.name,
+            sex: res.data.gender,
+            account: res.data.wechatUserId,
+            department: res.data.departmentName,
+            departmentId: res.data.mainDepartment,
+            post: res.data.position,
+            phone: res.data.mobile,
+            email: res.data.email,
+          }
+        })
+      }
+      this.memberFormType = type;
+      this.memberFormVisible = true;
+    },
+
+    // 取消 新增编辑 成员表单
+    cancelMemberForm(){
+      this.memberFormVisible = false;
+      this.$refs.memberForm.resetFields();
+    },
+
+    // 提交 成员表单
+    submitMemberForm() {
+      this.$refs.memberForm.validate((valid) => {
+        if (valid) {
+          let params = {
+            name: this.memberForm.name,
+            gender: this.memberForm.sex,
+            wechatUserId: this.memberForm.account,
+            mainDepartmentId: this.memberForm.departmentId,
+            position: this.memberForm.post,
+            mobile: this.memberForm.phone,
+            email: this.memberForm.email,
+          }
+          if(this.memberFormType == 'edit') {
+            params.id = this.editMemberId;
+            editMember(params).then(res => {
+              this.cancelMemberForm();
+              this.getList();
+              this.$successMsg('编辑成功');
+            })
+          }else {
+            addMember(params).then(res => {
+              this.cancelMemberForm();
+              this.getList();
+              this.$successMsg('添加成功');
+            })
+          }
+        }
+      })
+    },
+
+    // 表格选择列
+    handleTableSelection(val) {
+      this.tableSelection = val;
+    },
+
+    // 批量删除成员
+    batchDeleteMember() {
+      if(this.tableSelection.length < 1) {
+        return this.$errorMsg('至少选择一名成员');
+      }
+      this.$confirm(`确定删除选中的成员吗?`, '提示', {
+        confirmButtonText: '确定',
+        cancelButtonText: '取消',
+        type: 'warning'
+      }).then(() => {
+        let memberIds = [];
+        this.tableSelection.forEach(item => {
+          memberIds.push(item.id);
+        });
+        deleteMember({id: memberIds.join(',')}).then(res => {
+          this.$successMsg();
+          this.getTree();
+          this.getList();
+        })
+      }).catch(() => {});
+    },
+
+    // 删除成员
+    deleteMember(id) {
+      deleteMember({id: id}).then(res => {
+        this.$successMsg();
+        this.getTree();
+        this.getList();
+      })
+    },
+
+    // 导出
+    handleExport() {
+      let screenData = {
+        adminWebsitId: this.selectDepartment ? this.selectDepartment.websitId : '',
+        keyword: this.screenForm.name
+      };
+      downloadFiles('wechat/enterprise/export', screenData);
+    },
+
+    // 下载导入模版
+    handleDownload() {
+      downloadFiles('wechat/enterprise/download');
+    },
+    // 下载导入删除模板
+    delHandleDownload() {
+      downloadFiles('wechat/enterprise/downloadDeleteExcel');
+    },
+
+    clickImport() {
+      if(!this.selectDepartment) {
+        return this.$errorMsg('请选择部门');
+      }else {
+        document.querySelector('.import-btn input').click();
+      }
+    },
+
+    // 导入
+    async handleImport(param) {
+      this.importLoading = true;
+      const file = param.file;
+      const formData = new FormData();
+      formData.append("file", file);
+      formData.append("mainDepartmentId", this.selectDepartment.websitId);
+      let result = await handleImport('wechat/enterprise/import', formData);
+      this.importLoading = false;
+      this.importFileList = [];
+      if(result.code == 200) {
+        this.$alert(result.message, '导入成功', {
+          confirmButtonText: '确定'
+        });
+        this.getList();
+      }else {
+        this.$alert(result.message, '导入失败', {
+          confirmButtonText: '确定'
+        });
+      }
+    },
+
+    // 导入删除成员
+    async handleImport2(param) {
+      this.importLoading2 = true;
+      const file = param.file;
+      const formData = new FormData();
+      formData.append("file", file);
+      let result = await handleImport('wechat/enterprise/excelDelete', formData);
+      this.importLoading2 = false;
+      this.importFileList2 = [];
+      if(result.code == 200) {
+        this.$alert(result.message, '导入成功', {
+          confirmButtonText: '确定'
+        });
+        this.getList();
+      }else {
+        this.$alert(result.message, '导入失败', {
+          confirmButtonText: '确定'
+        });
+      }
+    },
+
+  }
+}
+</script>
+
+<style scoped lang="scss">
+  .app-container {
+    display: flex;
+    .tree-container {
+      width: 18%;
+      height: calc(100vh - 110px);
+      flex-shrink: 0;
+      background: #f5f5f5;
+      margin-right: 2%;
+      display: flex;
+      flex-direction: column;
+      overflow-y: hidden;
+      .el-tree {
+        height: 100%;
+        background: none;
+        width: 100%;
+        overflow: scroll;
+        // ::v-deep .el-tree-node:focus > .el-tree-node__content {
+        //   color: #ffffff;
+        //   background-color: #409EFF;
+        // }
+        ::v-deep >.el-tree-node {
+          display: inline-block;
+          min-width: 100%;
+        }
+        ::v-deep .el-tree-node>.el-tree-node__content {
+          padding-right: 10px;
+          align-self: baseline;
+        }
+        ::v-deep .el-tree-node.is-current>.el-tree-node__content {
+          background-color: #409EFF;
+          .custom-tree-node {
+            i {
+              color: #fff;
+            }
+            span {
+              color: #fff;
+            }
+          }
+        }
+        ::v-deep .el-tree-node>.el-tree-node__children {
+          overflow: unset;
+        }
+        .custom-tree-node {
+          i {
+            font-size: 14px;
+            color: #999;
+          }
+          span {
+            font-size: 14px;
+            margin-left: 6px;
+            color: #666;
+          }
+        }
+      }
+    }
+    .mymain-container {
+      width: 80%;
+      margin-top: 0;
+    }
+  }
+  ::v-deep .el-divider--vertical {
+    margin: 0 15px;
+  }
+</style>

+ 4 - 4
src/views/merchant/mall_set.vue

@@ -271,12 +271,12 @@ import { getInfo } from '@/api/user'
 export default {
   data() {
     return {
-      isAdmin: JSON.parse(localStorage.getItem("greemall_user")).type === 2,
+      isAdmin: JSON.parse(localStorage.getItem("supply_user")).type === 2,
       baseURL: process.env.VUE_APP_BASE_API,
       myHeaders: {'x-token': getToken()},
       step: 'first',
-      companyId: JSON.parse(localStorage.getItem("greemall_user")).companyWechatId,
-      currentTemplate: JSON.parse(localStorage.getItem("greemall_user")).useTemplate,
+      companyId: JSON.parse(localStorage.getItem("supply_user")).companyWechatId,
+      currentTemplate: JSON.parse(localStorage.getItem("supply_user")).useTemplate,
 
       switch_dialog: true,
       switch_banner: true,
@@ -392,7 +392,7 @@ export default {
         this.getTemplate();
         this.$successMsg('保存成功');
         getInfo(getUserid()).then(response => {
-          localStorage.setItem("greemall_user", JSON.stringify(response.data));
+          localStorage.setItem("supply_user", JSON.stringify(response.data));
         })
       }).finally(res => {
         this.formLoading = false;

+ 1 - 1
src/views/setting/agreement.vue

@@ -176,7 +176,7 @@ export default {
     submitForm() {
       this.formLoading = true;
       editAgreement({
-        companyWechatId: JSON.parse(localStorage.getItem("greemall_user")).companyWechatId,
+        companyWechatId: JSON.parse(localStorage.getItem("supply_user")).companyWechatId,
         userAgreementContent: this.mainForm.content1,
         privacyStatementContent: this.mainForm.content2,
       }).then(res => {

+ 1 - 1
src/views/setting/menu.vue

@@ -23,7 +23,6 @@
           </el-table-column>
           <el-table-column align="center" prop="sortNum" label="排序"></el-table-column>
 
-
           <el-table-column align="right" label="操作" width="150" fixed="right">
             <template slot-scope="scope">
               <el-button type="primary" size="mini" icon="el-icon-plus" v-if="scope.row.level == 1" @click="addOrEditChild('add', scope.row.moduleId)"></el-button>
@@ -650,6 +649,7 @@ export default {
 
     // 操作 - 删除
     handleDelete(id) {
+      console.log(123123);
       deleteMenu({id: id}).then(res => {
         this.getList();
         this.$successMsg();