Browse Source

审核功能上线

yuwenjun 3 years ago
parent
commit
b18d8a1f80

+ 3 - 1
.env.development

@@ -1,8 +1,10 @@
 # just a flag
 ENV = 'development'
 
-# 正式地址 API接口
+# 测试地址 API接口
 VUE_APP_BASE_API = 'https://zplma-b.caimei365.com'
+# VUE_APP_BASE_API = 'http://192.168.2.68:8012'
+
 
 # 文件上传 API接口地址
 VUE_APP_UPLOAD_API='https://zplma-b.caimei365.com'

+ 1 - 0
.eslintignore

@@ -2,3 +2,4 @@ build/*.js
 src/assets
 public
 dist
+

+ 198 - 196
.eslintrc.js

@@ -1,198 +1,200 @@
 module.exports = {
-  root: true,
-  parserOptions: {
-    parser: 'babel-eslint',
-    sourceType: 'module'
-  },
-  env: {
-    browser: true,
-    node: true,
-    es6: true,
-  },
-  extends: ['plugin:vue/recommended', 'eslint:recommended'],
+    root: true,
+    parserOptions: {
+        parser: 'babel-eslint',
+        sourceType: 'module'
+    },
+    env: {
+        browser: true,
+        node: true,
+        es6: true,
+    },
+    extends: ['plugin:vue/recommended', 'eslint:recommended'],
 
-  // add your custom rules here
-  //it is base on https://github.com/vuejs/eslint-config-vue
-  rules: {
-    "vue/max-attributes-per-line": [2, {
-      "singleline": 10,
-      "multiline": {
-        "max": 1,
-        "allowFirstLine": false
-      }
-    }],
-    "vue/singleline-html-element-content-newline": "off",
-    "vue/multiline-html-element-content-newline":"off",
-    "vue/name-property-casing": ["error", "PascalCase"],
-    "vue/no-v-html": "off",
-    'accessor-pairs': 2,
-    'arrow-spacing': [2, {
-      'before': true,
-      'after': true
-    }],
-    'block-spacing': [2, 'always'],
-    'brace-style': [2, '1tbs', {
-      'allowSingleLine': true
-    }],
-    'camelcase': [0, {
-      'properties': 'always'
-    }],
-    'comma-dangle': [2, 'never'],
-    'comma-spacing': [2, {
-      'before': false,
-      'after': true
-    }],
-    'comma-style': [2, 'last'],
-    'constructor-super': 2,
-    'curly': [2, 'multi-line'],
-    'dot-location': [2, 'property'],
-    'eol-last': 2,
-    'eqeqeq': ["error", "always", {"null": "ignore"}],
-    'generator-star-spacing': [2, {
-      'before': true,
-      'after': true
-    }],
-    'handle-callback-err': [2, '^(err|error)$'],
-    'indent': [2, 2, {
-      'SwitchCase': 1
-    }],
-    'jsx-quotes': [2, 'prefer-single'],
-    'key-spacing': [2, {
-      'beforeColon': false,
-      'afterColon': true
-    }],
-    'keyword-spacing': [2, {
-      'before': true,
-      'after': true
-    }],
-    'new-cap': [2, {
-      'newIsCap': true,
-      'capIsNew': false
-    }],
-    'new-parens': 2,
-    'no-array-constructor': 2,
-    'no-caller': 2,
-    'no-console': 'off',
-    'no-class-assign': 2,
-    'no-cond-assign': 2,
-    'no-const-assign': 2,
-    'no-control-regex': 0,
-    'no-delete-var': 2,
-    'no-dupe-args': 2,
-    'no-dupe-class-members': 2,
-    'no-dupe-keys': 2,
-    'no-duplicate-case': 2,
-    'no-empty-character-class': 2,
-    'no-empty-pattern': 2,
-    'no-eval': 2,
-    'no-ex-assign': 2,
-    'no-extend-native': 2,
-    'no-extra-bind': 2,
-    'no-extra-boolean-cast': 2,
-    'no-extra-parens': [2, 'functions'],
-    'no-fallthrough': 2,
-    'no-floating-decimal': 2,
-    'no-func-assign': 2,
-    'no-implied-eval': 2,
-    'no-inner-declarations': [2, 'functions'],
-    'no-invalid-regexp': 2,
-    'no-irregular-whitespace': 2,
-    'no-iterator': 2,
-    'no-label-var': 2,
-    'no-labels': [2, {
-      'allowLoop': false,
-      'allowSwitch': false
-    }],
-    'no-lone-blocks': 2,
-    'no-mixed-spaces-and-tabs': 2,
-    'no-multi-spaces': 2,
-    'no-multi-str': 2,
-    'no-multiple-empty-lines': [2, {
-      'max': 1
-    }],
-    'no-native-reassign': 2,
-    'no-negated-in-lhs': 2,
-    'no-new-object': 2,
-    'no-new-require': 2,
-    'no-new-symbol': 2,
-    'no-new-wrappers': 2,
-    'no-obj-calls': 2,
-    'no-octal': 2,
-    'no-octal-escape': 2,
-    'no-path-concat': 2,
-    'no-proto': 2,
-    'no-redeclare': 2,
-    'no-regex-spaces': 2,
-    'no-return-assign': [2, 'except-parens'],
-    'no-self-assign': 2,
-    'no-self-compare': 2,
-    'no-sequences': 2,
-    'no-shadow-restricted-names': 2,
-    'no-spaced-func': 2,
-    'no-sparse-arrays': 2,
-    'no-this-before-super': 2,
-    'no-throw-literal': 2,
-    'no-trailing-spaces': 2,
-    'no-undef': 2,
-    'no-undef-init': 2,
-    'no-unexpected-multiline': 2,
-    'no-unmodified-loop-condition': 2,
-    'no-unneeded-ternary': [2, {
-      'defaultAssignment': false
-    }],
-    'no-unreachable': 2,
-    'no-unsafe-finally': 2,
-    'no-unused-vars': [2, {
-      'vars': 'all',
-      'args': 'none'
-    }],
-    'no-useless-call': 2,
-    'no-useless-computed-key': 2,
-    'no-useless-constructor': 2,
-    'no-useless-escape': 0,
-    'no-whitespace-before-property': 2,
-    'no-with': 2,
-    'one-var': [2, {
-      'initialized': 'never'
-    }],
-    'operator-linebreak': [2, 'after', {
-      'overrides': {
-        '?': 'before',
-        ':': 'before'
-      }
-    }],
-    'padded-blocks': [2, 'never'],
-    'quotes': [2, 'single', {
-      'avoidEscape': true,
-      'allowTemplateLiterals': true
-    }],
-    'semi': [2, 'never'],
-    'semi-spacing': [2, {
-      'before': false,
-      'after': true
-    }],
-    'space-before-blocks': [2, 'always'],
-    'space-before-function-paren': [2, 'never'],
-    'space-in-parens': [2, 'never'],
-    'space-infix-ops': 2,
-    'space-unary-ops': [2, {
-      'words': true,
-      'nonwords': false
-    }],
-    'spaced-comment': [2, 'always', {
-      'markers': ['global', 'globals', 'eslint', 'eslint-disable', '*package', '!', ',']
-    }],
-    'template-curly-spacing': [2, 'never'],
-    'use-isnan': 2,
-    'valid-typeof': 2,
-    'wrap-iife': [2, 'any'],
-    'yield-star-spacing': [2, 'both'],
-    'yoda': [2, 'never'],
-    'prefer-const': 2,
-    'no-debugger': process.env.NODE_ENV === 'production' ? 2 : 0,
-    'object-curly-spacing': [2, 'always', {
-      objectsInObjects: false
-    }],
-    'array-bracket-spacing': [2, 'never']
-  }
-}
+    // add your custom rules here
+    //it is base on https://github.com/vuejs/eslint-config-vue
+    rules: {
+        // "eslint no-whitespace-before-property": true,
+        "vue/max-attributes-per-line": [2, {
+            "singleline": 10,
+            "multiline": {
+                "max": 1,
+                "allowFirstLine": false
+            }
+        }],
+        "vue/singleline-html-element-content-newline": "off",
+        "vue/multiline-html-element-content-newline": "off",
+        "vue/name-property-casing": ["error", "PascalCase"],
+        "vue/no-v-html": "off",
+        'accessor-pairs': 2,
+        'arrow-spacing': [2, {
+            'before': true,
+            'after': true
+        }],
+        'block-spacing': [2, 'always'],
+        'brace-style': [2, '1tbs', {
+            'allowSingleLine': true
+        }],
+        'camelcase': [0, {
+            'properties': 'always'
+        }],
+        'comma-dangle': [2, 'never'],
+        'comma-spacing': [2, {
+            'before': false,
+            'after': true
+        }],
+        'comma-style': [2, 'last'],
+        'constructor-super': 2,
+        'curly': [2, 'multi-line'],
+        'dot-location': [2, 'property'],
+        'eol-last': 2,
+        'eqeqeq': ["error", "always", { "null": "ignore" }],
+        'generator-star-spacing': [2, {
+            'before': true,
+            'after': true
+        }],
+        'handle-callback-err': [2, '^(err|error)$'],
+        'indent': [2, 2, {
+            'SwitchCase': 1
+        }],
+        // "indent": [4, 4],
+        'jsx-quotes': [2, 'prefer-single'],
+        'key-spacing': [2, {
+            'beforeColon': false,
+            'afterColon': true
+        }],
+        'keyword-spacing': [2, {
+            'before': true,
+            'after': true
+        }],
+        'new-cap': [2, {
+            'newIsCap': true,
+            'capIsNew': false
+        }],
+        'new-parens': 2,
+        'no-array-constructor': 2,
+        'no-caller': 2,
+        'no-console': 'off',
+        'no-class-assign': 2,
+        'no-cond-assign': 2,
+        'no-const-assign': 2,
+        'no-control-regex': 0,
+        'no-delete-var': 2,
+        'no-dupe-args': 2,
+        'no-dupe-class-members': 2,
+        'no-dupe-keys': 2,
+        'no-duplicate-case': 2,
+        'no-empty-character-class': 2,
+        'no-empty-pattern': 2,
+        'no-eval': 2,
+        'no-ex-assign': 2,
+        'no-extend-native': 2,
+        'no-extra-bind': 2,
+        'no-extra-boolean-cast': 2,
+        'no-extra-parens': [2, 'functions'],
+        'no-fallthrough': 2,
+        'no-floating-decimal': 2,
+        'no-func-assign': 2,
+        'no-implied-eval': 2,
+        'no-inner-declarations': [2, 'functions'],
+        'no-invalid-regexp': 2,
+        'no-irregular-whitespace': 2,
+        'no-iterator': 2,
+        'no-label-var': 2,
+        'no-labels': [2, {
+            'allowLoop': false,
+            'allowSwitch': false
+        }],
+        'no-lone-blocks': 2,
+        'no-mixed-spaces-and-tabs': 2,
+        'no-multi-spaces': 2,
+        'no-multi-str': 2,
+        'no-multiple-empty-lines': [2, {
+            'max': 1
+        }],
+        'no-native-reassign': 2,
+        'no-negated-in-lhs': 2,
+        'no-new-object': 2,
+        'no-new-require': 2,
+        'no-new-symbol': 2,
+        'no-new-wrappers': 2,
+        'no-obj-calls': 2,
+        'no-octal': 2,
+        'no-octal-escape': 2,
+        'no-path-concat': 2,
+        'no-proto': 2,
+        'no-redeclare': 2,
+        'no-regex-spaces': 2,
+        'no-return-assign': [2, 'except-parens'],
+        'no-self-assign': 2,
+        'no-self-compare': 2,
+        'no-sequences': 2,
+        'no-shadow-restricted-names': 2,
+        'no-spaced-func': 2,
+        'no-sparse-arrays': 2,
+        'no-this-before-super': 2,
+        'no-throw-literal': 2,
+        'no-trailing-spaces': 2,
+        'no-undef': 2,
+        'no-undef-init': 2,
+        'no-unexpected-multiline': 2,
+        'no-unmodified-loop-condition': 2,
+        'no-unneeded-ternary': [2, {
+            'defaultAssignment': false
+        }],
+        'no-unreachable': 2,
+        'no-unsafe-finally': 2,
+        'no-unused-vars': [2, {
+            'vars': 'all',
+            'args': 'none'
+        }],
+        'no-useless-call': 2,
+        'no-useless-computed-key': 2,
+        'no-useless-constructor': 2,
+        'no-useless-escape': 0,
+        'no-whitespace-before-property': 2,
+        'no-with': 2,
+        'one-var': [2, {
+            'initialized': 'never'
+        }],
+        'operator-linebreak': [2, 'after', {
+            'overrides': {
+                '?': 'before',
+                ':': 'before'
+            }
+        }],
+        'padded-blocks': [2, 'never'],
+        'quotes': [2, 'single', {
+            'avoidEscape': true,
+            'allowTemplateLiterals': true
+        }],
+        'semi': [2, 'never'],
+        'semi-spacing': [2, {
+            'before': false,
+            'after': true
+        }],
+        'space-before-blocks': [2, 'always'],
+        'space-before-function-paren': [2, 'never'],
+        'space-in-parens': [2, 'never'],
+        'space-infix-ops': 2,
+        'space-unary-ops': [2, {
+            'words': true,
+            'nonwords': false
+        }],
+        'spaced-comment': [2, 'always', {
+            'markers': ['global', 'globals', 'eslint', 'eslint-disable', '*package', '!', ',']
+        }],
+        'template-curly-spacing': [2, 'never'],
+        'use-isnan': 2,
+        'valid-typeof': 2,
+        'wrap-iife': [2, 'any'],
+        'yield-star-spacing': [2, 'both'],
+        'yoda': [2, 'never'],
+        'prefer-const': 2,
+        'no-debugger': process.env.NODE_ENV === 'production' ? 2 : 0,
+        'object-curly-spacing': [2, 'always', {
+            objectsInObjects: false
+        }],
+        'array-bracket-spacing': [2, 'never']
+    }
+}

+ 2 - 1
.prettierrc

@@ -1,4 +1,5 @@
 {
   "semi": false,
-  "singleQuote": true
+  "singleQuote": true,
+  "printWidth": 120
 }

+ 10 - 0
README.es.md

@@ -1,3 +1,4 @@
+<<<<<<< HEAD
 ### 分支说明
 
 master:线上版本分支
@@ -5,4 +6,13 @@ master:线上版本分支
 static:测试版本分支
 
 developer:开发分支
+=======
+# 修改说明
+
+#### 2021-06-03
+
+主要:授权机构审核,商品审核功能
+
+其它:修改弹窗样式,修改了代操作模式,对供应商品牌的新增及修改做控制,及部分bug的修复
+>>>>>>> static
 

+ 1 - 1
jsconfig.json

@@ -6,4 +6,4 @@
     }
   },
   "exclude": ["node_modules", "dist"]
-}
+}

+ 9 - 0
src/api/auth.js

@@ -35,3 +35,12 @@ export function removeAuth(data) {
     data
   })
 }
+
+// 审核状态
+export function auditAuth(data) {
+  return request({
+    url: '/auth/audit',
+    method: 'post',
+    data
+  })
+}

+ 9 - 0
src/api/product.js

@@ -44,3 +44,12 @@ export function removeProduct(data) {
     data
   })
 }
+
+// 审核商品 /auth/product/audit
+export function auditProduct(data) {
+  return request({
+    url: '/auth/product/audit',
+    method: 'post',
+    data
+  })
+}

+ 15 - 13
src/components/qrcode/index.vue

@@ -1,16 +1,14 @@
 <template>
   <div class="code-container">
-    <transition name="fade">
-      <div v-if="isVisible" class="qrcode">
-        <div class="title">{{ productInfo.authParty }}</div>
-        <div class="sncode"><span>仪器SN码:</span>{{ hanldeSNcode(productInfo.snCode) }}</div>
-        <div class="content">
-          <img :src="imgUrl" alt="">
-        </div>
-        <div class="btn down-btn" @click="handleDown">下载二维码</div>
-        <div class="btn close-btn" @click="handleClose">关闭</div>
+    <div class="qrcode">
+      <div class="title">{{ productInfo.productName }}</div>
+      <div class="sncode"><span>仪器SN码:</span>{{ hanldeSNcode(productInfo.snCode) }}</div>
+      <div class="content">
+        <img :src="imgUrl" alt="">
       </div>
-    </transition>
+      <div class="btn down-btn" @click="handleDown">下载二维码</div>
+      <div class="btn close-btn" @click="handleClose">关闭</div>
+    </div>
     <canvas id="canvas" style="display:none" />
     <div v-if="isVisible" class="mask" @click="handleClose" />
     <a id="downloadLink" href="#" style="display:none" />
@@ -32,7 +30,7 @@ export default {
     },
     isVisible: {
       type: Boolean,
-      default: false
+      default: true
     }
   },
   data() {
@@ -155,17 +153,21 @@ export default {
 </script>
 
 <style lang="scss" scoped>
+.code-container{
+  position: relative;
+  z-index: 999999;
+}
 .mask{
   position: fixed;
   top: 0;
   left: 0;
-  z-index: 9998;
+  z-index: 999998;
   width: 100vw;
   height: 100vh;
   background: rgba(0,0,0,.5);
 }
 .qrcode{
-  z-index: 9999;
+  z-index: 999999;
   position: fixed;
   left: 50%;
   top: 20%;

+ 7 - 4
src/layout/components/Navbar.vue

@@ -7,7 +7,7 @@
     <div class="right-menu">
       <template v-if="device!=='mobile'">
         <!-- <search id="header-search" class="right-menu-item" /> -->
-
+        <!-- <notice-todo /> -->
         <!-- <error-log class="errLog-container right-menu-item hover-effect" /> -->
 
         <screenfull id="screenfull" class="right-menu-item hover-effect" />
@@ -40,6 +40,7 @@ import Hamburger from '@/components/Hamburger'
 // import ErrorLog from '@/components/ErrorLog'
 import Screenfull from '@/components/Screenfull'
 // import Search from '@/components/HeaderSearch'
+// import NoticeTodo from './NoticeTodo'
 
 export default {
   components: {
@@ -47,6 +48,7 @@ export default {
     Hamburger,
     // ErrorLog,
     Screenfull
+    // NoticeTodo
     // Search
   },
   computed: {
@@ -65,10 +67,11 @@ export default {
       this.$store.dispatch('app/toggleSideBar')
     },
     async logout() {
-      await this.$store.dispatch('user/logout')
-      await this.$store.commit('permission/SET_INITROUTER', false)
       this.$message.success('已退出当前账号')
-      window.location.replace('/#/login')
+      this.$store.dispatch('user/logout')
+      setTimeout(() => {
+        this.$router.replace('/login')
+      }, 500)
     }
   }
 }

+ 184 - 0
src/layout/components/NoticeTodo/index.vue

@@ -0,0 +1,184 @@
+<template>
+  <div class="notice-container">
+    <div class="notice-btn">
+      <span class="el-icon-message-solid" @click="drawer = true" />
+    </div>
+    <el-drawer
+      title="消息通知"
+      :visible.sync="drawer"
+      :with-header="true"
+      :modal="false"
+      size="380px"
+    >
+      <!-- 侧边展开 -->
+      <div class="drawer-content">
+        <el-tabs v-model="activeName" :stretch="true" @tab-click="handleClick">
+          <el-tab-pane label="全部" name="first">
+            <ul>
+              <li class="dot">
+                <time>2021/05/28</time>
+                <span>XX新增了品牌授权信息</span>
+                <a href="#">去审核</a>
+              </li>
+              <li>
+                <time>2021/05/28</time>
+                <span>XX新增了品牌授权信息</span>
+                <a href="#">去审核</a>
+              </li>
+              <li>
+                <time>2021/05/28</time>
+                <span>XX新增了品牌授权信息</span>
+                <a href="#">已审核</a>
+              </li>
+            </ul>
+          </el-tab-pane>
+          <el-tab-pane label="已处理" name="second">
+            <div class="no-notice">
+              <span class="el-icon-message-solid" />
+              <p>暂时没有任何消息</p>
+            </div>
+          </el-tab-pane>
+          <el-tab-pane label="未处理(99+)" class="untreated" name="third">
+            <div class="no-notice">
+              <span class="el-icon-message-solid" />
+              <p>暂时没有任何消息</p>
+            </div>
+          </el-tab-pane>
+        </el-tabs>
+        <!-- 有新消息时的标识或没处理的标识 -->
+        <div class="dot-list">
+          <span v-show="false" class="dot" />
+          <span v-show="false" class="dot" />
+          <span class="dot" />
+          <span class="dot" />
+        </div>
+      </div>
+    </el-drawer>
+  </div>
+</template>
+
+<script>
+
+export default {
+  data() {
+    return {
+      activeName: 'first',
+      drawer: false
+    }
+  },
+  methods: {
+    handleClick() {}
+  }
+}
+</script>
+
+<style lang="scss" scoped>
+.notice-container{
+  display: inline-block;
+  height: 50px;
+  margin-right: 10px;
+  vertical-align: text-bottom;
+}
+.notice-btn {
+  position: relative;
+  cursor: pointer;
+  font-size: 24px;
+  color: #666;
+  &::before{
+    content: "";
+    display: block;
+    position: absolute;
+    width: 6px;
+    height: 6px;
+    background-color: red;
+    border-radius: 50%;
+    top: 10px;
+    right: 0;
+  }
+}
+.drawer-content{
+  line-height: initial;
+  padding: 15px;
+  position: relative;
+  .no-notice{
+    text-align: center;
+    color: #ddd;
+    span{
+      display: inline-block;
+      font-size: 60px;
+      margin: 25px 0 0;
+    }
+  }
+  ul{
+    line-height: 26px;
+    margin: 0;
+    padding-left: 15px;
+    list-style-type: none;
+    li{
+      margin: 0;
+      font-size: 12px;
+      color: #666;
+      position: relative;
+      border-bottom: 1px dashed #ddd;
+      &.dot{
+        &::before{
+          content:"";
+          display: block;
+          position: absolute;
+          width: 4px;
+          height: 4px;
+          border-radius: 2px;
+          left: -10px;
+          top: 10px;
+          background-color: red;
+        }
+      }
+      span{
+        display: inline-block;
+        vertical-align: middle;
+        max-width: 200px;
+        white-space: nowrap;
+        text-overflow: ellipsis;
+        overflow: hidden;
+        margin: 0 10px;
+      }
+      a{
+        color: #409EFF;
+        &:hover{
+          text-decoration: underline;
+        }
+      }
+    }
+  }
+  .dot-list{
+    top: 0;
+    width: 100%;
+    position: absolute;
+    z-index: 99;
+    .dot{
+      position: absolute;
+      display: inline-block;
+      width: 6px;
+      height: 6px;
+      background-color: red;
+      border-radius: 50%;
+      top: 32px;
+      &:nth-child(1){
+        left: 63px;
+      }
+      &:nth-child(2){
+        left: 200px;
+      }
+      &:nth-child(3){
+        left: 346px;
+      }
+      &:nth-child(4){
+        top: -28px;
+        left: 75px;
+      }
+    }
+  }
+
+}
+
+</style>

+ 21 - 0
src/mixin/scrollTo.js

@@ -0,0 +1,21 @@
+import { getStorage } from '@/utils/storage'
+import { scrollTo } from '@/utils/scroll-to'
+
+export default {
+  data() {
+    return {
+      mPath: ''
+    }
+  },
+  created() {
+    this.mPath = this.$route.path
+    this.initPageInfo()
+  },
+  methods: {
+    initPageInfo() {
+      const { listQuery, scrollY } = JSON.parse(getStorage(this.mPath))
+      this.listQuery = listQuery
+      scrollTo(scrollY, 500)
+    }
+  }
+}

+ 23 - 33
src/permission.js

@@ -1,50 +1,49 @@
 import router from './router'
 import store from './store'
 import { Message } from 'element-ui'
-import NProgress from 'nprogress' // progress bar
-import 'nprogress/nprogress.css' // progress bar style
-import { getToken } from '@/utils/auth' // get token from cookie
+import { getToken } from '@/utils/auth'
 import getPageTitle from '@/utils/get-page-title'
 
-NProgress.configure({ showSpinner: false }) // NProgress Configuration
-
 const whiteList = ['/login', '/auth-redirect'] // no redirect whitelist
-const toSupplier = ['/supplier/list', '/supplier', '/supplier/add', '/supplier/edit']
+const toSupplier = ['/supplier/list', '/supplier']
 
-router.beforeEach(async(to, from, next) => {
-  // start progress bar
-  NProgress.start()
+// const onlyPath = ['/auth/list', '/product/list', '/product/add', '/product/edit']
 
-  // set page title
+router.beforeEach(async(to, from, next) => {
+  // 设置页面名称
+  // eslint-disable-next-line indent
   document.title = getPageTitle(to.meta.title)
-
-  // determine whether the user has logged in
+  // 获取token
   const hasToken = getToken()
+
   if (hasToken) {
-    if (toSupplier.includes(to.path)) {
-      store.dispatch('tagsView/delAllViews')
+    /**
+         * 满足要求则关闭所有标签,防止代理数据冲突
+         * 条件:1、sotre中存有代理数据 即 proxyInfo !== null
+         *      2、即将跳转的页面为 /supplier/list 或者 /supplier
+         */
+    if (toSupplier.includes(to.path) && store.getters.proxyInfo !== null) {
+      store.dispatch('tagsView/delAllProxyView')
       store.commit('user/SET_PROXY_INFO', null)
-      next()
+      console.log('关闭其他的标签')
     }
     if (to.path === '/login') {
-      // if is logged in, redirect to the home page
+      // 在登录状态下访问login页面,直接跳转到首页
       next()
-      NProgress.done() // hack: https://github.com/PanJiaChen/vue-element-admin/pull/2939
     } else {
-      // determine whether the user has obtained his permission roles through getInfo
-      // const hasRoles = store.getters.roles && store.getters.roles.length > 0
       // 加载国家列表
       store.dispatch('app/setCountry')
-      const hasInitRouter = store.getters.initRouter
+      const hasInitRouter = store.getters.initRouter // 是否需要初始化路由
       if (hasInitRouter) {
         next()
       } else {
         try {
-          // get user info
-          // note: roles must be a object array! such as: ['admin'] or ,['developer','editor']
+          // 设置路由的初始化状态
           store.commit('permission/SET_INITROUTER', true)
-          // generate accessible routes map based on roles
+
+          // 通过
           const accessRoutes = await store.dispatch('permission/generateRoutes', store.getters.roles)
+
           // dynamically add accessible routes
           router.addRoutes(accessRoutes)
 
@@ -56,7 +55,6 @@ router.beforeEach(async(to, from, next) => {
           await store.dispatch('user/resetToken')
           Message.error(error || 'Has Error')
           next(`/login?redirect=${to.path}`)
-          NProgress.done()
         }
       }
     }
@@ -67,17 +65,9 @@ router.beforeEach(async(to, from, next) => {
       next()
     } else {
       // other pages that do not have permission to access are redirected to the login page.
+      Message({ message: '登录失效,请重新登录!' })
       next(`/login`)
-      // Message.error('登录失效,请重新登录!')
-      // Message({ message: '登录失效,请重新登录!' })
-      // router.replace('/login')
-      NProgress.done()
       return
     }
   }
 })
-
-router.afterEach(() => {
-  // finish progress bar
-  NProgress.done()
-})

+ 48 - 13
src/router/index.js

@@ -24,6 +24,7 @@ import Layout from '@/layout'
     affix: true                  if set true, the tag will affix in the tags-view
     breadcrumb: false            if set false, the item will hidden in breadcrumb(default is true)
     activeMenu: '/example/list'  if set path, the sidebar will highlight the path you set
+    proxy: false
   }
  */
 
@@ -68,8 +69,8 @@ export const constantRoutes = [
   // 首页显示的页面
   {
     path: '/',
-    component: Layout
-    // redirect: '/supplier/list'
+    component: Layout,
+    redirect: '/login'
   },
   // 修改密码
   {
@@ -105,7 +106,6 @@ export const asyncRoutes = [
     redirect: '/supplier/list',
     meta: { title: '供应商管理', icon: 'el-icon-s-custom', roles: ['admin'], noCache: true },
     children: [
-      // admin
       {
         path: 'list',
         component: () => import('@/views/supplier/user/index'),
@@ -134,16 +134,14 @@ export const asyncRoutes = [
     component: Layout,
     alwaysShow: true,
     redirect: '/auth/list',
-    // hidden: 'true',
-    // hidden: store.getters.userIdentity === 1 ? 'true' : 'false',
     name: 'Auth',
-    meta: { title: '授权管理', icon: 'el-icon-s-promotion', roles: ['admin', 'normal'], noCache: true },
+    meta: { title: '授权管理', icon: 'el-icon-s-promotion', roles: ['admin', 'normal'], noCache: true, proxy: true },
     children: [
       {
         path: 'list',
         component: () => import('@/views/supplier/auth/index'),
         name: 'AuthList',
-        meta: { title: '授权列表', icon: 'el-icon-menu', roles: ['admin', 'normal'], noCache: true, affix: true }
+        meta: { title: '授权列表', icon: 'el-icon-menu', roles: ['admin', 'normal'], affix: true, noCache: true, proxy: true }
       }
     ]
   },
@@ -155,32 +153,70 @@ export const asyncRoutes = [
     redirect: '/product/list',
     hidden: true,
     name: 'Auth',
-    meta: { title: '商品管理', icon: 'el-icon-s-shop', roles: ['admin', 'normal'], noCache: true },
+    meta: { title: '商品管理', icon: 'el-icon-s-shop', roles: ['admin', 'normal'], noCache: true, proxy: true },
     children: [
       {
         hidden: true,
         path: 'list',
         component: () => import('@/views/supplier/product/index'),
         name: 'Product',
-        meta: { title: '商品列表', icon: 'el-icon-menu', roles: ['admin', 'normal'], noCache: true }
+        meta: { title: '商品列表', icon: 'el-icon-menu', roles: ['admin', 'normal'], noCache: true, proxy: true }
       },
       {
         hidden: true,
         path: 'add',
         component: () => import('@/views/supplier/product/add'),
         name: 'AddProduct',
-        meta: { title: '添加商品', icon: 'el-icon-menu', roles: ['admin', 'normal'], noCache: false }
+        meta: { title: '添加商品', icon: 'el-icon-menu', roles: ['admin', 'normal'], noCache: true, proxy: true }
       },
       {
         hidden: true,
         path: 'edit',
         component: () => import('@/views/supplier/product/edit'),
         name: 'EditProduct',
-        meta: { title: '修改商品', icon: 'el-icon-menu', roles: ['admin', 'normal'], noCache: false }
+        meta: { title: '修改商品', icon: 'el-icon-menu', roles: ['admin', 'normal'], noCache: true, proxy: true }
+      }
+    ]
+  },
+  // 审核页面
+  {
+    path: '/review',
+    component: Layout,
+    alwaysShow: true,
+    redirect: '/review/list',
+    name: 'Review',
+    meta: { title: '品牌授权审核', icon: 'el-icon-s-check', roles: ['admin'], noCache: true },
+    children: [
+      {
+        path: 'list',
+        component: () => import('@/views/supplier/review/index'),
+        name: 'ReviewList',
+        meta: { title: '审核列表', icon: 'el-icon-menu', roles: ['admin'], noCache: true }
+      },
+      {
+        path: 'auth-list',
+        hidden: true,
+        component: () => import('@/views/supplier/review/authList'),
+        name: 'AuthList',
+        meta: { title: '授权机构审核列表', icon: 'el-icon-menu', roles: ['admin'], noCache: true }
+      },
+      {
+        path: 'shop-list',
+        hidden: true,
+        component: () => import('@/views/supplier/review/shopList'),
+        name: 'ShopList',
+        meta: { title: '商品审核列表', icon: 'el-icon-menu', roles: ['admin'], noCache: true }
+      },
+      {
+        path: 'shop-detail',
+        hidden: true,
+        component: () => import('@/views/supplier/review/shopDetail'),
+        name: 'ShopDetail',
+        meta: { title: '商品审核详情', icon: 'el-icon-menu', roles: ['admin'], noCache: true }
       }
     ]
   },
-  // 404 page must be placed at the end !!!
+  // 404页面
   { path: '*', redirect: '/404', hidden: true }
 ]
 
@@ -193,7 +229,6 @@ const createRouter = () =>
 
 const router = createRouter()
 
-// Detail see: https://github.com/vuejs/vue-router/issues/1234#issuecomment-357941465
 export function resetRouter() {
   const newRouter = createRouter()
   router.matcher = newRouter.matcher // reset router

+ 14 - 0
src/store/modules/tagsView.js

@@ -63,6 +63,16 @@ const mutations = {
         break
       }
     }
+  },
+
+  // 关闭所有可被代理的页面
+  DEL_ALL_PROXY_VIEW: state => {
+    let i = state.visitedViews.length
+    while (i--) {
+      if (state.visitedViews[i].meta?.proxy) {
+        state.visitedViews.splice(i, 1)
+      }
+    }
   }
 }
 
@@ -149,6 +159,10 @@ const actions = {
 
   updateVisitedView({ commit }, view) {
     commit('UPDATE_VISITED_VIEW', view)
+  },
+
+  delAllProxyView({ commit }) {
+    commit('DEL_ALL_PROXY_VIEW')
   }
 }
 

+ 24 - 19
src/store/modules/user.js

@@ -6,11 +6,14 @@ const userInfo = getUser() && JSON.parse(getUser())
 function formatRoles(userIdentity) {
   let roles = []
   switch (userIdentity) {
-    case 1: roles = ['admin']
+    case 1:
+      roles = ['admin']
       break
-    case 2:roles = ['normal']
+    case 2:
+      roles = ['normal']
       break
-    default :roles = []
+    default:
+      roles = []
       break
   }
   return roles
@@ -58,21 +61,23 @@ const actions = {
   login({ commit }, userInfo) {
     const { username, password } = userInfo
     return new Promise((resolve, reject) => {
-      login({ mobileOrName: username.trim(), password: password }).then(response => {
-        const { shopStatus, token, authUserId, userIdentity, name, shopType, brandId } = response.data
-        const roles = formatRoles(userIdentity)
-        commit('SET_TOKEN', token) // 保存token
-        commit('SET_USERINFO', { shopStatus, authUserId, userIdentity, shopType, brandId }) // 保存用户信息
-        commit('SET_ROLES', roles) // 根据用户类型生成角色列表
-        commit('SET_NAME', name) // 保存用户名称
-        // commit('app/SET_IS_REFRESH', false)
-        setToken(token) // cokies保存token
-        setUser(response.data) // cokies保存当前用户信息
-        console.log(response)
-        resolve()
-      }).catch(error => {
-        reject(error)
-      })
+      login({ mobileOrName: username.trim(), password: password })
+        .then(response => {
+          const { shopStatus, token, authUserId, userIdentity, name, shopType, brandId } = response.data
+          const roles = formatRoles(userIdentity)
+          commit('SET_TOKEN', token) // 保存token
+          commit('SET_USERINFO', { shopStatus, authUserId, userIdentity, shopType, brandId }) // 保存用户信息
+          commit('SET_ROLES', roles) // 根据用户类型生成角色列表
+          commit('SET_NAME', name) // 保存用户名称
+          // commit('app/SET_IS_REFRESH', false)
+          setToken(token) // cokies保存token
+          setUser(response.data) // cokies保存当前用户信息
+          console.log(response)
+          resolve()
+        })
+        .catch(error => {
+          reject(error)
+        })
     })
   },
 
@@ -82,6 +87,7 @@ const actions = {
     commit('SET_ROLES', []) // 重置角色权限表
     commit('SET_PROXY_INFO', null)
     commit('SET_NAME', '')
+
     removeToken() // 从cokies中移除token
     resetRouter() // 重置路由
     removeUser() // 从cokies中移除用户信息
@@ -97,7 +103,6 @@ const actions = {
       resolve()
     })
   }
-
 }
 
 export default {

+ 28 - 0
src/styles/index.css

@@ -655,6 +655,10 @@ aside a:hover {
   color: #F56C6C;
 }
 
+.status.warning {
+  color: #E6A23C;
+}
+
 .hidden .el-upload {
   display: none !important;
 }
@@ -662,3 +666,27 @@ aside a:hover {
 .tableHeader th {
   background-color: #f7f7f7 !important;
 }
+
+.el-drawer__header {
+  margin-bottom: 0 !important;
+}
+
+.table-cell .cell {
+  overflow: visible !important;
+}
+
+.table-cell .cell .el-badge {
+  vertical-align: 0;
+}
+
+.el-drawer header span {
+  outline: none;
+}
+
+.el-drawer button {
+  outline: none !important;
+}
+
+.reason {
+  cursor: pointer;
+}

File diff suppressed because it is too large
+ 0 - 0
src/styles/index.min.css


+ 133 - 108
src/styles/index.scss

@@ -4,210 +4,235 @@
 @import './element-ui.scss';
 @import './sidebar.scss';
 @import './btn.scss';
-
 body {
-  height: 100%;
-  -moz-osx-font-smoothing: grayscale;
-  -webkit-font-smoothing: antialiased;
-  text-rendering: optimizeLegibility;
-  font-family: Helvetica Neue, Helvetica, PingFang SC, Hiragino Sans GB, Microsoft YaHei, Arial, sans-serif;
+    height: 100%;
+    -moz-osx-font-smoothing: grayscale;
+    -webkit-font-smoothing: antialiased;
+    text-rendering: optimizeLegibility;
+    font-family: Helvetica Neue, Helvetica, PingFang SC, Hiragino Sans GB, Microsoft YaHei, Arial, sans-serif;
 }
 
 label {
-  font-weight: 700;
+    font-weight: 700;
 }
 
 html {
-  height: 100%;
-  box-sizing: border-box;
+    height: 100%;
+    box-sizing: border-box;
 }
 
 #app {
-  height: 100%;
+    height: 100%;
 }
 
 *,
 *:before,
 *:after {
-  box-sizing: inherit;
+    box-sizing: inherit;
 }
 
 .no-padding {
-  padding: 0px !important;
+    padding: 0px !important;
 }
 
 .padding-content {
-  padding: 4px 0;
+    padding: 4px 0;
 }
 
 a:focus,
 a:active {
-  outline: none;
+    outline: none;
 }
 
 a,
 a:focus,
 a:hover {
-  cursor: pointer;
-  color: inherit;
-  text-decoration: none;
+    cursor: pointer;
+    color: inherit;
+    text-decoration: none;
 }
 
 div:focus {
-  outline: none;
+    outline: none;
 }
 
 .fr {
-  float: right;
+    float: right;
 }
 
 .fl {
-  float: left;
+    float: left;
 }
 
 .pr-5 {
-  padding-right: 5px;
+    padding-right: 5px;
 }
 
 .pl-5 {
-  padding-left: 5px;
+    padding-left: 5px;
 }
 
 .block {
-  display: block;
+    display: block;
 }
 
 .pointer {
-  cursor: pointer;
+    cursor: pointer;
 }
 
 .inlineBlock {
-  display: block;
+    display: block;
 }
 
 .clearfix {
-  &:after {
-    visibility: hidden;
-    display: block;
-    font-size: 0;
-    content: " ";
-    clear: both;
-    height: 0;
-  }
+    &:after {
+        visibility: hidden;
+        display: block;
+        font-size: 0;
+        content: " ";
+        clear: both;
+        height: 0;
+    }
 }
 
 aside {
-  background: #eef1f6;
-  padding: 8px 24px;
-  margin-bottom: 20px;
-  border-radius: 2px;
-  display: block;
-  line-height: 32px;
-  font-size: 16px;
-  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen, Ubuntu, Cantarell, "Fira Sans", "Droid Sans", "Helvetica Neue", sans-serif;
-  color: #2c3e50;
-  -webkit-font-smoothing: antialiased;
-  -moz-osx-font-smoothing: grayscale;
-
-  a {
-    color: #337ab7;
-    cursor: pointer;
-
-    &:hover {
-      color: rgb(32, 160, 255);
+    background: #eef1f6;
+    padding: 8px 24px;
+    margin-bottom: 20px;
+    border-radius: 2px;
+    display: block;
+    line-height: 32px;
+    font-size: 16px;
+    font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen, Ubuntu, Cantarell, "Fira Sans", "Droid Sans", "Helvetica Neue", sans-serif;
+    color: #2c3e50;
+    -webkit-font-smoothing: antialiased;
+    -moz-osx-font-smoothing: grayscale;
+    a {
+        color: #337ab7;
+        cursor: pointer;
+        &:hover {
+            color: rgb(32, 160, 255);
+        }
     }
-  }
 }
 
 //main-container全局样式
 .app-container {
-  padding: 20px;
+    padding: 20px;
 }
 
 .components-container {
-  margin: 30px 50px;
-  position: relative;
+    margin: 30px 50px;
+    position: relative;
 }
 
 .pagination-container {
-  margin-top: 30px;
+    margin-top: 30px;
 }
 
 .text-center {
-  text-align: center
+    text-align: center
 }
 
 .sub-navbar {
-  height: 50px;
-  line-height: 50px;
-  position: relative;
-  width: 100%;
-  text-align: right;
-  padding-right: 20px;
-  transition: 600ms ease position;
-  background: linear-gradient(90deg, rgba(32, 182, 249, 1) 0%, rgba(32, 182, 249, 1) 0%, rgba(33, 120, 241, 1) 100%, rgba(33, 120, 241, 1) 100%);
-
-  .subtitle {
-    font-size: 20px;
-    color: #fff;
-  }
-
-  &.draft {
-    background: #d0d0d0;
-  }
-
-  &.deleted {
-    background: #d0d0d0;
-  }
+    height: 50px;
+    line-height: 50px;
+    position: relative;
+    width: 100%;
+    text-align: right;
+    padding-right: 20px;
+    transition: 600ms ease position;
+    background: linear-gradient(90deg, rgba(32, 182, 249, 1) 0%, rgba(32, 182, 249, 1) 0%, rgba(33, 120, 241, 1) 100%, rgba(33, 120, 241, 1) 100%);
+    .subtitle {
+        font-size: 20px;
+        color: #fff;
+    }
+    &.draft {
+        background: #d0d0d0;
+    }
+    &.deleted {
+        background: #d0d0d0;
+    }
 }
 
 .link-type,
 .link-type:focus {
-  color: #337ab7;
-  cursor: pointer;
-
-  &:hover {
-    color: rgb(32, 160, 255);
-  }
+    color: #337ab7;
+    cursor: pointer;
+    &:hover {
+        color: rgb(32, 160, 255);
+    }
 }
 
 .filter-container {
-  padding-bottom: 10px;
-
-  .filter-item {
-    display: inline-block;
-    vertical-align: middle;
-    margin-bottom: 10px;
-  }
+    padding-bottom: 10px;
+    .filter-item {
+        display: inline-block;
+        vertical-align: middle;
+        margin-bottom: 10px;
+    }
 }
 
 //refine vue-multiselect plugin
 .multiselect {
-  line-height: 16px;
+    line-height: 16px;
 }
 
 .multiselect--active {
-  z-index: 1000 !important;
+    z-index: 1000 !important;
 }
 
-.status{
-  &.success{
-    color: #67C23A;
-  }
-  &.danger{
-    color: #F56C6C;
-  }
+.status {
+    &.success {
+        color: #67C23A;
+    }
+    &.danger {
+        color: #F56C6C;
+    }
+    &.warning {
+        color: #E6A23C;
+    }
 }
 
-
 .hidden {
-  .el-upload {
-    display: none !important;
-  }
+    .el-upload {
+        display: none !important;
+    }
+}
+
+.tableHeader {
+    th {
+        background-color: #f7f7f7 !important;
+    }
 }
 
-.tableHeader{
-  th{
-    background-color: #f7f7f7 !important;
-  }
+// .el-badge__content.is-fixed{
+//   top: 14px !important;
+// }
+.el-drawer__header {
+    margin-bottom: 0 !important;
+}
+
+.table-cell {
+    .cell {
+        overflow: visible !important;
+        .el-badge {
+            vertical-align: 0;
+        }
+    }
+}
+
+.el-drawer {
+    header {
+        span {
+            outline: none;
+        }
+    }
+    button {
+        outline: none !important;
+    }
+}
+
+.reason {
+    cursor: pointer;
 }

+ 21 - 18
src/utils/request.js

@@ -3,6 +3,10 @@ import { Message } from 'element-ui'
 import store from '@/store'
 import { getToken } from '@/utils/auth'
 import router from '@/router'
+import NProgress from 'nprogress' // progress bar
+import 'nprogress/nprogress.css' // progress bar style
+
+NProgress.configure({ showSpinner: false }) // NProgress Configuration
 
 // create an axios instance
 const service = axios.create({
@@ -11,28 +15,24 @@ const service = axios.create({
   timeout: 6000 // request timeout
 })
 
-// request interceptor
+// 请求拦截
 service.interceptors.request.use(
   config => {
-    // do something before request is sent
+    NProgress.start()
     config.headers['Content-Type'] = 'application/json'
     config.data = JSON.stringify(config.data)
     if (store.getters.token) {
-      // let each request carry token
-      // ['X-Token'] is a custom headers key
-      // please modify it according to the actual situation
       config.headers['X-Token'] = getToken()
     }
     return config
   },
   error => {
-    // do something with request error
-    console.log(error) // for debug
+    NProgress.done()
     return Promise.reject(error)
   }
 )
 
-// response interceptor
+// 响应拦截
 service.interceptors.response.use(
   /**
    * If you want to get http information such as headers or status
@@ -46,24 +46,26 @@ service.interceptors.response.use(
    */
   response => {
     const res = response.data
-
     // token失效时
     if (res.code === -99) {
-      Message({ message: '登录失效,请重新登录!' })
-      router.replace('/login')
+      Message({ message: '登录失效,请重新登录!', duration: 1000 })
+      store.dispatch('user/logout')
+      setTimeout(() => {
+        router.replace('/login')
+      }, 500)
+      NProgress.done()
       return
-    }
-
     // 返回不成功
-    if (res.code !== 0) {
+    } else if (res.code !== 0) {
       Message({
-        message: res.msg || 'Error',
+        message: res.msg || '操作失败了,请重试!',
         type: 'error',
-        duration: 5 * 1000
+        duration: 500
       })
-      // return Promise.reject(new Error(res.message || 'Error'))
+      NProgress.done()
       return
     } else {
+      NProgress.done()
       return res
     }
   },
@@ -72,8 +74,9 @@ service.interceptors.response.use(
     Message({
       message: error.message,
       type: 'error',
-      duration: 5 * 1000
+      duration: 500
     })
+    NProgress.done()
     return Promise.reject(error)
   }
 )

+ 1 - 1
src/utils/storage.js

@@ -5,7 +5,7 @@ export function setStorage(key, value) {
 }
 
 export function getStorage(key) {
-  window.localStorage.getItem(key)
+  return window.localStorage.getItem(key)
 }
 
 export function removeStorage(key) {

+ 22 - 0
src/utils/tools.js

@@ -17,3 +17,25 @@ export function throttle(func, wait) {
     }
   }
 }
+
+// 防抖
+export function debounce(func, wait, immediate) {
+  let timeout, result
+  return function() {
+    const context = this
+    const args = arguments
+    if (timeout) clearTimeout(timeout)
+    if (immediate) {
+      const callNow = !timeout
+      timeout = setTimeout(function() {
+        timeout = null
+      }, wait)
+      if (callNow) result = func.apply(context, args)
+    } else {
+      timeout = setTimeout(function() {
+        func.apply(context, args)
+      }, wait)
+    }
+    return result
+  }
+}

+ 2 - 1
src/views/login/index.vue

@@ -22,7 +22,7 @@
         />
       </el-form-item>
 
-      <el-tooltip v-model="capsTooltip" content="Caps lock is On" placement="right" manual>
+      <el-tooltip v-model="capsTooltip" content="大写已开启" placement="right" manual>
         <el-form-item prop="password">
           <span class="svg-container">
             <svg-icon icon-class="password" />
@@ -88,6 +88,7 @@ export default {
   created() {
     // window.addEventListener('storage', this.afterQRScan)
     const isRefresh = this.$store.getters.isRefresh
+    console.log(isRefresh)
     if (!isRefresh) {
       window.location.reload()
     }

+ 3 - 2
src/views/password/index.vue

@@ -80,8 +80,9 @@ export default {
     },
     async logout() {
       await this.$store.dispatch('user/logout')
-      await this.$store.commit('permission/SET_INITROUTER', false)
-      window.location.replace('/#/login')
+      setTimeout(() => {
+        this.$router.replace('/login')
+      }, 500)
     }
   }
 }

+ 111 - 21
src/views/supplier/auth/index.vue

@@ -3,8 +3,36 @@
     <div class="filter-container">
       <span>授权机构:</span>
       <el-input v-model="listQuery.authParty" placeholder="授权机构" style="width: 280px;" class="filter-item" @keyup.enter.native="handleFilter" />
-      <el-button type="primary" @click="getList">查询</el-button>
-      <el-button v-if="userIdentity === 2 || proxyInfo!==null" type="primary" @click="handleShowEditDialog('添加品牌授权')">添加品牌授权</el-button>
+      <span>审核状态:</span>
+      <el-select
+        v-model="listQuery.auditStatus"
+        placeholder="审核状态"
+        clearable
+        style="width: 200px"
+        class="filter-item"
+        @change="getList"
+      >
+        <el-option label="全部" value="" />
+        <el-option label="待审核" :value="2" />
+        <el-option label="审核通过" :value="1" />
+        <el-option label="审核未通过" :value="0" />
+      </el-select>
+      <span>上线状态:</span>
+      <el-select
+        v-model="listQuery.status"
+        placeholder="上线状态"
+        clearable
+        style="width: 200px"
+        class="filter-item"
+        @change="getList"
+      >
+        <el-option label="全部" value="" />
+        <el-option label="已上线" :value="1" />
+        <el-option label="待上线" :value="2" />
+        <el-option label="未上线" :value="0" />
+      </el-select>
+      <el-button icon="el-icon-search" type="primary" @click="getList">查询</el-button>
+      <el-button v-if="userIdentity === 2 || proxyInfo!==null" icon="el-icon-edit" type="primary" @click="handleShowEditDialog('添加品牌授权')">添加品牌授权</el-button>
     </div>
     <!-- 表格区域 -->
     <el-table
@@ -21,15 +49,46 @@
 
       <el-table-column label="授权机构" align="center" prop="authParty" />
 
-      <el-table-column v-if="userIdentity===2 || proxyInfo!==null" label="上线状态" width="140px" align="center">
+      <el-table-column label="审核状态" width="220px" align="center">
+        <template slot-scope="{ row }">
+          <el-tag v-if="row.auditStatus === 2" size="small" type="warning">待审核</el-tag>
+          <el-tag v-if="row.auditStatus === 1" size="small" type="success">审核通过</el-tag>
+          <!-- 未通过原因展示 -->
+          <template v-if="row.auditStatus === 0">
+            <!-- <span class="status danger">审核未通过&nbsp;</span> -->
+            <el-popover
+              placement="top-start"
+              title="审核说明"
+              width="400"
+              trigger="hover"
+              :content="row.invalidReason"
+            >
+              <el-tag slot="reference" size="small" type="danger" class="reason">
+                <span>审核未通过</span>
+                <span class="el-icon-question status danger " />
+              </el-tag>
+            </el-popover>
+            <!-- 未通过原因展示END -->
+          </template>
+        </template>
+      </el-table-column>
+
+      <el-table-column label="上线状态" width="140px" align="center">
         <template slot-scope="{row}">
-          <template v-if="row.status === 0">
-            <span style="margin-right:10px;" class="status danger">已下线</span>
-            <el-button type="primary" size="mini" @click="handleChangeStatus(row)">上线</el-button>
+          <!-- 只有审核通过了才能操作上下线 auditStatus :审核状态 -->
+          <template v-if="row.auditStatus === 1">
+            <template v-if="row.status === 0">
+              <span style="margin-right:10px;" class="status danger">已下线</span>
+              <el-button v-if="userIdentity===2 || proxyInfo!==null" type="primary" size="mini" @click="handleChangeStatus(row)">上线</el-button>
+            </template>
+            <template v-else>
+              <span style="margin-right:10px;" class="status success ">已上线</span>
+              <el-button v-if="userIdentity===2 || proxyInfo!==null" type="info" size="mini" plain @click="handleChangeStatus(row)">下线</el-button>
+            </template>
           </template>
           <template v-else>
-            <span style="margin-right:10px;" class="status success ">已上线</span>
-            <el-button type="info" size="mini" plain @click="handleChangeStatus(row)">下线</el-button>
+            <!-- <el-tag type="warning">待上线</el-tag> -->
+            <span style="margin-right:10px;" class="status warning">待上线</span>
           </template>
         </template>
       </el-table-column>
@@ -73,12 +132,12 @@
         <el-form-item label="授权机构:" prop="authParty">
           <el-input v-model="addAuthFormData.authParty" placeholder="请输入授权机构名称" />
         </el-form-item>
-        <el-form-item label="上线状态:">
+        <!-- <el-form-item label="上线状态:">
           <el-select v-model="addAuthFormData.status">
             <el-option label="上线" :value="1" />
             <el-option label="下线" :value="0" />
           </el-select>
-        </el-form-item>
+        </el-form-item> -->
       </el-form>
       <span slot="footer" class="dialog-footer">
         <el-button @click="showAddAuthDialog = false">取 消</el-button>
@@ -106,6 +165,7 @@ export default {
   },
   data() {
     return {
+      noticeTitle: '添加',
       dialogFlag: true, // 对话框状态
       tableKey: 0,
       list: null,
@@ -116,7 +176,8 @@ export default {
         authParty: '', // 授权机构
         authUserId: '', // 供应商用户id
         pageNum: 1, // 页码
-        pageSize: 10 // 分页
+        pageSize: 10, // 分页
+        status: ''
       },
       // 添加品牌授权
       showAddAuthDialog: false, // 显示添加供应商对话框
@@ -126,14 +187,17 @@ export default {
         authUserId: '', // 供应商用户id
         authParty: '', // 授权机构
         createBy: '', // 创建人id
-        status: 1 // 授权状态 0下架,1上架
+        status: 2 // 授权状态 0下线,1上线  2待审核
       },
       addAuthFormRules: {
         authParty: [
           { required: true, message: '请输入授权机构名称', trigger: 'blur' }
         ]
       },
-      disabled: false
+      disabled: false,
+      // 审核未通过
+      auditFailedList: [],
+      auditNoticeFlag: true
     }
   },
   computed: {
@@ -160,6 +224,8 @@ export default {
         // this.formatList(list)
         this.list = list
         this.total = total
+        // 获取审核未通过的列表
+        this.checkAuditFailedList(list)
       }).catch(err => {
         console.log(err)
         return this.$message.error('授权列表信息获取失败')
@@ -167,6 +233,21 @@ export default {
         this.listLoading = false
       })
     },
+    // 获取审核未通过条数
+    // Audit failed 审核未通过
+    checkAuditFailedList(data) {
+      this.auditFailedList = data.filter(item => item.auditStatus === 0)
+      console.log(this.auditFailedList)
+      if (this.auditFailedList.length > 0 && this.auditNoticeFlag && (this.userIdentity !== 1 || this.proxyInfo !== null)) {
+        this.$notify.info({
+          title: '消息通知',
+          dangerouslyUseHTMLString: true,
+          message: `共有<b style="color:red">${this.auditFailedList.length}</b>个授权机构未能通过审核,请查看原因并及时修改!`,
+          duration: 3000
+        })
+        this.auditNoticeFlag = false
+      }
+    },
     // 检查机构名是否存在 true:存在  false:不存在
     handleCheckAuthName(name) {
       const flag = this.list.some(item => item.authParty === name)
@@ -195,7 +276,12 @@ export default {
               return
             }
             this.getList()
-            this.$message.success(res.data)
+            const h = this.$createElement
+            this.$notify.success({
+              title: `${this.noticeTitle}授权机构`,
+              message: h('i', { style: 'color: #333' }, `已${this.noticeTitle}授权机构:"${this.addAuthFormData.authParty}"`),
+              duration: 3000
+            })
             this.$refs.addAuthForm.resetFields()
           }).catch(err => {
             console.log(err)
@@ -221,9 +307,14 @@ export default {
       // 要执行的操作
       this.listLoading = true
       removeAuth({	authId: item.authId }).then(res => {
-        this.$message.success(res.data)
+        if (res.code !== 0) return
+        const h = this.$createElement
+        this.$notify.success({
+          title: '移除授权机构',
+          message: h('i', { style: 'color: #333' }, `移除授权机构:"${item.authParty}"`),
+          duration: 3000
+        })
       }).catch(err => {
-        this.$message.danger('删除失败')
         console.log(err)
       }).finally(() => {
         this.listLoading = false
@@ -273,23 +364,22 @@ export default {
     },
     // 对话框关闭事件
     dialogClosed() {
+      console.log('dialog is closed')
+      this.addAuthFormData.authParty = ''
       this.addAuthFormData.authId = ''
       this.addAuthFormData.status = 1
+      this.noticeTitle = '添加'
       this.$refs.addAuthForm.resetFields()
     },
     handleShowEditDialog(title, data) {
       this.dialogTitle = title
       if (data) {
-        // authId: '', // 授权id
-        // authUserId: '', // 供应商用户id
-        // authParty: '', // 授权机构
-        // createBy: '', // 创建人id
-        // status: 1
         this.addAuthFormData.authId = data.authId
         this.addAuthFormData.authUserId = data.authUserId
         this.addAuthFormData.authParty = data.authParty
         this.addAuthFormData.createBy = data.createBy
         this.status = data.status
+        this.noticeTitle = '修改'
         this.dialogFlag = false
       } else {
         this.dialogFlag = true

+ 13 - 5
src/views/supplier/components/uploadFile.vue

@@ -13,6 +13,7 @@
       :accept="accept"
       :before-upload="beforeUpload"
       :on-remove="remove"
+      :on-change="change"
     >
       <el-button slot="trigger" size="mini" type="primary">选取文件</el-button>
       <!-- <el-button style="margin-left: 10px;" size="mini" type="success" @click="uploadFile">上传</el-button> -->
@@ -81,14 +82,21 @@ export default {
     // 文件上传之前的钩子
     beforeUpload(file) {
       this.params.authUserId = this.authUserId || -1
-      // const size = file.size
-      // if (size > 1024 * 2000) {
-      //   this.$message.warning('文件上传大小超出限制(≤2MB)')
-      //   return false
-      // }
+      const size = file.size
+      if (size > 1024 * 5000) {
+        const h = this.$createElement
+        this.$notify.info({
+          title: '上传文件过大',
+          message: h('p', { style: 'color: #333' }, '文件上传保存需要一定的时间,请您耐心等待,在此期间请勿执执行其他操作,以免影响文件上传失败!'),
+          duration: 5000
+        })
+      }
     },
     remove() {
       this.$emit('remove')
+    },
+    change() {
+      this.$emit('change')
     }
   }
 }

+ 11 - 7
src/views/supplier/product/add.vue

@@ -61,7 +61,7 @@
           @click="handleAddParam"
         >添加参数</el-button>
       </el-form-item>
-      <el-form-item label="上线状态:">
+      <!-- <el-form-item label="上线状态:">
         <el-select
           v-model="formData.status"
           placeholder="上线状态"
@@ -70,7 +70,7 @@
           <el-option label="上线" :value="1" />
           <el-option label="下线" :value="0" />
         </el-select>
-      </el-form-item>
+      </el-form-item> -->
     </el-form>
     <div class="submit-btn">
       <el-button type="primary" @click="submit">保存</el-button>
@@ -115,7 +115,7 @@ export default {
         productImage: '', //	商品图片
         productName: '', //	商品名称
         snCode: '', //	商品SN码
-        status: 1, //	上架状态:0下架,1上架
+        status: 2, //	上架状态:0下线,1上线 2待审核
         brandId: ''
       },
       rules: {
@@ -165,12 +165,16 @@ export default {
       this.formData.createBy = this.proxyInfo?.authUserId || this.authUserId
       this.formData.authUserId = this.proxyInfo?.authUserId || this.authUserId
       saveProduct(this.formData).then(res => {
-        if (res.code !== 0) {
-          return
-        }
-        this.$message.success('保存成功')
+        if (res.code !== 0) return
+        const h = this.$createElement
+        this.$notify.success({
+          title: '新增商品',
+          message: h('i', { style: 'color: #333' }, `已添加商品:"${this.formData.productName}"`),
+          duration: 2000
+        })
         this.$refs.addFormRef.resetFields()
         this.clearFormData()
+        this.$store.dispatch('tagsView/delView', this.$route)
         this.$router.push(`/product/list?id=${this.formData.authId}`)
       }).finally(() => {
         this.isLoading = false

+ 10 - 5
src/views/supplier/product/edit.vue

@@ -60,7 +60,7 @@
           @click="handleAddParam"
         >添加参数</el-button>
       </el-form-item>
-      <el-form-item label="上线状态:">
+      <!-- <el-form-item label="上线状态:">
         <el-select
           v-model="formData.status"
           placeholder="上架状态"
@@ -69,7 +69,7 @@
           <el-option label="上线" :value="1" />
           <el-option label="下线" :value="0" />
         </el-select>
-      </el-form-item>
+      </el-form-item>-->
     </el-form>
     <div class="submit-btn">
       <el-button type="primary" @click="submit">保存</el-button>
@@ -100,7 +100,6 @@ export default {
         productImage: '', //	商品图片
         productName: '', //	商品名称
         snCode: '', //	商品SN码
-        status: 1, //	上架状态:0下架,1上架
         brandId: ''
       },
       brandList: [],
@@ -184,8 +183,14 @@ export default {
       this.formData.createBy = this.proxyInfo?.authUserId || this.authUserId
       this.formData.authUserId = this.proxyInfo?.authUserId || this.authUserId
       saveProduct(this.formData).then(res => {
-        console.log(res)
-        this.$message.success(res.data)
+        if (res.code !== 0) return
+        const h = this.$createElement
+        this.$notify.success({
+          title: '修改商品',
+          message: h('i', { style: 'color: #333' }, `已修改商品:"${this.formData.productName}"`),
+          duration: 2000
+        })
+        this.$store.dispatch('tagsView/delView', this.$route)
         this.$router.back()
       }).finally(() => {
         this.isLoading = false

+ 109 - 17
src/views/supplier/product/index.vue

@@ -1,12 +1,40 @@
 <template>
   <div class="app-container">
     <div class="filter-container">
-      <span>授权机构:</span>
-      <el-input v-model="listQuery.title" placeholder="授权机构" style="width: 200px;" class="filter-item" @keyup.enter.native="handleFilter" />
+      <span>商品名称:</span>
+      <el-input v-model="listQuery.productName" placeholder="商品名称" style="width: 200px;" class="filter-item" @keyup.enter.native="handleFilter" />
       <span>商品SN码:</span>
       <el-input v-model="listQuery.snCode" placeholder="商品SN码" style="width: 200px;" class="filter-item" @keyup.enter.native="handleFilter" />
-      <el-button type="primary" @click="handleFilter">查询</el-button>
-      <el-button v-if="userIdentity === 2 || proxyInfo !== null" type="primary" @click="$_navigationTo(`add?id=${listQuery.authId}`)">添加商品</el-button>
+      <span>审核状态:</span>
+      <el-select
+        v-model="listQuery.auditStatus"
+        placeholder="审核状态"
+        clearable
+        style="width: 200px"
+        class="filter-item"
+        @change="getList"
+      >
+        <el-option label="全部" value="" />
+        <el-option label="待审核" :value="2" />
+        <el-option label="审核通过" :value="1" />
+        <el-option label="审核未通过" :value="0" />
+      </el-select>
+      <span>上线状态:</span>
+      <el-select
+        v-model="listQuery.status"
+        placeholder="上线状态"
+        clearable
+        style="width: 200px"
+        class="filter-item"
+        @change="getList"
+      >
+        <el-option label="全部" value="" />
+        <el-option label="已上线" :value="1" />
+        <el-option label="待上线" :value="2" />
+        <el-option label="未上线" :value="0" />
+      </el-select>
+      <el-button type="primary" icon="el-icon-search" @click="handleFilter">查询</el-button>
+      <el-button v-if="userIdentity === 2 || proxyInfo !== null" icon="el-icon-edit" type="primary" @click="$_navigationTo(`add?id=${listQuery.authId}`)">添加商品</el-button>
     </div>
     <!-- 表格区域 -->
     <el-table
@@ -22,15 +50,47 @@
       <el-table-column label="序号" type="index" align="center" width="80" />
       <el-table-column label="商品名称" align="center" prop="productName" />
       <el-table-column label="商品SN码" align="center" prop="snCode" />
-      <el-table-column v-if="userIdentity===2 || proxyInfo !== null" label="上线状态" width="140px" align="center">
+
+      <el-table-column label="审核状态" width="220px" align="center">
+        <template slot-scope="{ row }">
+          <el-tag v-if="row.auditStatus === 2" size="small" type="warning">待审核</el-tag>
+          <el-tag v-if="row.auditStatus === 1" size="small" type="success">审核通过</el-tag>
+          <!-- 未通过原因展示 -->
+          <template v-if="row.auditStatus === 0">
+            <!-- <span class="status danger">审核未通过&nbsp;</span> -->
+            <el-popover
+              placement="top-start"
+              title="审核说明"
+              width="400"
+              trigger="hover"
+              :content="row.invalidReason"
+            >
+              <el-tag slot="reference" size="small" type="danger" class="reason">
+                <span>审核未通过</span>
+                <span class="el-icon-question status danger " />
+              </el-tag>
+            </el-popover>
+            <!-- 未通过原因展示END -->
+          </template>
+        </template>
+      </el-table-column>
+
+      <el-table-column label="上线状态" width="140px" align="center">
         <template slot-scope="{row}">
-          <template v-if="row.status === 0">
-            <span style="margin-right:10px;" class="status danger">已下线</span>
-            <el-button type="primary" size="mini" @click="handleChangeStatus(row)">上线</el-button>
+          <!-- 只有审核通过了才能操作上下线 auditStatus :审核状态 -->
+          <template v-if="row.auditStatus === 1">
+            <template v-if="row.status === 0">
+              <span style="margin-right:10px;" class="status danger">已下线</span>
+              <el-button v-if="userIdentity===2 || proxyInfo !== null" type="primary" size="mini" @click="handleChangeStatus(row)">上线</el-button>
+            </template>
+            <template v-else>
+              <span style="margin-right:10px;" class="status success ">已上线</span>
+              <el-button v-if="userIdentity===2 || proxyInfo !== null" type="info" size="mini" plain @click="handleChangeStatus(row)">下线</el-button>
+            </template>
           </template>
           <template v-else>
-            <span style="margin-right:10px;" class="status success ">已上线</span>
-            <el-button type="info" size="mini" plain @click="handleChangeStatus(row)">下线</el-button>
+            <!-- <el-tag type="warning">待上线</el-tag> -->
+            <span style="margin-right:10px;" class="status warning">待上线</span>
           </template>
         </template>
       </el-table-column>
@@ -50,7 +110,10 @@
               删除
             </el-button>
           </template>
-          <el-button type="primary" size="mini" @click="handleShowQRcode(row)">
+          <el-button v-if="row.auditStatus === 1" type="primary" size="mini" @click="handleShowQRcode(row)">
+            二维码
+          </el-button>
+          <el-button v-else type="info" size="mini" disabled>
             二维码
           </el-button>
         </template>
@@ -61,7 +124,9 @@
     <pagination v-show="total>0" :total="total" :page.sync="listQuery.pageNum" :limit.sync="listQuery.pageSize" @pagination="getList" />
 
     <!-- 二维码 -->
-    <qrcode v-if="showQRcode" :is-visible="showQRcode" :product-info="productInfo" @close="showQRcode = false" />
+    <transition name="fade">
+      <qrcode v-if="showQRcode" :product-info="productInfo" @close="showQRcode = false" />
+    </transition>
   </div>
 </template>
 
@@ -91,6 +156,8 @@ export default {
       total: 0,
       listLoading: true,
       listQuery: {
+        status: '',
+        auditStatus: '',
         authId: '',
         productName: '',
         snCode: '',
@@ -98,7 +165,10 @@ export default {
         pageSize: 10
       },
       showQRcode: false,
-      productInfo: {}
+      productInfo: {},
+      // 审核未通过
+      auditFailedList: [],
+      auditNoticeFlag: true
     }
   },
   computed: {
@@ -122,8 +192,10 @@ export default {
     // 获取列表信息
     getList() {
       getProdList(this.listQuery).then(res => {
-        this.total = res.data.total
-        this.list = res.data.list
+        const { total, list } = res.data
+        this.total = total
+        this.list = list
+        this.checkAuditFailedList(list)
       }).finally(() => {
         this.listLoading = false
       })
@@ -154,7 +226,7 @@ export default {
     },
     // 删除商品
     async handleRemoveProduct(item) {
-      const text = await this.$confirm('此操作将删除该授权机构, 是否继续?', '提示', {
+      const text = await this.$confirm('此操作将删除该商品, 是否继续?', '提示', {
         confirmButtonText: '确定',
         cancelButtonText: '取消',
         type: 'warning'
@@ -164,7 +236,12 @@ export default {
       if (text !== 'confirm') return
 
       removeProduct({ productId: item.productId }).then(res => {
-        this.$message.success(res.data)
+        const h = this.$createElement
+        this.$notify.success({
+          title: '删除商品',
+          message: h('i', { style: 'color: #333' }, `已删除商品:"${item.productName}"`),
+          duration: 2000
+        })
       }).finally(() => {
         this.getList()
       })
@@ -174,6 +251,21 @@ export default {
       this.productInfo = item
       this.productInfo.authParty = this.authParty
       this.showQRcode = true
+    },
+    // 获取审核未通过条数
+    // Audit failed 审核未通过
+    checkAuditFailedList(data) {
+      this.auditFailedList = data.filter(item => item.auditStatus === 0)
+      console.log(this.auditFailedList)
+      if (this.auditFailedList.length > 0 && this.auditNoticeFlag && (this.userIdentity !== 1 || this.proxyInfo !== null)) {
+        this.$notify.info({
+          title: '消息通知',
+          dangerouslyUseHTMLString: true,
+          message: `共有<b style="color:red">${this.auditFailedList.length}</b>件商品未能通过审核,请查看原因并及时修改!`,
+          duration: 3000
+        })
+        this.auditNoticeFlag = false
+      }
     }
   }
 }

+ 275 - 0
src/views/supplier/review/authList.vue

@@ -0,0 +1,275 @@
+<template>
+  <div class="app-container">
+    <!-- 搜索区域 -->
+    <div class="filter-container">
+      <span>授权机构名称:</span>
+      <el-input
+        v-model="listQuery.authParty"
+        placeholder="授权机构名称"
+        style="width: 200px"
+        class="filter-item"
+        @keyup.enter.native="getList"
+      />
+      <span>审核状态:</span>
+      <el-select
+        v-model="listQuery.auditStatus"
+        placeholder="审核状态"
+        clearable
+        style="width: 200px"
+        class="filter-item"
+        @change="getList"
+      >
+        <el-option label="全部" value="" />
+        <el-option label="待审核" :value="2" />
+        <el-option label="审核通过" :value="1" />
+        <el-option label="审核未通过" :value="0" />
+      </el-select>
+      <span>商品信息审核状态:</span>
+      <el-select
+        v-model="listQuery.lowerAuditStatus"
+        placeholder="供应商类型"
+        clearable
+        style="width: 200px"
+        class="filter-item"
+        @change="getList"
+      >
+        <el-option label="全部" value="" />
+        <el-option label="已完成审核" :value="1" />
+        <el-option label="未完成审核" :value="0" />
+      </el-select>
+      <el-button type="primary" icon="el-icon-search" @click="getList">查询</el-button>
+    </div>
+    <!-- 搜索区域END -->
+    <!-- 表格区域 -->
+    <el-table
+      v-loading="listLoading"
+      :data="list"
+      style="width: 100%"
+      border
+      fit
+      highlight-current-row
+      cell-class-name="table-cell"
+    >
+      <el-table-column label="序号" type="index" width="80" align="center" />
+      <el-table-column prop="authParty" label="授权机构" align="center" />
+      <el-table-column label="审核状态" width="220px" align="center">
+        <template slot-scope="{ row }">
+          <el-tag v-if="row.auditStatus === 2" size="small" type="warning">待审核</el-tag>
+          <el-tag v-if="row.auditStatus === 1" size="small" type="success">审核通过</el-tag>
+          <!-- 未通过原因展示 -->
+          <template v-if="row.auditStatus === 0">
+            <!-- <span class="status danger">审核未通过&nbsp;</span> -->
+            <el-popover
+              placement="top-start"
+              title="审核说明"
+              width="400"
+              trigger="hover"
+              :content="row.invalidReason"
+            >
+              <el-tag slot="reference" size="small" type="danger" class="reason">
+                <span>审核未通过</span>
+                <span class="el-icon-question status danger " />
+              </el-tag>
+            </el-popover>
+            <!-- 未通过原因展示END -->
+          </template>
+        </template>
+      </el-table-column>
+      <el-table-column label="商品信息审核状态" width="220px" align="center">
+        <template slot-scope="{ row }">
+          <el-tag v-if="row.lowerAuditStatus === 0" size="small" type="danger">未完成审核</el-tag>
+          <el-tag v-if="row.lowerAuditStatus === 1" size="small" type="success">已完成审核</el-tag>
+        </template>
+      </el-table-column>
+
+      <el-table-column label="审核时间" width="250px" align="center">
+        <template slot-scope="{row}">
+          <span v-if="row.auditStatus!==2">{{ row.auditTime | formatTime }}</span>
+          <span v-else>—</span>
+        </template>
+      </el-table-column>
+
+      <el-table-column label="审核人" align="center" width="200px">
+        <template slot-scope="{row}">
+          <span v-if="row.auditStatus!==2">{{ row.auditBy }}</span>
+          <span v-else>—</span>
+        </template>
+      </el-table-column>
+
+      <el-table-column label="操作" width="240px" align="center">
+        <template slot-scope="{ row }">
+          <el-button
+            v-if="row.auditStatus === 2"
+            type="warning"
+            size="mini"
+            style="margin-right:5px"
+            icon="el-icon-s-check"
+            @click="handleShowDialog(row)"
+          >审核</el-button>
+          <el-badge :hidden="row.lowerAuditStatus === 1" :value="row.waitAuditNum" :max="99">
+            <el-button icon="el-icon-s-shop" type="primary" size="mini" @click="$_navigationTo(`shop-list?authId=${row.authId}`)">商品信息审核</el-button>
+          </el-badge>
+        </template>
+      </el-table-column>
+    </el-table>
+    <!-- 表格区域END -->
+    <!-- 页码 -->
+    <pagination v-show="total>0" :total="total" :page.sync="listQuery.pageNum" :limit.sync="listQuery.pageSize" @pagination="getList" />
+    <!-- 审核弹窗 -->
+    <el-dialog title="授权机构审核" :visible.sync="dialogVisible" width="450px" @close="dialogClosed">
+      <div class="auth-info">
+        <div class="auth-name">
+          <i>授权机构:</i>
+          <b>{{ dialogData.authParty }}</b>
+        </div>
+        <el-form ref="formRef" :model="dialogData" label-width="85px" :rules="dialogFormRules">
+          <el-form-item label="审核状态:">
+            <el-radio-group v-model="dialogData.auditStatus">
+              <el-radio :label="1">通过</el-radio>
+              <el-radio :label="0">不通过</el-radio>
+            </el-radio-group>
+          </el-form-item>
+          <el-form-item v-if="dialogData.auditStatus === 0" label="原因:" prop="invalidReason">
+            <el-input v-model="dialogData.invalidReason" type="textarea" placeholder="请说明原因" />
+          </el-form-item>
+        </el-form>
+      </div>
+      <div slot="footer">
+        <el-button @click="dialogVisible = false">取 消</el-button>
+        <el-button type="primary" @click="auditStatusHandle">确 定</el-button>
+      </div>
+    </el-dialog>
+  </div>
+</template>
+
+<script>
+import Pagination from '@/components/Pagination'
+import { fecthAuthList, auditAuth } from '@/api/auth'
+import { formatDate } from '@/utils'
+import { mapGetters } from 'vuex'
+export default {
+  components: { Pagination },
+  filters: {
+    formatTime(time) {
+      if (!time) {
+        return ''
+      }
+      return formatDate(time, 'yyyy-MM-DD HH:mm:ss')
+    }
+  },
+  data() {
+    return {
+      // 是否显示dialog
+      dialogVisible: false,
+      listLoading: false,
+      // 查询参数
+      listQuery: {
+        listType: 2,
+        authParty: '', // 授权机构
+        authUserId: '', // 供应商用户id
+        pageNum: 1, // 页码
+        pageSize: 10, // 分页
+        auditStatus: '', // 审核状态
+        lowerAuditStatus: '' // 下属内容审核状态
+      },
+      total: 0,
+      dialogData: {
+        auditBy: '', // 审核人
+        authId: '', // 授权机构id
+        authParty: '', // 授权机构名称
+        auditStatus: 1, // 审核状态
+        invalidReason: '' // 审核信息
+      },
+      dialogFormRules: {
+        invalidReason: {
+          required: true,
+          message: '不通过原因不能为空',
+          tigger: 'blur'
+        }
+      },
+      // 机构信息审核列表
+      list: []
+    }
+  },
+  computed: {
+    ...mapGetters(['authUserId'])
+  },
+  created() {
+    this.listQuery.authUserId = this.$route.query.authUserId
+    this.getList()
+  },
+  methods: {
+    // 获取授权列表
+    getList() {
+      this.listLoading = true
+      fecthAuthList(this.listQuery).then(response => {
+        if (response.code !== 0) return
+        const { list, total } = response.data
+        this.list = list
+        this.total = total
+      }).finally(() => {
+        this.listLoading = false
+      })
+    },
+    // 审核
+    auditStatusHandle() {
+      this.$refs.formRef.validate(valid => {
+        if (valid) {
+          // 指定审核人
+          this.dialogData.auditBy = this.authUserId
+          // 提交审核信息
+          auditAuth(this.dialogData).then(res => {
+            if (res.code !== 0) return
+            this.$message.success(res.data)
+          }).finally(() => {
+            this.dialogVisible = false
+            this.getList()
+          })
+        }
+      })
+    },
+    // 审核对话框
+    handleShowDialog(item) {
+      console.log(item)
+      this.dialogData.authParty = item.authParty
+      this.dialogData.authId = item.authId
+      this.dialogVisible = true
+    },
+    // 审核对话框关闭
+    dialogClosed() {
+      this.dialogData.authParty = ''
+      this.dialogData.reviewStatus = 1
+    }
+  }
+}
+</script>
+
+<style lang="scss" scoped>
+.filter-container {
+  span {
+    display: inline-block;
+    margin-bottom: 10px;
+    vertical-align: middle;
+    font-size: 14px;
+  }
+  .el-button {
+    display: inline-block;
+    margin-bottom: 10px;
+    vertical-align: middle;
+  }
+  .el-input,
+  .el-select {
+    margin-right: 10px;
+    margin-left: 10px;
+  }
+}
+
+.auth-info {
+  .auth-name {
+    font-size: 16px;
+    padding-bottom: 25px;
+    border-bottom: 1px solid #ddd;
+    margin-bottom: 25px;
+  }
+}
+</style>

+ 177 - 0
src/views/supplier/review/index.vue

@@ -0,0 +1,177 @@
+<template>
+  <div class="app-container">
+    <!-- 搜索区域 -->
+    <div class="filter-container">
+      <span>供应商名称:</span>
+      <el-input
+        v-model="listQuery.shopName"
+        placeholder="供应商名称"
+        style="width: 200px"
+        class="filter-item"
+        @keyup.enter.native="getList"
+      />
+      <span>供应商类型:</span>
+      <el-select
+        v-model="listQuery.shopType"
+        placeholder="供应商类型"
+        clearable
+        style="width: 200px"
+        class="filter-item"
+        @change="getList"
+      >
+        <el-option label="所有类型" value="" />
+        <el-option label="代理商" :value="2" />
+        <el-option label="品牌方" :value="1" />
+      </el-select>
+      <span>手机号:</span>
+      <el-input
+        v-model="listQuery.mobile"
+        placeholder="手机号"
+        style="width: 200px"
+        class="filter-item"
+        @keyup.enter.native="getList"
+      />
+      <span>审核状态:</span>
+      <el-select
+        v-model="listQuery.lowerAuditStatus"
+        placeholder="供应商类型"
+        clearable
+        style="width: 200px"
+        class="filter-item"
+        @change="getList"
+      >
+        <el-option label="全部" value="" />
+        <el-option label="已完成审核" :value="1" />
+        <el-option label="未完成审核" :value="0" />
+      </el-select>
+      <span>联系人:</span>
+      <el-input
+        v-model="listQuery.linkMan"
+        placeholder="联系人"
+        style="width: 200px"
+        class="filter-item"
+        @keyup.enter.native="getList"
+      />
+      <el-button type="primary" icon="el-icon-search" @click="getList">查询</el-button>
+    </div>
+    <!-- 搜索区域END -->
+    <!-- 表格区域 -->
+    <el-table
+      v-loading="listLoading"
+      :data="list"
+      style="width: 100%"
+      border
+      fit
+      highlight-current-row
+      cell-class-name="table-cell"
+    >
+      <el-table-column label="序号" type="index" width="80" align="center" />
+      <el-table-column prop="name" label="供应商名称" align="center" />
+      <el-table-column label="供应商类型" width="150px" align="center">
+        <template slot-scope="{ row }">
+          <span v-if="row.shopType === 1">品牌方</span>
+          <span v-if="row.shopType === 2">代理商</span>
+        </template>
+      </el-table-column>
+      <el-table-column prop="mobile" label="手机号" width="200px" align="center" />
+      <el-table-column prop="linkMan" label="联系人" width="200px" align="center" />
+      <el-table-column label="审核状态" width="220px" align="center">
+        <template slot-scope="{ row }">
+          <el-tag v-if="row.lowerAuditStatus === 0" size="small" type="danger">未完成审核</el-tag>
+          <el-tag v-if="row.lowerAuditStatus === 1" size="small" type="success">已完成审核</el-tag>
+        </template>
+      </el-table-column>
+      <el-table-column label="操作" width="240px" align="center">
+        <template slot-scope="{ row }">
+          <el-badge :hidden="row.lowerAuditStatus === 1" :value="row.waitAuditNum" :max="99">
+            <el-button
+              type="primary"
+              icon="el-icon-s-check"
+              size="mini"
+              @click="$_navigationTo(`auth-list?authUserId=${row.authUserId}`)"
+            >品牌授权信息审核</el-button>
+          </el-badge>
+        </template>
+      </el-table-column>
+    </el-table>
+    <!-- 表格区域END -->
+    <!-- 页码 -->
+    <pagination
+      v-show="total > 0"
+      :total="total"
+      :page.sync="listQuery.pageNum"
+      :limit.sync="listQuery.pageSize"
+      @pagination="getList(listQuery)"
+    />
+  </div>
+</template>
+
+<script>
+import { fetchSupplierList } from '@/api/supplier'
+import Pagination from '@/components/Pagination'
+export default {
+  components: { Pagination },
+  data() {
+    return {
+      listQuery: {
+        listType: 2,
+        brandId: '', // 品牌id
+        linkMan: '', // 联系人
+        mobile: '', // 手机号
+        pageNum: 0, // 页码
+        pageSize: 20, // 分页大小
+        shopName: '', // 供应商名称
+        shopType: '', // 供应商类型
+        lowerAuditStatus: ''
+      },
+      listLoading: false,
+      list: [],
+      total: 0
+    }
+  },
+  created() {
+    this.getList()
+  },
+  methods: {
+    // 过滤列表
+    handleFilter() {},
+    // 获取供应商列表
+    getList() {
+      this.listLoading = true
+      fetchSupplierList(this.listQuery)
+        .then(res => {
+          if (res.code !== 0) return
+          this.list = res.data.list
+          this.total = res.data.total
+        })
+        .finally(() => {
+          this.listLoading = false
+        })
+    }
+  }
+}
+</script>
+
+<style lang="scss" scoped>
+.filter-container {
+  span {
+    display: inline-block;
+    margin-bottom: 10px;
+    vertical-align: middle;
+    font-size: 14px;
+  }
+  .el-button {
+    display: inline-block;
+    margin-bottom: 10px;
+    vertical-align: middle;
+  }
+  .el-input,
+  .el-select {
+    margin-right: 10px;
+    margin-left: 10px;
+  }
+}
+.el-table .cell {
+  overflow: visible;
+}
+</style>

+ 138 - 0
src/views/supplier/review/shopDetail.vue

@@ -0,0 +1,138 @@
+<template>
+  <div v-loading="isLoading" class="shop-detail">
+    <el-form v-if="product!==null" ref="formRef" :model="formData" :rules="formRules" label-width="120px">
+      <el-form-item label="商品名称:">
+        <span>{{ product.productName }}</span>
+      </el-form-item>
+      <el-form-item label="商品SN码:">
+        <span>{{ product.snCode }}</span>
+      </el-form-item>
+      <el-form-item label="商品图片:">
+        <el-image
+          style="width: 140px; height: 140px"
+          :src="product.productImage"
+          :preview-src-list="imgList"
+        />
+      </el-form-item>
+      <el-form-item label="授权牌:">
+        <el-image
+          style="width: 140px; height: 140px"
+          :src="product.certificateImage"
+          :preview-src-list="imgList"
+        />
+      </el-form-item>
+      <template v-if="product.paramList.length>0">
+        <el-form-item label="相关参数:">
+          <table>
+            <tr v-for="(params,index) in product.paramList" :key="index">
+              <td>{{ params.paramName }}:</td>
+              <td>{{ params.paramContent }}</td>
+            </tr>
+          </table>
+        </el-form-item>
+      </template>
+
+      <el-form-item label="审核状态:">
+        <el-radio-group v-model="formData.auditStatus">
+          <el-radio :label="1">通过</el-radio>
+          <el-radio :label="0">不通过</el-radio>
+        </el-radio-group>
+      </el-form-item>
+      <el-form-item v-if="formData.auditStatus!==1" prop="invalidReason" label="原因:">
+        <el-input v-model="formData.invalidReason" type="textarea" placeholder="请说明原因" />
+      </el-form-item>
+      <el-form-item>
+        <el-button type="info" @click="$_back">返回</el-button>
+        <el-button type="primary" @click="submit">提交</el-button>
+      </el-form-item>
+    </el-form>
+  </div>
+</template>
+
+<script>
+import { getProductById, auditProduct } from '@/api/product'
+import { mapGetters } from 'vuex'
+export default {
+  data() {
+    return {
+      authId: '', // 当前产品所属授权机构id
+      isLoading: false,
+      formData: {
+        auditBy: '', // 审核人id
+        productId: '', // 商品id
+        auditStatus: 1, // 商品审核状态
+        invalidReason: '' // 审核信息
+      },
+      formRules: {
+        invalidReason: { required: true, message: '不通过原因不能为空', tigger: 'blur' }
+      },
+      imgList: [], // 图片列表
+      product: null // 商品信息
+    }
+  },
+  computed: {
+    ...mapGetters(['authUserId'])
+  },
+  created() {
+    this.formData.productId = this.$route.query.id
+    this.authId = this.$route.query.authId
+    this.getDetail()
+  },
+  methods: {
+    // 获取商品详情
+    getDetail() {
+      this.isLoading = true
+      getProductById({ productId: this.formData.productId })
+        .then(res => {
+          if (res.code !== 0) return
+          this.product = res.data
+          this.imgList = [this.product.productImage, this.product.certificateImage]
+        }).finally(() => {
+          this.isLoading = false
+        })
+    },
+    // 提交审核信息
+    submit() {
+      this.$refs.formRef.validate(valid => {
+        if (valid) {
+          this.isLoading = true
+          // 指定审核人
+          this.formData.auditBy = this.authUserId
+          // 提交审核信息
+          auditProduct(this.formData).then(res => {
+            if (res.code !== 0) return
+            this.$message.success(res.data)
+            this.$store.dispatch('tagsView/delView', this.$route)
+            this.$router.replace(`/review/shop-list?authId=${this.authId}`)
+          }).finally(() => {
+            this.isLoading = false
+          })
+        }
+      })
+    }
+  }
+}
+</script>
+
+<style lang="scss" scoped>
+.shop-detail{
+  height: 100vh;
+  font-size: 14px;
+  color: #444;
+  .params-list{
+    margin: 0;
+    padding: 0;
+    list-style: none;
+    li{
+      margin-bottom: 15px;
+    }
+  }
+  .el-form {
+    width: 800px;
+    margin: 25px auto 0;
+    .el-button{
+      width: 120px;
+    }
+  }
+}
+</style>

+ 175 - 0
src/views/supplier/review/shopList.vue

@@ -0,0 +1,175 @@
+<template>
+  <div class="app-container">
+    <!-- 搜索区域 -->
+    <div class="filter-container">
+      <span>商品名称:</span>
+      <el-input
+        v-model="listQuery.productName"
+        placeholder="请输入商品名称"
+        style="width: 200px"
+        class="filter-item"
+        @keyup.enter.native="getList"
+      />
+      <span>商品SN码:</span>
+      <el-input
+        v-model="listQuery.snCode"
+        placeholder="请输入商品SN码"
+        style="width: 200px"
+        class="filter-item"
+        @keyup.enter.native="getList"
+      />
+      <span>审核状态:</span>
+      <el-select
+        v-model="listQuery.reviewStatus"
+        placeholder="供应商类型"
+        clearable
+        style="width: 200px"
+        class="filter-item"
+        @change="getList"
+      >
+        <el-option label="所有类型" value="" />
+        <el-option label="待审核" :value="1" />
+        <el-option label="审核通过" :value="2" />
+        <el-option label="审核未通过" :value="0" />
+      </el-select>
+      <el-button type="primary" icon="el-icon-search" @click="getList">查询</el-button>
+    </div>
+    <!-- 搜索区域END -->
+    <!-- 表格区域 -->
+    <el-table
+      v-loading="listLoading"
+      :data="list"
+      style="width: 100%"
+      border
+      fit
+      highlight-current-row
+      cell-class-name="table-cell"
+    >
+      <el-table-column label="序号" type="index" width="80" align="center" />
+      <el-table-column prop="productName" label="商品名称" align="center" />
+      <el-table-column prop="snCode" label="商品SN码" align="center" />
+      <el-table-column label="审核状态" width="220px" align="center">
+        <template slot-scope="{ row }">
+          <el-tag v-if="row.auditStatus === 2" size="small" type="warning">待审核</el-tag>
+          <el-tag v-if="row.auditStatus === 1" size="small" type="success">审核通过</el-tag>
+          <!-- 未通过原因展示 -->
+          <template v-if="row.auditStatus === 0">
+            <!-- <span class="status danger">审核未通过&nbsp;</span> -->
+            <el-popover
+              placement="top-start"
+              title="审核说明"
+              width="400"
+              trigger="hover"
+              :content="row.invalidReason"
+            >
+              <el-tag slot="reference" size="small" type="danger" class="reason">
+                <span>审核未通过</span>
+                <span class="el-icon-question status danger " />
+              </el-tag>
+            </el-popover>
+            <!-- 未通过原因展示END -->
+          </template>
+        </template>
+      </el-table-column>
+      <el-table-column label="审核时间" width="250px" align="center">
+        <template slot-scope="{row}">
+          <span v-if="row.auditStatus!==2">{{ row.auditTime | formatTime }}</span>
+          <span v-else>—</span>
+        </template>
+      </el-table-column>
+      <el-table-column label="审核人" align="center">
+        <template slot-scope="{row}">
+          <span v-if="row.auditStatus!==2">{{ row.auditBy }}</span>
+          <span v-else>—</span>
+        </template>
+      </el-table-column>
+      <el-table-column label="操作" width="240px" align="center">
+        <template slot-scope="{row}">
+          <el-button v-if="row.auditStatus === 2" type="primary" icon="el-icon-s-check" size="mini" @click="$_navigationTo(`shop-detail?id=${row.productId}&authId=${listQuery.authId}`)">审核</el-button>
+          <span v-else class="status success el-icon-check">&nbsp;已审核</span>
+        </template>
+      </el-table-column>
+    </el-table>
+    <!-- 表格区域END -->
+    <!-- 页码 -->
+    <pagination v-show="total>0" :total="total" :page.sync="listQuery.pageNum" :limit.sync="listQuery.pageSize" @pagination="getList" />
+  </div>
+</template>
+
+<script>
+import Pagination from '@/components/Pagination'
+import { getProdList } from '@/api/product'
+import { formatDate } from '@/utils'
+export default {
+  components: { Pagination },
+  filters: {
+    formatTime(time) {
+      if (!time) {
+        return ''
+      }
+      return formatDate(time, 'yyyy-MM-DD HH:mm:ss')
+    }
+  },
+
+  data() {
+    return {
+      listLoading: false,
+      listQuery: {
+        listType: 2,
+        authId: '',
+        productName: '',
+        reviewStatus: '',
+        snCode: '',
+        pageNum: 1,
+        pageSize: 10
+      },
+      total: 0,
+      list: []
+    }
+  },
+  created() {
+    this.listQuery.authId = this.$route.query.authId
+    this.getList()
+  },
+  methods: {
+    // 过滤列表
+    handleFilter() {},
+    // 获取列表信息
+    getList() {
+      this.listLoading = true
+      getProdList(this.listQuery).then(res => {
+        if (res.code !== 0) return
+        this.total = res.data.total
+        this.list = res.data.list
+      }).finally(() => {
+        this.listLoading = false
+      })
+    }
+  }
+}
+</script>
+
+<style lang="scss" scoped>
+.filter-container {
+  span {
+    display: inline-block;
+    margin-bottom: 10px;
+    vertical-align: middle;
+    font-size: 14px;
+  }
+  .el-button {
+    display: inline-block;
+    margin-bottom: 10px;
+    vertical-align: middle;
+  }
+  .el-input,
+  .el-select {
+    margin-right: 10px;
+    margin-left: 10px;
+  }
+}
+.el-table .cell{
+  overflow: visible;
+}
+
+</style>

+ 349 - 338
src/views/supplier/user/add.vue

@@ -1,9 +1,9 @@
 <template>
   <div v-loading="isLoading" class="addSupplier">
-    <el-form ref="addFromDataRef" :model="addFromData" :rules="addFromDataRules" label-width="120px" class="addForm">
+    <el-form ref="formData1Ref" :model="formData1" :rules="formDataRules" label-width="120px" class="addForm">
       <el-form-item label="供应商类型:" prop="shopType">
         <el-select
-          v-model="addFromData.shopType"
+          v-model="formData1.shopType"
           placeholder="请选择供应商类型"
           style="width: 100%"
           @change="handleTypeChange"
@@ -14,17 +14,17 @@
       </el-form-item>
 
       <!-- 供应商名称 -->
-      <el-form-item v-if="addFromData.shopType === 2" label="供应商名称:" prop="shopName">
-        <el-input v-model="addFromData.shopName" placeholder="请输入供应商名称" maxlength="50" show-word-limit />
+      <el-form-item v-if="formData1.shopType === 2" label="供应商名称:" prop="shopName">
+        <el-input v-model="formData1.shopName" placeholder="请输入供应商名称" maxlength="50" show-word-limit />
       </el-form-item>
 
-      <el-form-item v-if="addFromData.shopType === 1" label="供应商名称:" prop="brandId">
+      <el-form-item v-if="formData1.shopType === 1" clearable label="供应商名称:" prop="brandId">
         <el-select
-          v-model="addFromData.brandId"
+          v-model="formData1.brandId"
           placeholder="请选择品牌"
           style="width: 100%"
           filterable
-          @change="setShopName"
+          @change="handleBrandChange"
         >
           <el-option v-for="item in brandList" :key="item.id" :label="item.name" :value="item.id" />
         </el-select>
@@ -32,24 +32,26 @@
       <!-- 供应商名称END -->
 
       <el-form-item label="手机号:" prop="mobile">
-        <el-input v-model="addFromData.mobile" placeholder="请输入手机号" maxlength="11" show-word-limit @input="handleInput" />
+        <el-input v-model="formData1.mobile" placeholder="请输入手机号" maxlength="11" show-word-limit @input="handleInput" />
       </el-form-item>
 
       <el-form-item label="联系人:" prop="linkMan">
-        <el-input v-model="addFromData.linkMan" placeholder="请输入联系人" />
+        <el-input v-model="formData1.linkMan" placeholder="请输入联系人" />
       </el-form-item>
 
-      <el-form-item v-if="addFromData.shopType === 2" label="代理品牌:" prop="shopInfo" class="brand-list">
-        <template v-if="supplierBrands !== []">
-          <el-tag v-for="(brand , index) in supplierBrands" :key="index" closable type="success" @close="handleRemove(index)" @click="handleShowInfo(index)">{{ brand.brandName }}</el-tag>
-        </template>
-        <el-tag type="primary" @click="handleShowDialog">添加品牌<span class="el-icon-plus" /></el-tag>
-        <!-- <el-input v-model="addFromData.shopInfo" class="hiddenInput" /> -->
-      </el-form-item>
+      <transition name="fade">
+        <el-form-item v-if="formData1.shopType === 2" label="代理品牌:" prop="shopInfo" class="brand-list">
+          <template v-if="supplierBrands !== []">
+            <el-tag v-for="(brand , index) in supplierBrands" :key="index" closable type="success" @close="handleRemove(index)" @click="handleShowInfo(index)">{{ brand.brandName }}</el-tag>
+          </template>
+          <el-tag type="primary" @click="handleShowDialog">添加品牌<span class="el-icon-plus" /></el-tag>
+          <!-- <el-input v-model="formData1.shopInfo" class="hiddenInput" /> -->
+        </el-form-item>
+      </transition>
 
-      <template v-if="addFromData.shopType === 1">
+      <template v-if="formData1.shopType === 1">
         <el-form-item label="产地:" prop="countryId">
-          <el-select v-model="addFromData.countryId" placeholder="产地" style="width: 100%" filterable>
+          <el-select v-model="formData1.countryId" placeholder="产地" style="width: 100%" filterable>
             <el-option
               v-for="item in countryList"
               :key="item.countryId"
@@ -67,16 +69,16 @@
             @error="imageUploadFaild1"
             @remove="imageRemove1"
           />
-          <el-input v-model="addFromData.brandAuthLogo" type="hidden" class="hiddenInput" />
+          <el-input v-model="formData1.brandAuthLogo" type="hidden" class="hiddenInput" />
         </el-form-item>
 
         <el-form-item label="官网认证链接:">
-          <el-input v-model="addFromData.securityLink" placeholder="请输入官网认证链接" />
+          <el-input v-model="formData1.securityLink" placeholder="请输入官网认证链接" />
         </el-form-item>
       </template>
 
       <el-form-item label="供应商状态:">
-        <el-select v-model="addFromData.shopStatus" placeholder="请选择供应商状态" style="width: 100%">
+        <el-select v-model="formData1.shopStatus" placeholder="请选择供应商状态" style="width: 100%">
           <el-option label="启用" :value="1" />
           <el-option label="禁用" :value="0" />
         </el-select>
@@ -88,23 +90,23 @@
     </div>
 
     <!-- 供应商添加品牌的对话框 -->
-    <el-dialog v-loading="dialogLoading" title="添加代理品牌" :visible.sync="showDialog" width="width" @closed="dialogClosed">
-      <el-form ref="brandDataRef" :model="brandData" :rules="brandDataRules" label-width="120px">
+    <el-dialog :title="dialogTitleText" :visible.sync="showDialog" width="width" @closed="dialogClosed">
+      <el-form ref="formData2Ref" :model="formData2" label-width="120px" :rules="formDataRules">
 
         <el-form-item label="选择品牌:" prop="brandId">
           <el-select
-            v-model="brandData.brandId"
+            v-model="formData2.brandId"
             placeholder="请选择品牌"
             style="width: 100%"
             filterable
-            @change="setShopName"
+            @change="handleBrandChange"
           >
-            <el-option v-for="item in brandListCody" :key="item.id" :label="item.name" :value="item.id" />
+            <el-option v-for="item in brandListCopy" :key="item.id" :label="item.name" :value="item.id" />
           </el-select>
         </el-form-item>
 
         <el-form-item label="产地:" prop="countryId">
-          <el-select v-model="brandData.countryId" placeholder="产地" style="width: 100%" filterable>
+          <el-select v-model="formData2.countryId" placeholder="产地" style="width: 100%" filterable>
             <el-option
               v-for="item in countryList"
               :key="item.countryId"
@@ -116,16 +118,17 @@
 
         <el-form-item label="品牌logo:" class="no-input" prop="brandAuthLogo">
           <upload-image
-            ref="uploadImageRef1"
-            :file-list="fileList1"
-            @success="imageUploadSuccess1"
-            @error="imageUploadFaild1"
+            ref="uploadImageRef2"
+            :file-list="fileList2"
+            @success="imageUploadSuccess2"
+            @error="imageUploadFaild2"
+            @remove="imageRemove2"
           />
-          <el-input v-model="brandData.brandAuthLogo" type="hidden" class="hiddenInput" />
+          <el-input v-model="formData2.brandAuthLogo" type="hidden" class="hiddenInput" />
         </el-form-item>
 
         <el-form-item label="代理声明:">
-          <el-radio-group v-model="brandData.statementType" @change="handleStatementChange">
+          <el-radio-group v-model="formData2.statementType" @change="handleStatementChange">
             <el-radio :label="1">弹窗</el-radio>
             <el-radio :label="2">链接</el-radio>
             <el-radio :label="3">图片</el-radio>
@@ -133,60 +136,61 @@
           </el-radio-group>
         </el-form-item>
 
-        <el-form-item v-if="brandData.statementType === 1" ref="statement1" label="弹窗:" prop="statementContent">
+        <el-form-item v-if="formData2.statementType === 1" ref="statement1" label="弹窗:" prop="statementContent">
           <el-input
-            v-if="brandData.statementType === 1"
-            v-model="brandData.statementContent"
+            v-if="formData2.statementType === 1"
+            v-model="formData2.statementContent"
             type="textarea"
           />
         </el-form-item>
 
-        <el-form-item v-else-if="brandData.statementType === 2" ref="statement2" label="链接:" prop="statementLink">
-          <el-input v-if="brandData.statementType === 2" v-model="brandData.statementLink" />
+        <el-form-item v-else-if="formData2.statementType === 2" ref="statement2" label="链接:" prop="statementLink">
+          <el-input v-if="formData2.statementType === 2" v-model="formData2.statementLink" />
         </el-form-item>
 
         <el-form-item
-          v-else-if="brandData.statementType === 3"
+          v-else-if="formData2.statementType === 3"
           ref="statement3"
           label="图片:"
           class="no-input"
           prop="statementImage"
         >
           <upload-image
-            v-if="brandData.statementType === 3"
-            ref="uploadImageRef2"
-            :file-list="fileList2"
-            tip-title="宽760px"
-            @success="imageUploadSuccess2"
-            @error="imageUploadFaild2"
-            @remove="imageRemove2"
+            v-if="formData2.statementType === 3"
+            ref="uploadImageRef3"
+            :file-list="fileList3"
+            tip-title="宽760px"
+            @success="imageUploadSuccess3"
+            @error="imageUploadFaild3"
+            @remove="imageRemove3"
           />
-          <el-input v-model="brandData.statementImage" type="hidden" class="hiddenInput" />
+          <el-input v-model="formData2.statementImage" type="hidden" class="hiddenInput" />
         </el-form-item>
 
-        <el-form-item v-else ref="statement4" label="文件:" prop="statementFileId">
+        <el-form-item v-else ref="statementFileRef" label="文件:" prop="statementFileId">
           <upload-file
-            v-if="brandData.statementType === 4"
+            v-if="formData2.statementType === 4"
             ref="uploadFileRef"
-            :auth-user-id="brandData.authUserId"
-            :brand-id="brandData.brandId"
-            :file-list="fileList3"
+            :auth-user-id="formData2.authUserId"
+            :brand-id="formData2.brandId"
+            :file-list="fileList4"
             @success="fileUploadSuccess"
             @error="fileUploadFaild"
             @remove="fileRemove"
+            @change="fileChange"
           />
-          <el-input v-model="brandData.statementFileId" type="hidden" class="hiddenInput" />
+          <el-input v-model="formData2.statementFileId" type="hidden" class="hiddenInput" />
         </el-form-item>
 
         <el-form-item label="官网认证链接:">
-          <el-input v-model="brandData.securityLink" placeholder="请输入官网认证链接" />
+          <el-input v-model="formData2.securityLink" placeholder="请输入官网认证链接" />
         </el-form-item>
 
       </el-form>
 
       <div slot="footer">
         <el-button @click="showDialog = false">取 消</el-button>
-        <el-button type="primary" @click="handleAddBrand">确 定</el-button>
+        <el-button type="primary" :loading="dialogLoading" @click="handleAddBrand">确 定</el-button>
       </div>
     </el-dialog>
 
@@ -204,155 +208,125 @@ import { addSupplier } from '@/api/supplier'
 export default {
   components: { UploadImage, UploadFile },
   data() {
-    const valideMobile = (rule, value, callback) => {
+    const validMobile = (rule, value, callback) => {
       if (!isMobile(value)) {
-        callback(new Error('手机号格式不正确'))
-      } else {
-        callback()
-      }
-    }
-
-    const valideShopInfo = (rule, value, callback) => {
-      if (value.length <= 0) {
-        callback(new Error('品牌不能为空'))
-      } else {
-        callback()
+        return callback(new Error('手机号格式不正确'))
       }
+      return callback()
     }
     return {
-      dialogLoading: false,
+      isCheckout: true,
       isLoading: false,
-      // 是否显示对话框
+      dialogLoading: false,
       showDialog: false,
-      // 需要排除的品牌列表
-      excludeBrand: [],
-      // 上1个选中的品牌
-      prevBrandId: -1,
-      // 品牌列表
-      brandList: [],
-      // 品牌列表处理后的结果
-      brandListCody: [],
-      // 加入的品牌列表
-      supplierBrands: [],
-      // 当前选中的品牌索引在数组中的id
-      currentBrandIndex: '',
-      // 表单校验数据1
-      addFromData: {
-        authUserId: null, // 供应商id
-        shopType: 1, //	供应商类型:1品牌方,2代理商
-        brandId: '', // 品牌id
+      excludeBrandList: [], // 已经选择的品牌,需要被排除在外的
+      selectedShopType: 1,
+      currentIndex: '',
+      prevBrandId: '',
+      dialogTitle: '添加',
+      // 表单1
+      formData1: {
+        shopType: 1, // 供应商类型
         shopName: '', // 供应商名称
+        brandId: '', // 品牌id
         mobile: '', // 手机号
         linkMan: '', // 联系人
-        countryId: 1, // 产地国家id
-        brandAuthLogo: '', //	品牌授权logo
-        createBy: '', // 创建人用户id
+        countryId: 1, // 产地id
+        brandAuthLogo: '', // 品牌logo
         securityLink: '', // 官网认证链接
-        shopStatus: 1, // 供应商状态:0停用 1启用
-        shopInfo: 1
+        shopStatus: 1, // 供应商状态,
+        shopInfo: ''
       },
-      // 表单校验数据2
-      brandData: {
+      // 表单2
+      formData2: {
+        index: '',
         isNew: true,
-        brandId: '', // 供应商id
-        countryId: 1, // 产地国家id
-        brandAuthLogo: '', //	品牌授权logo
         brandName: '',
+        brandId: '', // 品牌id
+        countryId: 1, // 产地id
+        brandAuthLogo: '', // 品牌logo
         securityLink: '', // 官网认证链接
-        statementType: 1, // 声明类型
-        statementContent: '', // 声明弹窗内容
+        statementType: 1, // 代理声明类型
+        statementContent: '', // 声明内容
         statementFileId: null, // 声明文件id
         statementImage: '', // 声明图片
         statementLink: '', // 声明链接
-        statementFileName: ''
-      },
-      // 表单校验规则1
-      addFromDataRules: {
-        shopType: { required: true, message: '供应商类型不能为空', trigger: 'change', type: 'number' },
-        brandId: { required: true, message: '品牌不能为空', trigger: 'change', type: 'number' },
-        shopName: { required: true, message: '请输入供应商名称', trigger: 'change' },
-        mobile: [
-          { required: true, message: '请输入手机号', trigger: 'blur' },
-          { validator: valideMobile, trigger: 'blur' }
-        ],
-        linkMan: { required: true, message: '联系人不能为空', trigger: 'blur' },
-        countryId: { required: true, message: '产地不能为空', trigger: 'change', type: 'number' },
-        brandAuthLogo: { required: true, message: '品牌logo不能为空', trigger: 'change' },
-        shopInfo: { validator: valideShopInfo, trigger: 'change', required: true }
+        statementFileName: '' // 上传图片的名称
       },
-      // 表单校验规则2
-      brandDataRules: {
-        brandId: { required: true, message: '品牌不能为空', trigger: 'change', type: 'number' },
-        countryId: { required: true, message: '产地不能为空', trigger: 'change', type: 'number' },
-        brandAuthLogo: { required: true, message: '品牌logo不能为空', trigger: 'change' },
-        statementContent: { required: true, message: '声明内容不能为空', trigger: 'blur' },
-        statementLink: { required: true, message: '声明链接不能为空', trigger: 'blur' },
-        statementFileId: { required: true, message: '请上传声明文件', trigger: 'change', type: 'number' },
-        statementImage: { required: true, message: '请上传声明图片', trigger: 'change' }
+      supplierBrands: [],
+      brandList: [],
+      // 表单数据校验
+      formDataRules: {
+        shopType: { required: true, message: '供应商类型不能为空', tigger: 'change', type: 'number' },
+        shopName: { required: true, message: '供应名称不能为空', tigger: 'change' },
+        mobile: [{ required: true, message: '手机号不能为空', tigger: 'change' }, { validator: validMobile, tigger: 'change' }],
+        linkMan: { required: true, message: '联系人不能为空', tigger: 'blur' },
+        countryId: { required: true, message: '产地不能为空', tigger: 'change', type: 'number' },
+        brandAuthLogo: { required: true, message: '品牌logo不能为空', tigger: 'change' },
+        shopInfo: { required: true, message: '代理品牌不能为空', tigger: 'change', type: 'string' },
+        brandId: { required: true, message: '品牌不能为空', tigger: 'change', type: 'number' },
+        statementContent: { required: true, message: '声明内容不能为空', tigger: 'change' }, // 声明内容
+        statementFileId: { required: true, message: '声明文件不能为空', tigger: 'change', type: 'number' }, // 声明文件id
+        statementImage: { required: true, message: '声明图片不能为空', tigger: 'change' }, // 声明图片
+        statementLink: { required: true, message: '声明链接不能为空', tigger: 'change' } // 声明链接
       },
-      // 上传成功的文件列表
-      fileList1: [], // 已上传的图片列表 品牌logo
-      fileList2: [], // 已上传的图片列表 声明图片
-      fileList3: [] // 已上传的图片列表 声明文件
+      // 上传的文件列表
+      fileList1: [],
+      fileList2: [],
+      fileList3: [],
+      fileList4: [] // 文件
     }
   },
   computed: {
-    ...mapGetters(['userIdentity', 'name', 'countryList', 'authUserId'])
+    ...mapGetters(['countryList', 'authUserId']),
+    brandListCopy() {
+      return this.brandList.filter(item => {
+        return !this.excludeBrandList.includes(item.id)
+      })
+    },
+    dialogTitleText() {
+      return `${this.dialogTitle}代理品牌`
+    }
   },
   watch: {
-    excludeBrand() {
-      this.excludeBrandHandle()
+    supplierBrands() {
+      if (this.supplierBrands.length > 0) {
+        this.formData1.shopInfo = '1'
+      } else {
+        this.formData1.shopInfo = ''
+      }
     }
   },
   created() {
-    this.initAddForm()
+    this.getBrandList(1)
   },
   methods: {
-
-    // 初始添加供应商时的表单数据
-    initAddForm() {
-      // this.addFromData.authUserId = this.authUserId
-      this.getBrandList(1)
-      this.addFromData.shopName = ''
-    },
-    // 提交表单数据
+    // 提交保存
     submit() {
-      this.$refs.addFromDataRef.validate(valide => {
-        if (valide) {
-          console.log('校验通过')
-          if (this.addFromData.shopType === 1) {
-            this.save()
-          } else if (this.addFromData.shopType === 2) {
-            if (this.supplierBrands.length < 1) {
-              this.$alert('请至少添加一个代理品牌', '不满足提交要求', { type: 'warning' })
-              return
-            }
-            this.save()
-          }
-        }
-      })
-    },
-    // 保存
-    save() {
-      this.isLoading = true
-      addSupplier(this.createAddData())
-        .then(res => {
+      this.$refs.formData1Ref.validate(valid => {
+        if (!valid) return
+        this.isLoading = true
+        addSupplier(this.setAddParams()).then(res => {
           if (res.code !== 0) {
             return
           }
-          console.log(res)
-          this.$message.success('添加成功')
-          this.$router.replace('/supplier')
-        })
-        .finally(() => {
+          const h = this.$createElement
+          this.$notify.success({
+            title: '添加供应商',
+            message: h('i', { style: 'color: #333' }, `已添加供应商:"${this.formData1.shopName}"`),
+            duration: 3000
+          })
+          this.$store.dispatch('tagsView/delView', this.$route)
+          this.$router.push('/supplier')
+        }).finally(() => {
           this.isLoading = false
         })
+      })
     },
-    // 创建请求参数
-    createAddData() {
-      let addData = {}
-      // 参数模板
-      const temp1 = {
+    // 封装请求参数
+    setAddParams() {
+      // 品牌方的参数列表
+      const result = {
         authUserId: '',
         createBy: '',
         linkMan: '',
@@ -362,231 +336,272 @@ export default {
         shopType: '',
         shopInfo: []
       }
-      const temp2 = {
-        brandId: 1,
-        countryId: 2,
-        brandAuthLogo: '',
-        securityLink: '',
-        statementType: 1,
-        statementContent: '',
-        statementFileId: null,
-        statementImage: '',
-        statementLink: ''
-      }
-      // 指定创建者为当前登录的账号id
-      this.addFromData.createBy = this.authUserId
-      for (const key in temp1) {
-        if (Object.hasOwnProperty.call(temp1, key)) {
-          temp1[key] = this.addFromData[key]
-        }
-      }
-      // 如果为品牌方
-      if (this.addFromData.shopType === 1) {
-        for (const key in temp2) {
-          if (Object.hasOwnProperty.call(temp2, key)) {
-            temp2[key] = this.addFromData[key] || ''
+      // 品牌方
+      if (this.selectedShopType === 1) {
+        for (const key in result) {
+          if (Object.hasOwnProperty.call(result, key)) {
+            if (key !== 'shopInfo') {
+              result[key] = this.formData1[key]
+            }
           }
         }
-        temp2.statementType = 1
-        temp2.statementFileId = null
-        addData = {
-          ...temp1,
-          shopInfo: [temp2]
-        }
+        result.shopInfo.push({
+          brandId: this.formData1.brandId,
+          countryId: this.formData1.countryId,
+          brandAuthLogo: this.formData1.brandAuthLogo,
+          securityLink: this.formData1.securityLink,
+          statementType: 1,
+          statementContent: '',
+          statementFileId: null,
+          statementImage: '',
+          statementLink: ''
+        })
       }
-      // 如果为代理商
-      if (this.addFromData.shopType === 2) {
-        addData = {
-          ...temp1,
-          shopInfo: this.supplierBrands
+
+      // 代理商
+      if (this.selectedShopType === 2) {
+        for (const key in result) {
+          if (Object.hasOwnProperty.call(result, key)) {
+            if (key !== 'shopInfo') {
+              result[key] = this.formData1[key]
+            }
+          }
         }
+        result.shopInfo = this.supplierBrands
       }
-
-      return addData
+      result.createBy = this.authUserId
+      console.log(result)
+      return result
     },
+
     // 获取品牌列表
     getBrandList(type) {
-      // 获取品牌列表
-      fetchBrandList({ type })
-        .then(res => {
-          console.log(res)
-          if (res.code === 0) {
-            this.brandList = res.data
-            this.brandListCody = res.data
-          }
-        })
-        .catch(err => console.log(err))
-    },
-    // 供应商类型切换
-    handleTypeChange(id) {
-      const type = id
-      this.$refs.addFromDataRef.clearValidate()
-      this.addFromData = {
-        authUserId: null, // 供应商id
-        shopType: type, //	供应商类型:1品牌方,2代理商
-        brandId: '', // 品牌id
-        shopName: '', // 供应商名称
-        mobile: '', // 手机号
-        linkMan: '', // 联系人
-        countryId: 1, // 产地国家id
-        brandAuthLogo: '', //	品牌授权logo
-        createBy: '', // 创建人用户id
-        securityLink: '', // 官网认证链接
-        shopStatus: 1, // 供应商状态:0停用 1启用
-        shopInfo: 1
-      }
-      this.fileList1 = []
-      this.getBrandList(type)
+      fetchBrandList({ type }).then(res => {
+        if (res.code !== 0) {
+          return
+        }
+        this.brandList = res.data
+      })
     },
-    // 设置品牌名称
-    setShopName(id) {
-      const selectBrand = this.brandList.filter(item => {
-        return item.id === id
-      })[0]
-      const str = this.addFromData.shopType === 1 ? 'addFromData' : 'brandData'
-      this[str].shopName = selectBrand.name
-      this[str].brandAuthLogo = selectBrand.authLogo
-      this[str].brandId = selectBrand.id
-      if (str === 'brandData') {
-        this[str].brandName = selectBrand.name
+    // 品牌改变事件
+    handleBrandChange(id) {
+      const selectBrand = this.brandList.filter(item => item.id === id)[0]
+      // 选择品牌方
+      if (this.formData1.shopType === 1) {
+        this.formData1.shopName = selectBrand.name
+        this.formData1.brandAuthLogo = selectBrand.authLogo
+        this.formData1.brandId = selectBrand.id
+        if (selectBrand.authLogo) {
+          this.fileList1 = [{ name: selectBrand.name, url: selectBrand.authLogo }]
+        }
       }
-      if (selectBrand.authLogo) {
-        this.fileList1 = [{ name: '文件已上传', url: selectBrand.authLogo }]
+      // 如果选择代理应商
+      if (this.formData1.shopType === 2) {
+        this.formData2.brandAuthLogo = selectBrand.authLogo
+        this.formData2.brandName = selectBrand.name
+        this.formData2.brandId = selectBrand.id
+        if (selectBrand.authLogo) {
+          this.fileList2 = [{ name: selectBrand.name, url: selectBrand.authLogo }]
+        }
       }
     },
-    // 添加品牌对话框开启
+    // 添加品牌对话框
     handleShowDialog() {
-      this.brandData.brandId = ''
+      this.dialogTitle = '新增'
       this.showDialog = true
+      this.resetFormData2()
     },
     // 添加品牌
     handleAddBrand() {
-      // 如果声明类型为文件
-      if (this.brandData.statementType === 4 && (this.brandData.statementFileId === null || this.brandData.statementFileId === '')) {
-        this.brandData.statementFileId = this.brandData.statementFileId === null ? '' : null
+      this.dialogLoading = true
+      // 如果声明类型为4,并且文件id为空或null,则需要先上传文件再保存
+      if (this.formData2.statementType === 4 && (this.formData2.statementFileId === '' || this.formData2.statementFileId === null)) {
         this.$refs.uploadFileRef.$refs.upload.submit()
       } else {
-        this.saveBrand()
+        this.saveShopInfo()
       }
     },
-    // 保存品牌信息
-    saveBrand() {
-      this.$refs.brandDataRef.validate(valid => {
-        if (valid) {
-          const brandInfo = this.clone(this.brandData)
-          console.log(brandInfo)
-          if (brandInfo.isNew) {
-            brandInfo.isNew = false
-            this.supplierBrands.push(brandInfo)
-          } else {
-            this.supplierBrands.splice(this.currentBrandIndex, 1, brandInfo)
-          }
-
-          if (this.addFromData.shopType === 2) {
-            this.excludeBrand.push(this.brandData.brandId)
-            this.prevBrandId = -1
-            console.log('添加:' + this.excludeBrand)
-          }
-          this.showDialog = false
+    saveShopInfo() {
+      this.dialogLoading = false
+      this.$refs.formData2Ref.validate(valid => {
+        if (!valid) {
+          return
+        }
+        // 如果是新增的
+        const shopInfo = this.clone(this.formData2)
+        if (shopInfo.isNew) {
+          this.supplierBrands.push(shopInfo)
+        } else {
+        // 修改的
+          this.supplierBrands.splice(this.currentIndex, shopInfo)
         }
+        this.addExcludeBrand(shopInfo.brandId)
+        shopInfo.isNew = false
+        this.prevBrandId = ''
+        this.showDialog = false
+        const h = this.$createElement
+        this.$notify.success({
+          title: `${this.dialogTitle}品牌`,
+          message: h('i', { style: 'color: #333' }, `${this.dialogTitle}品牌:"${shopInfo.brandName}"`),
+          duration: 2000
+        })
+      })
+    },
+    // 移除品牌
+    handleRemove(index) {
+      const pop = this.supplierBrands.splice(index, 1)[0]
+      this.removeExcludeBrand(pop.brandId)
+      const h = this.$createElement
+      this.$notify.success({
+        title: '移除品牌',
+        message: h('i', { style: 'color: #333' }, `已移除品牌:"${pop.brandName}"`),
+        duration: 2000
       })
     },
-    // 修改
+    // 修改品牌
     handleShowInfo(index) {
-      this.currentBrandIndex = index
-      this.brandData = this.clone(this.supplierBrands[index])
-      this.brandData.isNew = false
-      this.prevBrandId = this.brandData.brandId
-      if (this.addFromData.shopType === 2) {
-        const i = this.excludeBrand.indexOf(this.brandData.brandId)
-        this.excludeBrand.splice(i, 1)
-      }
-      if (this.brandData.brandAuthLogo) {
-        this.fileList1 = [{ name: '文件已上传', url: this.brandData.brandAuthLogo }]
-      }
-      if (this.brandData.statementImage) {
-        this.fileList2 = [{ name: '文件已上传', url: this.brandData.statementImage }]
-      }
-      if (this.brandData.statementFileId) {
-        this.fileList3 = [{ name: this.brandData.statementFileName, url: '' }]
-      }
+      this.dialogTitle = '修改'
+      this.currentIndex = index
+      this.formData2 = this.clone(this.supplierBrands[index])
+      this.prevBrandId = this.supplierBrands[index].brandId // 保存当前的品牌id
+      this.fileList2 = [{ name: '', url: this.formData2.brandAuthLogo }]
+      this.fileList3 = [{ name: '', url: this.formData2.statementImage }]
+      this.fileList4 = [{ name: this.formData2.statementFileName, url: '' }]
+      this.removeExcludeBrand(this.supplierBrands[index].brandId)
       this.showDialog = true
     },
-    // 删除
-    handleRemove(index) {
-      const i = this.excludeBrand.indexOf(this.supplierBrands[index].brandId)
-      this.excludeBrand.splice(i, 1)
-      this.supplierBrands.splice(index, 1)
-      console.log('删除:' + this.excludeBrand)
-    },
-    // 对话框关闭
+    // 添加品牌对话框关闭
     dialogClosed() {
-      this.$refs.brandDataRef.resetFields()
-      this.brandData.brandId = ''
-      this.fileList1 = []
-      this.fileList2 = []
-      this.fileList3 = []
-      this.brandData.isNew = true
-      // 如果部位-1 代表没有保存 则恢复到上一次的排除结果
-      if (this.prevBrandId !== -1) {
-        this.excludeBrand.push(this.prevBrandId)
-        this.prevBrandId = -1
+      if (this.prevBrandId) {
+        this.addExcludeBrand(this.prevBrandId)
+        this.prevBrandId = ''
       }
+      this.resetFormData2()
     },
     // 声明类型切换
-    handleStatementChange(index) {
-      console.log(index)
-      const ref = 'statement' + index
-      this.$refs[ref].clearValidate()
+    handleStatementChange() {},
+    // 供应商类型改变事件
+    handleTypeChange(shopType) {
+      this.selectedShopType = shopType
+      this.getBrandList(shopType)
+      this.resetFormData1(shopType)
+    },
+    // 添加排除品牌
+    addExcludeBrand(id) {
+      this.excludeBrandList.push(id)
     },
+    // 移除排除品牌
+    removeExcludeBrand(id) {
+      const index = this.excludeBrandList.indexOf(id)
+      this.excludeBrandList.splice(index, 1)
+    },
+    // 输入框输入时
+    handleInput() {
+      this.formData1.mobile = this.formData1.mobile.replace(/[^\w\.\/]/ig, '')
+    },
+
     // 文件上传成功
     fileUploadSuccess(data) {
-      this.brandData.statementFileId = data.data.fileId
-      this.brandData.statementFileName = data.data.fileName
+      this.formData2.statementFileName = data.data.fileName
+      this.formData2.statementFileId = data.data.fileId
       if (data.code === 0) {
-        this.saveBrand()
+        this.saveShopInfo()
       }
     },
     fileUploadFaild(err, file, fileList) {
+      this.$message.error('文件上传失败')
       console.log(err)
     },
     fileRemove() {
+      this.formData2.statementFileId = null
       console.log('删除文件')
-      this.brandData.statementFileId = null
+    },
+    fileChange() {
+      console.log('文件改变')
+      this.$refs.statementFileRef.clearValidate()
     },
 
-    // 图片上传成功 品牌logo
+    // 图片上传成功 品牌logo  1
     imageUploadSuccess1(data) {
-      const str = this.addFromData.shopType === 1 ? 'addFromData' : 'brandData'
-      this[str].brandAuthLogo = data.data
+      this.formData1.brandAuthLogo = data.data
     },
     imageUploadFaild1(err, file, fileList) {
+      this.$message.error('图片上传失败')
       console.log(err)
     },
     imageRemove1() {
-      const str = this.addFromData.shopType === 1 ? 'addFromData' : 'brandData'
-      this[str].brandAuthLogo = ''
-      console.log('删除文件')
+      this.formData1.brandAuthLogo = ''
+      console.log('删除图片')
     },
-
-    // 图片上传成功 声明图片
+    // 图片上传成功 品牌logo 2
     imageUploadSuccess2(data) {
-      this.brandData.statementImage = data.data
+      this.formData2.brandAuthLogo = data.data
     },
     imageUploadFaild2(err, file, fileList) {
+      this.$message.error('图片上传失败')
       console.log(err)
     },
     imageRemove2() {
-      this.brandData.statementImage = ''
-      console.log('删除文件')
+      this.formData2.brandAuthLogo = ''
+      console.log('删除图片')
     },
-    // 对品牌列表做排除操作
-    excludeBrandHandle() {
-      this.brandListCody = this.brandList.filter((item, index) => {
-        return this.excludeBrand.indexOf(item.id) === -1
-      })
+    // 图片上传成功 声明图片  3
+    imageUploadSuccess3(data) {
+      this.formData2.statementImage = data.data
+    },
+    imageUploadFaild3(err, file, fileList) {
+      this.$message.error('图片上传失败')
+      console.log(err)
+    },
+    imageRemove3() {
+      this.formData2.statementImage = ''
+      console.log('删除图片')
+    },
+    // 重置表单1
+    resetFormData1(shopType) {
+      this.formData1 = {
+        shopType: shopType, // 供应商类型
+        shopName: '', // 供应商名称
+        brandId: '', // 品牌id
+        mobile: '', // 手机号
+        linkMan: '', // 联系人
+        countryId: '', // 产地id
+        brandAuthLogo: '', // 品牌logo
+        securityLink: '', // 官网认证链接
+        shopStatus: 1, // 供应商状态,
+        shopInfo: []
+      }
+      this.fileList1 = []
+      this.fileList2 = []
+      this.fileList3 = []
+      this.fileList4 = []
+      this.$refs.formData1Ref.clearValidate()
+    },
+    // 重置表单2
+    resetFormData2() {
+      this.formData2 = {
+        index: '',
+        isNew: true,
+        brandName: '',
+        brandId: '', // 品牌id
+        countryId: 1, // 产地id
+        brandAuthLogo: '', // 品牌logo
+        securityLink: '', // 官网认证链接
+        statementType: 1, // 代理声明类型
+        statementContent: '', // 声明内容
+        statementFileId: null, // 声明文件id
+        statementImage: '', // 声明图片
+        statementLink: '', // 声明链接
+        statementFileName: ''
+      }
+      this.fileList1 = []
+      this.fileList2 = []
+      this.fileList3 = []
+      this.fileList4 = []
+      setTimeout(() => {
+        this.$refs.formData2Ref.clearValidate()
+      }, 200)
     },
-
     // 克隆
     clone(data) {
       const result = {}
@@ -596,10 +611,6 @@ export default {
         }
       }
       return result
-    },
-    // 输入框输入时
-    handleInput() {
-      this.addFromData.mobile = this.addFromData.mobile.replace(/[^\w\.\/]/ig, '')
     }
   }
 }

File diff suppressed because it is too large
+ 420 - 389
src/views/supplier/user/edit.vue


+ 12 - 32
src/views/supplier/user/index.vue

@@ -10,7 +10,7 @@
         <el-option label="品牌方" :value="1" />
       </el-select>
       <span>所属品牌:</span>
-      <el-select v-model="listQuery.brandId" placeholder="所属品牌" clearable class="filter-item" style="width: 200px" @change="getList()">
+      <el-select v-model="listQuery.brandId" placeholder="所属品牌" clearable class="filter-item" style="width: 200px" filterable @change="getList()">
         <el-option label="所有品牌" value="" />
         <el-option
           v-for="item in brandList"
@@ -23,8 +23,8 @@
       <el-input v-model="listQuery.mobile" placeholder="手机号" style="width: 200px;" class="filter-item" @keyup.enter.native="handleFilter" />
       <span>联系人:</span>
       <el-input v-model="listQuery.linkMan" placeholder="联系人" style="width: 200px;" class="filter-item" @keyup.enter.native="handleFilter" />
-      <el-button type="primary" @click="getList(listQuery)">查询</el-button>
-      <el-button type="primary" @click="$_navigationTo('add')">添加供应商</el-button>
+      <el-button type="primary" icon="el-icon-search" @click="getList(listQuery)">查询</el-button>
+      <el-button type="primary" icon="el-icon-edit" @click="$_navigationTo('add')">添加供应商</el-button>
     </div>
     <!-- 表格区域 -->
     <el-table
@@ -88,6 +88,7 @@ import { fetchSupplierList, supplierStatusChange } from '@/api/supplier'
 import { resetPassword } from '@/api/user'
 import { fetchBrandList } from '@/api/brand'
 import { formatDate } from '@/utils'
+// import scrollTo from '@/mixin/scrollTo'
 export default {
   name: 'ComplexTable',
   components: { Pagination },
@@ -99,6 +100,7 @@ export default {
       return formatDate(time, 'yyyy-MM-DD HH:mm:ss')
     }
   },
+  // mixins: [scrollTo],
   data() {
     return {
       slider: 1,
@@ -120,38 +122,10 @@ export default {
     }
   },
   created() {
-    // console.log(1)
-    // this.prevData = JSON.parse(window.localStorage.getItem('prevData')) || null
-    // if (this.prevData !== null) {
-    //   this.listQuery.pageNum = this.prevData.prevData
-    //   this.listQuery.pageSize = this.prevData.pageSize
-    // }
     this.getList()
     this.getBrandList()
   },
-  // mounted() {
-  //   if (this.prevData !== null) {
-  //     window.scrollTo(0, this.prevData.scroll)
-  //   }
-  //   this.addEventListenerScroll()
-  // },
   methods: {
-    // addEventListenerScroll() {
-    //   let timer = null
-    //   const that = this
-    //   window.addEventListener('scroll', function() {
-    //     clearTimeout(timer)
-    //     timer = setTimeout(() => {
-    //       // console.log(this.scrollY)
-    //       const data = JSON.stringify({
-    //         scroll: this.scrollY,
-    //         pageNum: that.listQuery.pageNum,
-    //         pageSize: that.listQuery.pageSize
-    //       })
-    //       window.localStorage.setItem('prevData', data)
-    //     }, 200)
-    //   })
-    // },
     // 获取列表数据
     getList() {
       this.listLoading = true
@@ -220,7 +194,13 @@ export default {
       if (text !== 'confirm') return
       // 要执行的操作
       resetPassword({ authUserId: item.authUserId }).then(res => {
-        this.$message.success(res.data)
+        if (res.code !== 0) return
+        const h = this.$createElement
+        this.$notify.success({
+          title: '重置密码',
+          message: h('i', { style: 'color: #333' }, `已重置供应商"${item.name}"的密码`),
+          duration: 2000
+        })
       })
     },
     // 代他操作

Some files were not shown because too many files changed in this diff