From a26f13ee999e84fc49cc3545e6e5d3daf9c6c41f Mon Sep 17 00:00:00 2001
From: king <18310653075@163.com>
Date: 星期一, 07 十月 2024 00:15:39 +0800
Subject: [PATCH] 2024-10-07

---
 src/tabviews/zshare/actionList/normalbutton/index.jsx | 1674 +++++++++++++++++++++++++++++++++++++++++++++++------------
 1 files changed, 1,316 insertions(+), 358 deletions(-)

diff --git a/src/tabviews/zshare/actionList/normalbutton/index.jsx b/src/tabviews/zshare/actionList/normalbutton/index.jsx
index d6c0450..af7d1e3 100644
--- a/src/tabviews/zshare/actionList/normalbutton/index.jsx
+++ b/src/tabviews/zshare/actionList/normalbutton/index.jsx
@@ -3,7 +3,7 @@
 import moment from 'moment'
 import qs from 'qs'
 import { is, fromJS } from 'immutable'
-import { Button, Modal, notification, message, Drawer, Switch, Checkbox, Progress } from 'antd'
+import { Button, Modal, notification, message, Popover, Drawer, Switch, Checkbox, Progress } from 'antd'
 import md5 from 'md5'
 
 import Api from '@/api'
@@ -28,6 +28,7 @@
     columns: PropTypes.any,           // 瀛楁鍒�
     setting: PropTypes.any,           // 椤甸潰閫氱敤璁剧疆
     disabled: PropTypes.any,          // 琛屾寜閽鐢�
+    name: PropTypes.any
   }
 
   state = {
@@ -43,10 +44,10 @@
     hidden: false,
     autoMatic: false,
     check: false,
-    count: 0
+    count: 0,
+    dict: window.GLOB.dict
   }
 
-  moduleParams = null
   preCallback = null
 
   UNSAFE_componentWillMount () {
@@ -203,9 +204,9 @@
   /**
    * @description 瑙﹀彂鎸夐挳鎿嶄綔
    */
-  actionTrigger = (triggerId, record, type, callback) => {
-    const { btn, selectedData } = this.props
-    const { loading, disabled } = this.state
+  actionTrigger = (triggerId, record, type, lid, callback) => {
+    const { btn, selectedData, LID } = this.props
+    const { loading, disabled, dict } = this.state
 
     if (type === 'preButton') {
       if (btn.uuid !== triggerId) return
@@ -218,12 +219,12 @@
 
     if (loading || disabled) return
     if (triggerId && btn.uuid !== triggerId) return
-    if (type === 'linkbtn' && !btn.$toolbtn && !is(fromJS(selectedData || []), fromJS(record))) return
+    if (type === 'linkbtn' && !btn.$toolbtn && LID !== lid) return
     if (btn.OpenType === 'form' && btn.formType === 'count_line') return
 
     this.setState({autoMatic: type === 'autoMatic'})
 
-    let _this = this
+    let that = this
     let data = record || selectedData || []
 
     let valid = this.checkBtnData(data)
@@ -241,14 +242,16 @@
     } else if (btn.OpenType === 'prompt') {
       this.setState({loading: true})
       confirm({
-        title: btn.tipTitle || '纭畾瑕佹墽琛屽悧?',
+        title: btn.tipTitle || dict['exec_sure'] || '纭畾瑕佹墽琛屽悧?',
+        okText: dict['ok'] || '纭畾',
+        cancelText: dict['cancel'] || '鍙栨秷',
         onOk() {
           return new Promise(resolve => {
-            _this.execSubmit(data, resolve)
+            that.execSubmit(data, resolve)
           })
         },
         onCancel() {
-          _this.setState({loading: false})
+          that.setState({loading: false})
         }
       })
     } else if (btn.OpenType === 'exec') {
@@ -304,21 +307,21 @@
       }
     }
 
-    if (window.GLOB.systemType === 'production') {
-      let _change = {
-        prompt: '鎻愮ず妗�',
-        exec: '鐩存帴鎵ц',
-        pop: '寮圭獥锛堣〃鍗曪級',
-        formSubmit: '琛ㄥ崟',
-        form: '琛ㄥ崟',
-      }
-      MKEmitter.emit('queryTrigger', {menuId: btn.uuid, name: _change[btn.OpenType]})
-    }
+    // if (window.GLOB.systemType === 'production') {
+    //   let _change = {
+    //     prompt: '鎻愮ず妗�',
+    //     exec: '鐩存帴鎵ц',
+    //     pop: '寮圭獥锛堣〃鍗曪級',
+    //     formSubmit: '琛ㄥ崟',
+    //     form: '琛ㄥ崟',
+    //   }
+    //   MKEmitter.emit('queryTrigger', {menuId: btn.uuid, name: _change[btn.OpenType]})
+    // }
   }
 
   preTrigger = (callback) => {
     const { btn, selectedData } = this.props
-    const { loading, disabled } = this.state
+    const { loading, disabled, dict } = this.state
 
     if (loading || disabled) {
       callback()
@@ -328,7 +331,7 @@
       return
     }
 
-    let _this = this
+    let that = this
     let data = selectedData || []
 
     let valid = this.checkBtnData(data)
@@ -351,15 +354,17 @@
     } else if (btn.OpenType === 'prompt') {
       this.setState({loading: true})
       confirm({
-        title: btn.tipTitle || '纭畾瑕佹墽琛屽悧?',
+        title: btn.tipTitle || dict['exec_sure'] || '纭畾瑕佹墽琛屽悧?',
+        okText: dict['ok'] || '纭畾',
+        cancelText: dict['cancel'] || '鍙栨秷',
         onOk() {
           return new Promise(resolve => {
-            _this.execSubmit(data, resolve)
+            that.execSubmit(data, resolve)
           })
         },
         onCancel() {
           callback()
-          _this.setState({loading: false})
+          that.setState({loading: false})
         }
       })
     } else if (btn.OpenType === 'exec') {
@@ -401,11 +406,12 @@
 
   checkBtnData = (data) => {
     const { BID, btn, setting } = this.props
+    const { dict } = this.state
 
     if (setting.supModule && !BID) {
       notification.warning({
         top: 92,
-        message: '闇�瑕佷笂绾т富閿�硷紒',
+        message: dict['sup_key_req'] || '闇�瑕佷笂绾т富閿�硷紒',
         duration: 5
       })
       return false
@@ -413,7 +419,7 @@
       // 闇�瑕侀�夋嫨琛屾椂锛屾牎楠屾暟鎹�
       notification.warning({
         top: 92,
-        message: '璇烽�夋嫨琛岋紒',
+        message: dict['select_row'] || '璇烽�夋嫨琛岋紒',
         duration: 5
       })
       return false
@@ -421,42 +427,17 @@
       // 闇�瑕侀�夋嫨鍗曡鏃讹紝鏍¢獙鏁版嵁
       notification.warning({
         top: 92,
-        message: '璇烽�夋嫨鍗曡鏁版嵁锛�',
+        message: dict['select_single_row'] || '璇烽�夋嫨鍗曡鏁版嵁锛�',
         duration: 5
       })
       return false
-    } else if (btn.intertype === 'system') {
-      if (data.length === 0 && btn.verify && btn.verify.voucher && btn.verify.voucher.enabled) {
-        notification.warning({
-          top: 92,
-          message: '浣跨敤鍒涘缓鍑瘉鍑芥暟锛岄渶瑕侀�夋嫨琛岋紒',
-          duration: 5
-        })
-        return false
-      }
-    } else if (btn.intertype === 'custom' || btn.intertype === 'outer') {
-      if (btn.callbackType === 'script' && (!btn.verify || !btn.verify.cbScripts || !btn.verify.cbScripts.filter(item => item.status !== 'false').length === 0)) {
-        notification.warning({
-          top: 92,
-          message: '浣跨敤鑷畾涔夎剼鏈洖璋冩椂锛屽洖璋冭剼鏈笉鍙负绌猴紒',
-          duration: 5
-        })
-        return false
-      } else if (btn.procMode === 'system' && data.length === 0 && btn.verify && btn.verify.voucher && btn.verify.voucher.enabled) {
-        notification.warning({
-          top: 92,
-          message: '浣跨敤鍒涘缓鍑瘉鍑芥暟锛岄渶瑕侀�夋嫨琛岋紒',
-          duration: 5
-        })
-        return false
-      } else if (btn.intertype === 'custom' && window.GLOB.systemType === 'production' && !btn.proInterface) {
-        notification.warning({
-          top: 92,
-          message: '灏氭湭璁剧疆姝e紡绯荤粺鎺ュ彛鍦板潃锛�',
-          duration: 5
-        })
-        return false
-      }
+    } else if (btn.intertype === 'custom' && window.GLOB.systemType === 'production' && !btn.proInterface) {
+      notification.warning({
+        top: 92,
+        message: dict['no_prod_link'] || '灏氭湭璁剧疆姝e紡绯荤粺鎺ュ彛鍦板潃锛�',
+        duration: 5
+      })
+      return false
     }
 
     return true
@@ -477,8 +458,8 @@
       
       let primaryId = ''
 
-      if ((btn.Ot === 'requiredSgl' || btn.Ot === 'requiredOnce') && setting.primaryKey) {
-        let ids = data.map(d => { return d[setting.primaryKey] || ''})
+      if (btn.Ot === 'requiredSgl' || btn.Ot === 'requiredOnce') {
+        let ids = data.map(d => d.$$uuid)
         ids = ids.filter(Boolean)
         primaryId = ids.join(',')
       }
@@ -487,17 +468,17 @@
         param.ID = primaryId
 
         if (retmsg) {
-          const { sql, callbacksql } = getSysDefaultSql(btn, setting, '', param, data[0], columns, retmsg, this.moduleParams) // 鏁版嵁婧�
+          const { sql, callbacksql } = getSysDefaultSql(btn, setting, '', param, data[0], columns, retmsg) // 鏁版嵁婧�
           param.LText = sql
           param.$callbacksql = callbacksql
         } else {
-          param.LText = getSysDefaultSql(btn, setting, '', param, data[0], columns, false, this.moduleParams) // 鏁版嵁婧�
+          param.LText = getSysDefaultSql(btn, setting, '', param, data[0], columns, false) // 鏁版嵁婧�
           if (btn.output) {
             param.key_back_type = 'Y'
           }
         }
 
-        param.exec_type = 'y' // 鍚庡彴瑙g爜
+        param.exec_type = window.GLOB.execType || 'y' // 鍚庡彴瑙g爜
         param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
         param.secretkey = Utils.encrypt('', param.timestamp)
 
@@ -508,32 +489,23 @@
           param.LText = param.LText.replace(/\$check@|@check\$/ig, '')
         }
 
-        param.LText = Utils.formatOptions(param.LText)
+        param.LText = Utils.formatOptions(param.LText, param.exec_type)
       } else if (btn.OpenType === 'pop' || btn.OpenType === 'formSubmit' || btn.OpenType === 'form') { // 琛ㄥ崟
         if (btn.sqlType === 'insert') { // 绯荤粺鍑芥暟娣诲姞鏃讹紝鐢熸垚uuid
-          primaryId = ''
-
-          if (formdata && setting.primaryKey) { // 琛ㄥ崟涓瓨鍦ㄤ富閿瓧娈碉紝涓婚敭鍊间互琛ㄥ崟涓殑鍊间负鍑�
-            let _form = formdata.filter(_form => _form.key === setting.primaryKey)[0]
-            if (_form) {
-              primaryId = _form.value
-            }
-          }
-
-          param.ID = primaryId || Utils.getguid()
+          param.ID = Utils.getguid()
 
           if (retmsg) {
-            const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, retmsg, this.moduleParams) // 鏁版嵁婧�
+            const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, retmsg) // 鏁版嵁婧�
             param.LText = sql
             param.$callbacksql = callbacksql
           } else {
-            param.LText = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, false, this.moduleParams) // 鏁版嵁婧�
+            param.LText = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, false) // 鏁版嵁婧�
             if (btn.output) {
               param.key_back_type = 'Y'
             }
           }
 
-          param.exec_type = 'y' // 鍚庡彴瑙g爜
+          param.exec_type = window.GLOB.execType || 'y' // 鍚庡彴瑙g爜
           param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
           param.secretkey = Utils.encrypt('', param.timestamp)
 
@@ -544,22 +516,22 @@
             param.LText = param.LText.replace(/\$check@|@check\$/ig, '')
           }
 
-          param.LText = Utils.formatOptions(param.LText)
+          param.LText = Utils.formatOptions(param.LText, param.exec_type)
         } else {
           param.ID = primaryId
 
           if (retmsg) {
-            const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, retmsg, this.moduleParams) // 鏁版嵁婧�
+            const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, retmsg) // 鏁版嵁婧�
             param.LText = sql
             param.$callbacksql = callbacksql
           } else {
-            param.LText = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, false, this.moduleParams) // 鏁版嵁婧�
+            param.LText = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, false) // 鏁版嵁婧�
             if (btn.output) {
               param.key_back_type = 'Y'
             }
           }
 
-          param.exec_type = 'y' // 鍚庡彴瑙g爜
+          param.exec_type = window.GLOB.execType || 'y' // 鍚庡彴瑙g爜
           param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
           param.secretkey = Utils.encrypt('', param.timestamp)
 
@@ -570,7 +542,7 @@
             param.LText = param.LText.replace(/\$check@|@check\$/ig, '')
           }
 
-          param.LText = Utils.formatOptions(param.LText)
+          param.LText = Utils.formatOptions(param.LText, param.exec_type)
         }
       }
 
@@ -590,7 +562,7 @@
 
       if (param.$unCheckParam) {
         param.$unCheckParam.LText = param.$unCheckParam.LText.replace(/\$check@/ig, '/*').replace(/@check\$/ig, '*/')
-        param.$unCheckParam.LText = Utils.formatOptions(param.$unCheckParam.LText)
+        param.$unCheckParam.LText = Utils.formatOptions(param.$unCheckParam.LText, param.exec_type)
         param.$unCheckParam.menuname = btn.logLabel
 
         if (window.GLOB.probation) {
@@ -615,17 +587,17 @@
           param.ID = primaryId
 
           if (retmsg) {
-            const { sql, callbacksql } = getSysDefaultSql(btn, setting, '', param, cell, columns, retmsg, this.moduleParams) // 鏁版嵁婧�
+            const { sql, callbacksql } = getSysDefaultSql(btn, setting, '', param, cell, columns, retmsg) // 鏁版嵁婧�
             param.LText = sql
             param.$callbacksql = callbacksql
           } else {
-            param.LText = getSysDefaultSql(btn, setting, '', param, cell, columns, false, this.moduleParams) // 鏁版嵁婧�
+            param.LText = getSysDefaultSql(btn, setting, '', param, cell, columns, false) // 鏁版嵁婧�
             if (btn.output) {
               param.key_back_type = 'Y'
             }
           }
 
-          param.exec_type = 'y' // 鍚庡彴瑙g爜
+          param.exec_type = window.GLOB.execType || 'y' // 鍚庡彴瑙g爜
           param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
           param.secretkey = Utils.encrypt('', param.timestamp)
 
@@ -636,7 +608,7 @@
             param.LText = param.LText.replace(/\$check@|@check\$/ig, '')
           }
 
-          param.LText = Utils.formatOptions(param.LText)
+          param.LText = Utils.formatOptions(param.LText, param.exec_type)
         } else if (btn.OpenType === 'pop') { // 琛ㄥ崟
           if (index !== 0) {
             let _cell = {}
@@ -655,17 +627,17 @@
             param.ID = Utils.getguid()
 
             if (retmsg) {
-              const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, cell, columns, retmsg, this.moduleParams) // 鏁版嵁婧�
+              const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, cell, columns, retmsg) // 鏁版嵁婧�
               param.LText = sql
               param.$callbacksql = callbacksql
             } else {
-              param.LText = getSysDefaultSql(btn, setting, formdata, param, cell, columns, false, this.moduleParams) // 鏁版嵁婧�
+              param.LText = getSysDefaultSql(btn, setting, formdata, param, cell, columns, false) // 鏁版嵁婧�
               if (btn.output) {
                 param.key_back_type = 'Y'
               }
             }
 
-            param.exec_type = 'y' // 鍚庡彴瑙g爜
+            param.exec_type = window.GLOB.execType || 'y' // 鍚庡彴瑙g爜
             param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
             param.secretkey = Utils.encrypt('', param.timestamp)
 
@@ -676,22 +648,22 @@
               param.LText = param.LText.replace(/\$check@|@check\$/ig, '')
             }
 
-            param.LText = Utils.formatOptions(param.LText)
+            param.LText = Utils.formatOptions(param.LText, param.exec_type)
           } else {
             param.ID = primaryId
 
             if (retmsg) {
-              const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, cell, columns, retmsg, this.moduleParams) // 鏁版嵁婧�
+              const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, cell, columns, retmsg) // 鏁版嵁婧�
               param.LText = sql
               param.$callbacksql = callbacksql
             } else {
-              param.LText = getSysDefaultSql(btn, setting, formdata, param, cell, columns, false, this.moduleParams) // 鏁版嵁婧�
+              param.LText = getSysDefaultSql(btn, setting, formdata, param, cell, columns, false) // 鏁版嵁婧�
               if (btn.output) {
                 param.key_back_type = 'Y'
               }
             }
 
-            param.exec_type = 'y' // 鍚庡彴瑙g爜
+            param.exec_type = window.GLOB.execType || 'y' // 鍚庡彴瑙g爜
             param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
             param.secretkey = Utils.encrypt('', param.timestamp)
 
@@ -702,7 +674,7 @@
               param.LText = param.LText.replace(/\$check@|@check\$/ig, '')
             }
 
-            param.LText = Utils.formatOptions(param.LText)
+            param.LText = Utils.formatOptions(param.LText, param.exec_type)
           }
         }
 
@@ -721,7 +693,7 @@
 
         if (param.$unCheckParam) {
           param.$unCheckParam.LText = param.$unCheckParam.LText.replace(/\$check@/ig, '/*').replace(/@check\$/ig, '*/')
-          param.$unCheckParam.LText = Utils.formatOptions(param.$unCheckParam.LText)
+          param.$unCheckParam.LText = Utils.formatOptions(param.$unCheckParam.LText, param.exec_type)
           param.$unCheckParam.menuname = btn.logLabel
   
           if (window.GLOB.probation) {
@@ -734,6 +706,464 @@
     }
 
     return _params
+  }
+
+  getBackSystemParam = (data, formdata) => {
+    const { btn } = this.props
+
+    let ex = window.GLOB.CacheData.get('sql_' + btn.uuid)
+    let _params = []
+
+    if (btn.Ot === 'notRequired' || btn.Ot === 'requiredSgl' || btn.Ot === 'requiredOnce') {
+      let primaryId = ''
+      let cell = null
+
+      if (btn.Ot === 'requiredSgl' || btn.Ot === 'requiredOnce') {
+        primaryId = data.map(d => d.$$uuid).filter(Boolean).join(',')
+        cell = data[0]
+      }
+
+      if (btn.OpenType === 'pop' || btn.OpenType === 'formSubmit' || btn.OpenType === 'form') { // 琛ㄥ崟
+        if (btn.sqlType === 'insert') { // 绯荤粺鍑芥暟娣诲姞鏃讹紝鐢熸垚uuid
+          primaryId = Utils.getguid()
+        }
+      }
+
+      let exp = this.getExps(ex, formdata, cell, primaryId, btn.$process)
+
+      if (ex.reps.includes('mk_check_begin')) {
+        exp.$unCheckParam = fromJS(exp).toJS()
+
+        exp.data[0].exps.push({
+          key: 'mk_check_begin',
+          value: ''
+        }, {
+          key: 'mk_check_end',
+          value: ''
+        })
+        exp.$unCheckParam.data[0].exps.push({
+          key: 'mk_check_begin',
+          value: 'Y'
+        }, {
+          key: 'mk_check_end',
+          value: 'Y'
+        })
+      } else if (btn.procMode === 'system' && btn.callbackType === 'script') {
+        let _backex = window.GLOB.CacheData.get('sql_back_' + btn.uuid)
+        exp.$backParam = this.getExps(_backex, formdata, cell, primaryId)
+      }
+
+      _params.push(exp)
+    } else if (btn.Ot === 'required') {
+      _params = data.map((cell, index) => {
+        let primaryId = cell.$$uuid || ''
+
+        if (btn.OpenType === 'pop') { // 琛ㄥ崟
+          if (index !== 0) {
+            let _cell = {}
+            Object.keys(cell).forEach(key => {
+              _cell[key.toLowerCase()] = cell[key]
+            })
+            formdata = formdata.map(_data => {
+              if (_data.readin && _cell.hasOwnProperty(_data.key.toLowerCase())) {
+                _data.value = _cell[_data.key.toLowerCase()]
+              }
+              return _data
+            })
+          }
+
+          if (btn.sqlType === 'insert') { // 绯荤粺鍑芥暟娣诲姞鏃讹紝鐢熸垚uuid
+            primaryId = Utils.getguid()
+          }
+        }
+        let exp = this.getExps(ex, formdata, cell, primaryId, btn.$process)
+        if (ex.reps.includes('mk_check_begin')) {
+          exp.$unCheckParam = fromJS(exp).toJS()
+  
+          exp.data[0].exps.push({
+            key: 'mk_check_begin',
+            value: ''
+          }, {
+            key: 'mk_check_end',
+            value: ''
+          })
+          exp.$unCheckParam.data[0].exps.push({
+            key: 'mk_check_begin',
+            value: 'Y'
+          }, {
+            key: 'mk_check_end',
+            value: 'Y'
+          })
+        } else if (btn.procMode === 'system' && btn.callbackType === 'script') {
+          let _backex = window.GLOB.CacheData.get('sql_back_' + btn.uuid)
+          exp.$backParam = this.getExps(_backex, formdata, cell, primaryId)
+        }
+
+        return exp
+      })
+    }
+
+    return _params
+  }
+
+  getExps = (ex, formdata, cell, id, process) => {
+    const { columns, BID, btn } = this.props
+    let exps = []
+    let values = {
+      time_id: Utils.getguid(),
+      roleid: sessionStorage.getItem('role_id') || '',
+      mk_departmentcode: sessionStorage.getItem('departmentcode') || '',
+      mk_organization: sessionStorage.getItem('organization') || '',
+      mk_user_type: sessionStorage.getItem('mk_user_type') || '',
+      mk_nation: sessionStorage.getItem('nation') || '',
+      mk_province: sessionStorage.getItem('province') || '',
+      mk_city: sessionStorage.getItem('city') || '',
+      mk_district: sessionStorage.getItem('district') || '',
+      mk_address: sessionStorage.getItem('address') || '',
+      id: id || '',
+      bid: BID || '',
+      typename: 'admin',
+      datam: sessionStorage.getItem('dataM') === 'true' ? 'Y' : '',
+      datam_begin: sessionStorage.getItem('dataM') === 'true' ? 'Y' : '',
+      datam_end: sessionStorage.getItem('dataM') === 'true' ? 'Y' : '',
+      // mk_check_begin: '',
+      // mk_check_end: ''
+    }
+
+    if (window.GLOB.externalDatabase !== null) {
+      values.db = window.GLOB.externalDatabase
+    }
+
+    let formkeys = []
+    formdata && formdata.forEach(form => {
+      // if (!ex.reps.includes(form.key)) return
+
+      formkeys.push(form.key)
+
+      let val = form.value
+      if (form.type === 'number' || form.type === 'rate') {
+        if (isNaN(val)) {
+          val = 0
+        }
+      } else if (['date', 'datemonth'].includes(form.type)) {
+        val = val || '1949-10-01'
+      }
+
+      exps.push({
+        key: 'mk_' + form.key + '_mk',
+        value: val
+      })
+    })
+
+    if (cell && columns && columns.length > 0) {
+      let datavars = {}
+
+      Object.keys(cell).forEach(key => {
+        datavars[key.toLowerCase()] = cell[key]
+      })
+  
+      columns.forEach(col => {
+        if (!ex.reps.includes(col.field) || formkeys.includes(col.field)) return
+        if (!col.datatype) return
+
+        let _key = col.field.toLowerCase()
+        let _val = datavars.hasOwnProperty(_key) ? datavars[_key] : ''
+
+        if (/^date/ig.test(col.datatype) && !_val) {
+          _val = '1949-10-01'
+        }
+
+        exps.push({
+          key: 'mk_' + col.field + '_mk',
+          value: _val
+        })
+      })
+    }
+
+    ex.reps.forEach(n => {
+      let key = n.toLowerCase()
+      if (values.hasOwnProperty(key)) {
+        exps.push({
+          key: n,
+          value: values[key]
+        })
+      }
+    })
+
+    if (process && btn.verify.workFlow === 'true') {
+      let flow = window.GLOB.UserCacheMap.get(btn.$flowId)
+      let node = null
+      let line = null
+      let target = null
+      let status = 0
+      let statusName = ''
+      let detailId = ''
+      let sign = ''
+      let error = ''
+      let userid = sessionStorage.getItem('UserID') || ''
+      let checkIds = []
+      let checkUsers = []
+      let noticeIds = []
+      let work_grade = sessionStorage.getItem('work_grade') || 0
+      let departmentcode = sessionStorage.getItem('departmentcode') || ''
+      let _data = cell || {}
+      let msg = ''
+  
+      if (btn.verify.flowType === 'start') {
+        target = flow ? flow.cells.filter(cell => cell.mknode === 'start')[0] : ''
+  
+        if (target) {
+          detailId = target.id
+          status = target.mkdata.status
+          statusName = target.mkdata.statusName
+        } else {
+          error = '宸ヤ綔娴佹棤寮�濮嬭妭鐐�'
+        }
+      } else if (_data.works_flow_param) {
+        try {
+          node = JSON.parse(window.decodeURIComponent(window.atob(_data.works_flow_param)))
+        } catch (e) {
+          node = null
+        }
+  
+        if (node) {
+          let lines = flow ? flow.cells.filter(cell => cell.shape === 'edge' && cell.source.cell === node.id) : []
+          if (btn.verify.flowType === 'reject') {
+            line = lines.filter(cell => cell.mkdata.flowType === 'reject' || cell.mknode === 'startEdge')[0]
+          } else {
+            lines = lines.filter(cell => cell.mkdata.flowType !== 'reject' && cell.mknode !== 'startEdge')
+  
+            if (lines.length === 0) {
+              error = '鏃犲彲鎵ц鐨勬祦绋嬪垎鏀�'
+            } else {
+              let branchKey = btn.verify.flowBranch ? btn.verify.flowBranch.toLowerCase() : ''
+  
+              formdata && formdata.forEach(form => {
+                let _key = form.key.toLowerCase()
+                _data[_key] = form.value
+              })
+  
+              if (!branchKey) {
+                lines.forEach(line => {
+                  if (line.mkdata.execCondition === 'open') {
+                    error = '鎸夐挳鏈缃祦绋嬫帶鍒跺瓧娈点��'
+                  }
+                })
+                if (!error) {
+                  lines = lines.filter(cell => {
+                    if (cell.mkdata.seniorCondition === 'open' && !line) {
+                      cell.mkdata.seniorbers && cell.mkdata.seniorbers.forEach(per => {
+                        if (per.worker_id === userid) {
+                          line = cell
+                        }
+                      })
+                      return false
+                    }
+                    return true
+                  })
+
+                  if (!line) {
+                    line = lines[0]
+                  }
+                }
+              } else if (!_data.hasOwnProperty(branchKey)) {
+                error = '淇℃伅涓棤娴佺▼鎺у埗瀛楁銆�'
+              } else {
+                let _def_lines = []
+                let _equ_lines = []
+                let _unequ_lines = []
+                let _or_lines = []
+                let branchVal = _data[branchKey]
+  
+                if (branchVal && typeof(branchVal) === 'string' && !isNaN(branchVal)) {
+                  branchVal = +branchVal
+                }
+  
+                lines.forEach(item => {
+                  if (item.mkdata.execCondition !== 'open') {
+                    _def_lines.push(item)
+                  } else {
+                    if (item.mkdata.match === '=') {
+                      if (item.mkdata.matchVal === branchVal + '') {
+                        _equ_lines.push(item)
+                      }
+                    } else if (item.mkdata.match === '!=') {
+                      if (item.mkdata.matchVal !== branchVal + '') {
+                        _unequ_lines.push(item)
+                      }
+                    } else {
+                      if (item.mkdata.match === '<') {
+                        if (item.mkdata.matchVal < branchVal) {
+                          _or_lines.push({...item, dist: Math.abs(item.mkdata.matchVal - branchVal)})
+                        }
+                      } else if (item.mkdata.match === '>') {
+                        if (item.mkdata.matchVal > branchVal) {
+                          _or_lines.push({...item, dist: Math.abs(item.mkdata.matchVal - branchVal)})
+                        }
+                      } else if (item.mkdata.match === '<=') {
+                        if (item.mkdata.matchVal <= branchVal) {
+                          _or_lines.push({...item, dist: Math.abs(item.mkdata.matchVal - branchVal)})
+                        }
+                      } else if (item.mkdata.match === '>=') {
+                        if (item.mkdata.matchVal >= branchVal) {
+                          _or_lines.push({...item, dist: Math.abs(item.mkdata.matchVal - branchVal)})
+                        }
+                      }
+                    }
+                  }
+                })
+  
+                _or_lines.sort((a, b) => a.dist - b.dist)
+  
+                let _lines = [..._equ_lines, ..._or_lines, ..._unequ_lines, ..._def_lines]
+  
+                _lines = _lines.filter(cell => {
+                  if (cell.mkdata.seniorCondition === 'open' && !line) {
+                    cell.mkdata.seniorbers && cell.mkdata.seniorbers.forEach(per => {
+                      if (per.worker_id === userid) {
+                        line = cell
+                      }
+                    })
+                    return false
+                  }
+                  return true
+                })
+                
+                if (!line) {
+                  line = _lines[0]
+                }
+              }
+            }
+          }
+        } else {
+          error = '琛屼俊鎭腑宸ヤ綔娴佸弬鏁版棤娉曡В鏋�'
+        }
+        
+        if (line) {
+          detailId = line.id
+          status = line.mkdata.status
+          statusName = line.mkdata.statusName
+          sign = line.mkdata.seniorSign || ''
+          target = flow.cells.filter(cell => cell.id === line.target.cell)[0]
+  
+          line.mkdata.members && line.mkdata.members.forEach(item => {
+            if (line.mkdata.approver === 'departmentManager') {
+              if (item.job_type === 'manage' && departmentcode === item.parentIds[1]) {
+                checkIds.push(item.worker_id)
+                checkUsers.push(item)
+              }
+            } else if (line.mkdata.approver === 'directManager') {
+              if (departmentcode === item.parentIds[1] && item.work_grade > work_grade) {
+                checkIds.push(item.worker_id)
+                checkUsers.push(item)
+              }
+            } else {
+              checkIds.push(item.worker_id)
+              checkUsers.push(item)
+            }
+          })
+          line.mkdata.copys && line.mkdata.copys.forEach(item => {
+            noticeIds.push(item.worker_id)
+          })
+  
+          if (!target) {
+            error = '鏈煡璇㈠埌宸ヤ綔娴佺洰鏍囪妭鐐�'
+          } else if (checkIds.length === 0 && !['startEdge', 'endEdge', 'throughEdge'].includes(line.mknode)) {
+            error = '鏈幏鍙栧埌涓嬩竴姝ュ鎵逛汉'
+          } else if (line.approvalMethod === 'countersign' && (!node.checkIds || !node.checkIds.includes(userid))) {
+            error = '褰撳墠鐢ㄦ埛涓嶅湪瀹℃壒浜哄垪琛ㄤ腑'
+          }
+        } else if (!error) {
+          error = '宸ヤ綔娴佷腑鏃犲搴旀祦绋�'
+        }
+      } else {
+        error = '琛屼俊鎭腑鏃犲伐浣滄祦鍙傛暟'
+      }
+
+      if (error) {
+        status = 0
+        statusName = '寮傚父'
+      } else if (target) {
+        let label = target.attrs && target.attrs.text && target.attrs.text.text ? target.attrs.text.text : ''
+        msg = {...target.mkdata, label: label, id: target.id, checkIds: [], checkUsers: []}
+        msg = window.btoa(window.encodeURIComponent(JSON.stringify(msg)))
+      }
+  
+      if (btn.verify.flowType === 'start') {
+        exps.push(
+          { key: 'works_flow_error', value: error },
+          { key: 'works_flow_code', value: flow ? flow.flow_code : '' },
+          { key: 'works_flow_name', value: flow ? flow.flow_name : '' },
+          { key: 'works_flow_param', value: msg },
+          { key: 'works_flow_detail_id', value: detailId },
+          { key: 'status', value: status },
+          { key: 'statusname', value: statusName },
+          { key: 'work_group', value: sessionStorage.getItem('work_group') || '' },
+          { key: 'work_grade', value: sessionStorage.getItem('work_grade') || 0 },
+          // { key: 'start_type', value: '寮�濮�' },
+        )
+      } else {
+        let works_flow_countersign = ''
+        let works_flow_sign_values = ''
+        let works_flow_sign_field = ''
+        let works_flow_sign_label = ''
+        let works_begin_branch = ''
+        if (line.approvalMethod === 'countersign' && node.checkIds.length > 1) {
+          works_flow_countersign = 'Y'
+          let mark = line.mark || '宸插鏍�'
+          let fields = ['statuscharone', 'statuschartwo', 'statuscharthree', 'statuscharfour', 'statuscharfive']
+          node.checkUsers.forEach((user, index) => {
+            if (user.worker_id === userid) {
+              works_flow_sign_field = fields[index]
+              works_flow_sign_label = `${user.parentNames[2] || ''}${user.workername || ''}${mark}`
+            } else {
+              works_flow_sign_values += `${user.parentNames[2] || ''}${user.workername || ''}${mark}`
+            }
+          })
+        } else {
+          works_begin_branch = line.mknode === 'startEdge' ? 'Y' : ''
+        }
+
+        exps.push(
+          { key: 'works_flow_error', value: error },
+          { key: 'works_flow_countersign', value: works_flow_countersign },
+          { key: 'works_flow_sign_values', value: works_flow_sign_values },
+          { key: 'works_begin_branch', value: works_begin_branch },
+          { key: 'works_flow_sign_field', value: works_flow_sign_field },
+          { key: 'works_flow_sign_label', value: works_flow_sign_label },
+          { key: 'works_flow_code', value: flow ? flow.flow_code : '' },
+          { key: 'works_flow_name', value: flow ? flow.flow_name : '' },
+          { key: 'works_flow_param', value: msg },
+          { key: 'works_flow_detail_id', value: detailId },
+          { key: 'status', value: status },
+          { key: 'statusname', value: statusName },
+          { key: 'work_group', value: sessionStorage.getItem('work_group') || '' },
+          { key: 'work_grade', value: sessionStorage.getItem('work_grade') || 0 },
+          // { key: 'check_type', value: btn.verify.flowType === 'reject' ? '椹冲洖' : '瀹℃牳' },
+          // { key: 'notice_type', value: '鎶勯��' },
+          { key: 'check_userids', value: checkIds.join(',') },
+          { key: 'notice_userids', value: noticeIds.join(',') },
+          { key: 'works_flow_sign', value: sign },
+        )
+      }
+    }
+
+    let md5_id = ''
+    if (window.GLOB.probation) {
+      md5_id = md5(ex.id + JSON.stringify(exps) + Math.floor(new Date().getTime() / 600000))
+      md5_id = moment().format('YYYYMMDDHHmmss') + md5_id.slice(-18)
+    }
+
+    return {
+      $backend: true,
+      $type: 's_TableData_InUpDe',
+      data: [{
+        id: ex.id,
+        menuname: btn.logLabel || '',
+        exps: exps,
+        md5_id: md5_id
+      }]
+    }
   }
 
   getInnerParam = (data, formdata, retmsg) => {
@@ -755,11 +1185,14 @@
         param.username = sessionStorage.getItem('User_Name') || ''
         param.fullname = sessionStorage.getItem('Full_Name') || ''
       }
+      if (btn.dataM === 'true') {
+        param.dataM = sessionStorage.getItem('dataM') === 'true' ? 'Y' : ''
+      }
       
       let primaryId = ''
 
       if ((btn.Ot === 'requiredSgl' || btn.Ot === 'requiredOnce') && setting.primaryKey) {
-        let ids = data.map(d => { return d[setting.primaryKey] || ''})
+        let ids = data.map(d => d.$$uuid)
         ids = ids.filter(Boolean)
         primaryId = ids.join(',')
 
@@ -778,7 +1211,10 @@
         param.open_key = Utils.encryptOpenKey(param.secretkey, param.timestamp)
       }
 
-      if (retmsg) {
+      if (btn.callbackType === 'script' && window.backend && window.GLOB.CacheData.has('sql_back_' + btn.uuid)) {
+        let _backex = window.GLOB.CacheData.get('sql_back_' + btn.uuid)
+        param.$backParam = this.getExps(_backex, formdata, data[0], primaryId)
+      } else if (retmsg) {
         param.$callbacksql = this.getSysDeclareSql(btn, formdata, data[0], columns, this.props.BID)
       }
 
@@ -797,8 +1233,11 @@
           param.username = sessionStorage.getItem('User_Name') || ''
           param.fullname = sessionStorage.getItem('Full_Name') || ''
         }
+        if (btn.dataM === 'true') {
+          param.dataM = sessionStorage.getItem('dataM') === 'true' ? 'Y' : ''
+        }
 
-        let primaryId = setting.primaryKey ? cell[setting.primaryKey] || '' : ''
+        let primaryId = cell.$$uuid || ''
 
         if (btn.OpenType === 'pop') { // 琛ㄥ崟
           if (index !== 0) {
@@ -828,7 +1267,10 @@
           param.open_key = Utils.encryptOpenKey(param.secretkey, param.timestamp)
         }
 
-        if (retmsg) {
+        if (btn.callbackType === 'script' && window.backend && window.GLOB.CacheData.has('sql_back_' + btn.uuid)) {
+          let _backex = window.GLOB.CacheData.get('sql_back_' + btn.uuid)
+          param.$backParam = this.getExps(_backex, formdata, cell, primaryId)
+        } else if (retmsg) {
           param.$callbacksql = this.getSysDeclareSql(btn, formdata, cell, columns, this.props.BID)
         }
 
@@ -1018,53 +1460,10 @@
    * @description 鎸夐挳鎻愪氦鎵ц
    */
   execSubmit = (data, _resolve, formdata, force) => {
-    const { setting, btn } = this.props
-    this.moduleParams = null
+    const { btn } = this.props
 
     if (btn.preButton && !force) {
       this.trigger(btn.preButton, data, _resolve, formdata, 0)
-    } else if (btn.verify && btn.verify.invalid === 'true' && setting.dataresource) {
-      MKEmitter.emit('queryModuleParam', btn.$menuId, (param) => {
-        let datasource = setting.dataresource
-        let customScript = setting.customScript || ''
-        let allSearch = Utils.getAllSearchOptions(param.search)
-
-        let regoptions = allSearch.map(item => {
-          return {
-            reg: new RegExp('@' + item.key + '@', 'ig'),
-            value: `'${item.value}'`
-          }
-        })
-
-        regoptions.push({
-          reg: new RegExp('@userName@', 'ig'),
-          value: `'${sessionStorage.getItem('User_Name') || ''}'`
-        }, {
-          reg: new RegExp('@fullName@', 'ig'),
-          value: `'${sessionStorage.getItem('Full_Name') || ''}'`
-        }, {
-          reg: new RegExp('@orderBy@', 'ig'),
-          value: setting.order
-        }, {
-          reg: new RegExp('@pageSize@', 'ig'),
-          value: 10
-        }, {
-          reg: new RegExp('@pageIndex@', 'ig'),
-          value: 1
-        })
-
-        regoptions.forEach(item => {
-          datasource = datasource.replace(item.reg, item.value)
-          customScript = customScript.replace(item.reg, item.value)
-        })
-
-        this.moduleParams = {
-          datasource,
-          customScript
-        }
-
-        this.execRealSubmit(data, _resolve, formdata)
-      })
     } else {
       this.execRealSubmit(data, _resolve, formdata)
     }
@@ -1074,7 +1473,7 @@
     if (times > 50) {
       notification.warning({
         top: 92,
-        message: '鍓嶇疆鎸夐挳鍔犺浇澶辫触锛�',
+        message: window.GLOB.dict['pre_btn_failed'] || '鍓嶇疆鎸夐挳鍔犺浇澶辫触锛�',
         duration: 5
       })
       this.setState({loading: false})
@@ -1086,7 +1485,7 @@
     let node = document.getElementById('button' + btnId)
 
     if (node) {
-      MKEmitter.emit('triggerBtnId', btnId, null, 'preButton', (res) => {
+      MKEmitter.emit('triggerBtnId', btnId, null, 'preButton', null, (res) => {
         if (!res) {
           this.setState({loading: false})
           resolve()
@@ -1112,7 +1511,7 @@
     if (setting.supModule && !BID) {
       notification.warning({
         top: 92,
-        message: '闇�瑕佷笂绾т富閿�硷紒',
+        message: window.GLOB.dict['sup_key_req'] || '闇�瑕佷笂绾т富閿�硷紒',
         duration: 5
       })
       _resolve()
@@ -1122,8 +1521,22 @@
     if (btn.intertype === 'system' || btn.intertype === 'inner') { // 绯荤粺鎺ュ彛
       let params = []
 
-      if (btn.intertype === 'system') {
+      if (btn.intertype === 'system' && window.backend && window.GLOB.CacheData.has('sql_' + btn.uuid)) {
+        params = this.getBackSystemParam(data, formdata)
+      } else if (btn.intertype === 'system') {
         params = this.getSystemParam(data, formdata)
+        if (btn.returnValue === 'true') {
+          params = params.map(item => {
+            item.script_type = 'Y'
+            return item
+          })
+        }
+        if (btn.database === 'sso' && window.GLOB.mainSystemApi) {
+          params = params.map(item => {
+            item.rduri = window.GLOB.mainSystemApi
+            return item
+          })
+        }
       } else {
         params = this.getInnerParam(data, formdata)
       }
@@ -1170,6 +1583,14 @@
           _resolve()
         })
       } else if (params.length <= 20 && btn.execType !== 'single') {
+        if (window.backend && params[0].$backend && (!btn.verify || (btn.verify.printEnable !== 'true' && !btn.output))) {
+          params = [{
+            $backend: true,
+            $type: 's_TableData_InUpDe',
+            data: params.map(item => item.data[0])
+          }]
+        }
+
         let deffers = params.map((param, i) => {
           return new Promise(resolve => {
             setTimeout(() => {
@@ -1217,7 +1638,9 @@
       /** *********************璋冪敤澶栭儴鎺ュ彛************************* */
       let _params = [] // 璇锋眰鍙傛暟鏁扮粍
 
-      if (btn.procMode === 'system') {
+      if (btn.procMode === 'system' && window.backend && window.GLOB.CacheData.has('sql_' + btn.uuid)) {
+        _params = this.getBackSystemParam(data, formdata)
+      } else if (btn.procMode === 'system') {
         _params = this.getSystemParam(data, formdata, true)
         _params = _params.map(item => {
           item.script_type = 'Y'
@@ -1238,7 +1661,9 @@
     } else if (btn.intertype === 'custom') { // 绯荤粺鎺ュ彛
       let params = []
 
-      if (btn.procMode === 'system') {
+      if (btn.procMode === 'system' && window.backend && window.GLOB.CacheData.has('sql_' + btn.uuid)) {
+        params = this.getBackSystemParam(data, formdata)
+      } else if (btn.procMode === 'system') {
         params = this.getSystemParam(data, formdata, true)
         params = params.map(item => {
           item.script_type = 'Y'
@@ -1274,13 +1699,15 @@
       BID: param.BID || '',
       ID: param.ID || '',
       callbacksql: param.$callbacksql || '',
-      mk_api_key: ''
+      mk_api_key: '',
+      backParam: param.$backParam || ''
     }
 
     if (!record.ID && btn.Ot !== 'notRequired' && param[setting.primaryKey]) {
       record.ID = param[setting.primaryKey]
     }
 
+    delete param.$backParam
     delete param.$callbacksql
 
     if (param.$pice) {
@@ -1290,12 +1717,12 @@
 
       this.customOuterRequest(params, param, record, _resolve)
       return
-    } else if (!param.func) {
+    } else if (!param.func && !param.$backend) {
       this.customOuterRequest(params, param, record, _resolve)
       return
     }
 
-    Api.genericInterface(param).then(res => {
+    Api.genericInterface(param, btn.$innerScript, 'inner').then(res => {
       record.mk_api_key = res.mk_api_key || ''
 
       if (res.status) {
@@ -1344,7 +1771,7 @@
   // Api.directRequest('http://localhost:3001/test.xml', 'get', null, 'true').then(res => {
   //   let $x2js = new x2js()
   //   let jsonObj = $x2js.xml2js(res);
-  //   console.info(jsonObj)
+  //   window.mkInfo(jsonObj)
   // })
 
   /**
@@ -1386,7 +1813,21 @@
       method: btn.method || 'post'
     }
 
-    if (btn.cross === 'true') {
+    if (btn.ContentType) {
+      _params.headers = {
+        'Content-Type': btn.ContentType
+      }
+    }
+
+    if (btn.$outerScript) {
+      if (JSON.stringify(param) !== '{}') {
+        if (btn.stringify === 'qs') {
+          _params.data = qs.stringify(param)
+        } else {
+          _params.data = param
+        }
+      }
+    } else if (btn.cross === 'true') {
       if (JSON.stringify(param) !== '{}') {
         if (btn.stringify === 'qs') {
           _params.data = qs.stringify(param)
@@ -1420,13 +1861,7 @@
       _params.method = 'post'
     }
 
-    if (btn.ContentType) {
-      _params.headers = {
-        'Content-Type': btn.ContentType
-      }
-    }
-
-    Api.directRequest(_params).then(res => {
+    Api.directRequest(_params, btn.$outerScript, 'outer').then(res => {
       if (typeof(res) !== 'object') {
         let error = '鏈煡鐨勮繑鍥炵粨鏋滐紒'
 
@@ -1493,6 +1928,8 @@
         _resolve()
       }
       return
+    } else if (btn.callbackType === 'script' && record.backParam) {
+      param = this.getCallBackendParam(result, record)
     } else if (btn.callbackType === 'script' || btn.callbackType === 'default') {
       param = this.getCallBackSql(result, record)
     } else if (btn.callbackType === 'func') {
@@ -1535,7 +1972,7 @@
       param.menuname = param.menuname + '(鍥炶皟)'
     }
 
-    Api.genericInterface(param).then(res => {
+    Api.genericInterface(param, btn.$callbackScript, 'callback').then(res => {
       if (res.status) {
         this.triggerNote(res, param.ID) // 娑堟伅
 
@@ -1554,6 +1991,108 @@
       this.updateStatus()
       _resolve()
     })
+  }
+
+  getCallBackendParam = (result, record) => {
+    const { btn } = this.props
+    let lines = []
+    let tables = []
+    let param = fromJS(record.backParam).toJS()
+
+    btn.verify.cbScripts.forEach(script => {
+      if (script.status === 'false') return
+
+      if (/\s#[a-z0-9_]+(\s|\()/ig.test(script.sql)) {
+        tables.push(...script.sql.match(/\s#[a-z0-9_]+(\s|\()/ig))
+      }
+    })
+
+    tables = tables.map(tb => tb.replace(/\s|\(/g, ''))
+
+    if (result.$ErrCode) {
+      delete result.$ErrCode
+      delete result.$ErrMesg
+    }
+
+    let getDefaultSql = (obj, tb, bid, level) => {
+      let vals = {}
+      let subObjs = []
+      let id = Utils.getuuid()
+
+      delete obj.$$key
+
+      Object.keys(obj).forEach(key => {
+        let val = obj[key]
+        if (val === null || val === undefined) return
+        if (typeof(val) === 'object') {
+          if (Array.isArray(val)) {
+            val.forEach(item => {
+              if (typeof(item) !== 'object' || Array.isArray(item)) return
+              if (Object.keys(item).length === 0) return
+
+              Object.keys(item).forEach(k => {
+                if (item[k] === null) {
+                  item[k] = ''
+                }
+              })
+              item.$$key = tb + '_' + key
+              subObjs.push(item)
+            })
+          } else if (Object.keys(val).length > 0) {
+            val.$$key = tb + '_' + key
+            subObjs.push(val)
+          }
+        } else {
+          if (typeof(val) === 'string') {
+            val = val.replace(/'/ig, '"')
+          } else {
+            val = val + ''
+          }
+          vals[key] = val
+        }
+      })
+
+      vals.mk_level = level
+      vals.mk_id = id
+      vals.mk_bid = bid
+
+      let isnew = true
+      lines.forEach(line => {
+        if (line.tb === tb) {
+          line.values.push(vals)
+          isnew = false
+        }
+      })
+      if (isnew) {
+        lines.push({
+          tb: tb,
+          type: tables.includes('#' + tb) ? '01' : '02',
+          values: [vals]
+        })
+      }
+
+      subObjs.forEach(item => {
+        getDefaultSql(item, item.$$key, id, level + 1)
+      })
+    }
+    
+    getDefaultSql(result, btn.cbTable, '', 1)
+
+    param.data[0].exps.push({
+      key: 'mk_outer_params',  // 鍥炶皟鑴氭湰鐨勬暟鎹浛鎹�
+      value: lines
+    })
+
+    let md5_id = ''
+    if (window.GLOB.probation) {
+      md5_id = md5('back_' + btn.uuid + JSON.stringify(param.data[0].exps) + Math.floor(new Date().getTime() / 600000))
+      md5_id = moment().format('YYYYMMDDHHmmss') + md5_id.slice(-18)
+    }
+
+    param.data[0].md5_id = md5_id
+    param.data[0].menuname = btn.logLabel + '(鍥炶皟)'
+
+    return param
   }
 
   getCallBackSql = (result, record) => {
@@ -1606,10 +2145,15 @@
           if (Array.isArray(val)) {
             val.forEach(item => {
               if (typeof(item) !== 'object' || Array.isArray(item)) return
-              if (Object.keys(item).length > 0) {
-                item.$$key = tb + '_' + key
-                subObjs.push(item)
-              }
+              if (Object.keys(item).length === 0) return
+
+              Object.keys(item).forEach(k => {
+                if (item[k] === null) {
+                  item[k] = ''
+                }
+              })
+              item.$$key = tb + '_' + key
+              subObjs.push(item)
             })
           } else if (Object.keys(val).length > 0) {
             val.$$key = tb + '_' + key
@@ -1625,11 +2169,12 @@
       })
 
       keys = keys.join(',')
+      vals = vals.join(',')
 
       lines.push({
         table: md5(tb + keys),
-        insert: `Insert into ${tbName} (${keys},[mk_level],[mk_id],[mk_bid])`,
-        select: `Select ${vals.join(',')},'${level}','${id}','${bid}'`
+        insert: `Insert into ${tbName} (${keys ? keys + ',' : ''}[mk_level],[mk_id],[mk_bid])`,
+        select: `Select ${keys ? vals + ',' : ''}'${level}','${id}','${bid}'`
       })
 
       subObjs.forEach(item => {
@@ -1712,24 +2257,25 @@
       sql = sql.replace(/@SessionUid@/ig, `'${localStorage.getItem('SessionUid') || ''}'`)
       sql = sql.replace(/@UserID@/ig, `'${sessionStorage.getItem('UserID') || ''}'`)
       sql = sql.replace(/@Appkey@/ig, `'${window.GLOB.appkey || ''}'`)
+      sql = sql.replace(/@lang@/ig, `'${sessionStorage.getItem('lang')}'`)
       sql = sql.replace(/@typename@/ig, `'admin'`)
 
       if (sessionStorage.getItem('dataM') === 'true') { // 鏁版嵁鏉冮檺
-        sql = sql.replace(/\$@/ig, '/*').replace(/@\$/ig, '*/').replace(/@datam@/ig, '\'Y\'')
+        sql = sql.replace(/\$@/ig, '/*').replace(/@\$/ig, '*/').replace(/@datam@/ig, `'Y'`)
       } else {
-        sql = sql.replace(/@\$|\$@/ig, '').replace(/@datam@/ig, '\'\'')
+        sql = sql.replace(/@\$|\$@/ig, '').replace(/@datam@/ig, `''`)
       }
 
       if (window.GLOB.debugger === true) {
-        console.info('%c' + btn.logLabel + '(鍥炶皟)', 'color: blue')
-        console.info(sql.replace(/\n\s{8}/ig, '\n'))
+        window.mkInfo('%c' + btn.logLabel + '(鍥炶皟)', 'color: blue')
+        window.mkInfo(sql.replace(/\n\s{8}/ig, '\n'))
       }
 
       param.LText = sql
-      param.exec_type = 'y' // 鍚庡彴瑙g爜
+      param.exec_type = window.GLOB.execType || 'y' // 鍚庡彴瑙g爜
       param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
       param.secretkey = Utils.encrypt('', param.timestamp)
-      param.LText = Utils.formatOptions(param.LText)
+      param.LText = Utils.formatOptions(param.LText, param.exec_type)
       param.menuname = btn.logLabel
 
       if (window.GLOB.probation) {
@@ -1756,7 +2302,7 @@
           `)}
         `))
         sql = sql.join('')
-        console.info(sql.replace(/\n\s{10}/ig, '\n'))
+        window.mkInfo(sql.replace(/\n\s{10}/ig, '\n'))
       }
     }
 
@@ -1823,24 +2369,26 @@
           msg = msg.replace(/\n|\r/ig, '<br/>')
           msg = <span dangerouslySetInnerHTML={{__html: msg}}></span>
         }
-        const _this = this
+        const that = this
         confirm({
-          title: '璇风‘璁�',
+          title: window.GLOB.dict['exec_sure'] || '璇风‘璁�',
           content: msg,
+          okText: window.GLOB.dict['ok'] || '纭畾',
+          cancelText: window.GLOB.dict['cancel'] || '鍙栨秷',
           onOk() {
             return new Promise(resolve => {
               Api.genericInterface(unCheckParam).then(result => {
                 if (result.status) {
-                  _this.triggerNote(result, param.ID) // 娑堟伅
+                  that.triggerNote(result, param.ID) // 娑堟伅
           
                   if (params.length === 0) {
-                    _this.execSuccess(result)
+                    that.execSuccess(result)
                     _resolve()
                   } else {
-                    _this.checkLoopRequest(params, _resolve)
+                    that.checkLoopRequest(params, _resolve)
                   }
                 } else {
-                  _this.execError(result)
+                  that.execError(result)
                   _resolve()
                 }
                 resolve()
@@ -1848,7 +2396,7 @@
             })
           },
           onCancel() {
-            _this.execError(res)
+            that.execError(res)
             _resolve()
           }
         })
@@ -1878,21 +2426,23 @@
     let record = {
       BID: param.BID || '',
       ID: param.ID || '',
-      callbacksql: param.$callbacksql || ''
+      callbacksql: param.$callbacksql || '',
+      backParam: param.$backParam || ''
     }
 
     if (!record.ID && btn.Ot !== 'notRequired' && param[setting.primaryKey]) {
       record.ID = param[setting.primaryKey]
     }
 
+    delete param.$backParam
     delete param.$callbacksql
 
-    if (!param.func) {
+    if (!param.func && !param.$backend) {
       this.outerOuterRequest(params, param, record, _resolve)
       return
     }
 
-    Api.genericInterface(param).then(res => {
+    Api.genericInterface(param, btn.$innerScript, 'inner').then(res => {
       if (res.status) {
         if ((res.mk_ex_invoke === 'false' || res.mk_ex_invoke === false) && params.length === 0) {
           this.execSuccess(res)
@@ -1990,7 +2540,7 @@
       }
     }
 
-    Api.genericInterface(result).then(res => {
+    Api.genericInterface(result, btn.$outerScript, 'outer').then(res => {
       if (!res) return // LoginError鏃朵腑鏂姹�
       if (ver_token && res.ErrCode === 'token_error') {
         res.ErrCode = 'E'
@@ -2041,6 +2591,8 @@
         _resolve()
       }
       return
+    } else if (btn.callbackType === 'script' && record.backParam) {
+      param = this.getCallBackendParam(result, record)
     } else if (btn.callbackType === 'script' || btn.callbackType === 'default') {
       param = this.getCallBackSql(result, record)
     } else if (btn.callbackType === 'func' || btn.callbackFunc) {
@@ -2053,11 +2605,14 @@
         func: btn.callbackFunc
       }
 
-      // special 鍑芥暟 s_sDataDictb_TBBack 浜戠楠岃瘉
-      if (window.GLOB.mkHS && param.func === 's_sDataDictb_TBBack' && param.LTextOut) {
-        param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
-        param.secretkey = Utils.encrypt(param.LTextOut, param.timestamp)
-        param.open_key = Utils.encryptOpenKey(param.secretkey, param.timestamp)
+      if (window.GLOB.mkHS) {
+        if (btn.callbackFunc === 's_sVersion_Local_add' && window.GLOB.forcedUpdate) { // special 浼犺緭鍙锋坊鍔犲洖璋冨鐞�
+          param.local_userid = sessionStorage.getItem('LocalUserID') || ''
+        } else if (btn.callbackFunc === 's_sDataDictb_TBBack' && param.LTextOut) { // special 鍑芥暟 s_sDataDictb_TBBack 浜戠楠岃瘉
+          param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
+          param.secretkey = Utils.encrypt(param.LTextOut, param.timestamp)
+          param.open_key = Utils.encryptOpenKey(param.secretkey, param.timestamp)
+        }
       }
     } else {
       if (result.status) {
@@ -2079,7 +2634,7 @@
       param.menuname = param.menuname + '(鍥炶皟)'
     }
 
-    Api.genericInterface(param).then(res => {
+    Api.genericInterface(param, btn.$callbackScript, 'callback').then(res => {
       if (res.status) {
         this.triggerNote(res, param.ID) // 娑堟伅
 
@@ -2103,30 +2658,77 @@
     delete result.message
     delete result.status
 
-    result.func = btn.callbackFunc
-
     let ssoParam = null
+    let sinParam = null
     let callParam = {...outParam, ...result}
 
-    if (callParam.LTextOut) {
-      callParam.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
-      callParam.secretkey = Utils.encrypt(callParam.LTextOut, callParam.timestamp)
-      callParam.open_key = Utils.encryptOpenKey(callParam.secretkey, callParam.timestamp)
-    }
-
+    callParam.func = btn.callbackFunc
     callParam.userid = sessionStorage.getItem('LocalUserID') || ''
     callParam.LoginUID = sessionStorage.getItem('LocalLoginUID') || ''
 
-    if (callParam.UpType === 'SSO' && window.GLOB.localSystemApi) {
+    if (result.LTextOut) {
+      callParam.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
+      callParam.secretkey = Utils.encrypt(callParam.LTextOut, callParam.timestamp)
+      callParam.open_key = Utils.encryptOpenKey(callParam.secretkey, callParam.timestamp)
+    } else {
+      callParam = {...outParam}
+      callParam.func = btn.callbackFunc
+      callParam.MenuNO = 'sVersionDetail_LocalM'
+      callParam.UpType = 'SSO'
+      callParam.LTextOut = 'minke'
+      callParam.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
+      callParam.secretkey = Utils.encrypt(callParam.LTextOut, callParam.timestamp)
+      callParam.open_key = Utils.encryptOpenKey(callParam.secretkey, callParam.timestamp)
+      callParam.userid = sessionStorage.getItem('LocalUserID') || ''
+      callParam.LoginUID = sessionStorage.getItem('LocalLoginUID') || ''
+
+      delete result.ErrCode
+      delete result.ErrMesg
+
+      sinParam = {...result}
+      sinParam.func = 'sPC_TrdMenu_AddUpt_sso'
+
+      if (window.GLOB.sysType === 'local') {
+        if (!window.GLOB.systemType && window.GLOB.cloudServiceApi) {
+          sinParam.rduri = window.GLOB.cloudServiceApi
+        } else if (window.GLOB.localSystemApi) {
+          sinParam.rduri = window.GLOB.localSystemApi
+          sinParam.userid = sessionStorage.getItem('LocalUserID') || ''
+          sinParam.LoginUID = sessionStorage.getItem('LocalLoginUID') || ''
+        }
+      }
+    }
+    
+    if (result.UpType === 'SSO' && window.GLOB.localSystemApi) {
       ssoParam = fromJS(callParam).toJS()
       ssoParam.rduri = window.GLOB.localSystemApi
 
       delete ssoParam.UpType
-    } else {
-      delete callParam.UpType
     }
 
-    if (ssoParam) {
+    if (sinParam) {
+      Api.genericInterface(sinParam).then(res => {
+        if (!res.status) {
+          this.execError(res)
+          _resolve()
+        } else {
+          Api.genericInterface(callParam).then(re => {
+            if (!re.status) {
+              this.execError(re)
+              _resolve()
+            } else {
+              if (params.length === 0) {
+                this.clearBackCache()
+                this.execSuccess(res)
+                _resolve()
+              } else {
+                this.outerLoopRequest(params, _resolve)
+              }
+            }
+          })
+        }
+      })
+    } else if (ssoParam) {
       Api.genericInterface(ssoParam).then(res => {
         if (!res.status) {
           this.execError(res)
@@ -2138,6 +2740,7 @@
               _resolve()
             } else {
               if (params.length === 0) {
+                this.clearBackCache()
                 this.execSuccess(res)
                 _resolve()
               } else {
@@ -2154,6 +2757,7 @@
           _resolve()
         } else {
           if (params.length === 0) {
+            this.clearBackCache()
             this.execSuccess(re)
             _resolve()
           } else {
@@ -2162,6 +2766,34 @@
         }
       })
     }
+  }
+
+  clearBackCache = () => {
+    if (!window.GLOB.backend) return
+
+    Api.cacheInterface({userid: sessionStorage.getItem('UserID') || '', LoginUID: sessionStorage.getItem('LoginUID') || ''}).then(res => {
+      if (!res.status) {
+        notification.warning({
+          top: 92,
+          message: res.message || '缂撳瓨娓呯┖澶辫触锛�',
+          duration: 5
+        })
+      } else if (window.GLOB.localSystemApi) {
+        Api.cacheInterface({
+          userid: sessionStorage.getItem('LocalUserID') || sessionStorage.getItem('UserID') || '',
+          LoginUID: sessionStorage.getItem('LocalLoginUID') || sessionStorage.getItem('LoginUID') || '',
+          rduri: window.GLOB.localSystemApi.replace('dostars', 'excache')
+        }).then(result => {
+          if (!result.status) {
+            notification.warning({
+              top: 92,
+              message: result.message || '缂撳瓨娓呯┖澶辫触锛�',
+              duration: 5
+            })
+          }
+        })
+      }
+    })
   }
 
   /**
@@ -2174,10 +2806,22 @@
    */
   execSuccess = (res = {}) => {
     const { btn } = this.props
-    const { autoMatic } = this.state
+    const { autoMatic, dict } = this.state
 
     if (btn.resetForms) {
-      MKEmitter.emit('resetForms', btn.uuid)
+      let data = {}
+
+      Object.keys(res).forEach(key => {
+        data[key.toLowerCase()] = res[key]
+      })
+
+      delete data.errcode
+      delete data.errmesg
+      delete data.message
+      delete data.status
+
+      MKEmitter.emit('resetForms', btn.uuid, data)
+      MKEmitter.emit('refreshByButtonResult', btn.$menuId, 'resetData', btn, null, null, data)
     }
 
     if (this.preCallback) {
@@ -2197,6 +2841,17 @@
     }
 
     let sign = ''
+    let focusField = ''
+
+    if (/@focus:[a-z0-9_]+@/i.test(res.message)) {
+      let val = res.message.match(/@focus:[a-z0-9_]+@/i)
+      res.message = res.message.replace(/@focus:[a-z0-9_]+@/i, '')
+      focusField = val ? val[0].replace(/@focus:|@/ig, '') : ''
+
+      if (!res.message) {
+        res.ErrCode = '-1'
+      }
+    }
     if (/^@speak@/i.test(res.message)) {
       res.message = res.message.replace(/^@speak@/i, '')
       let val = res.message.match(/<<.*>>/)
@@ -2212,9 +2867,10 @@
       if (!res.message) {
         res.ErrCode = '-1'
       }
-    } else if (/@close_tab@|@close_popup@|@goback@|@no_target_menu@/i.test(res.message)) {
-      sign = res.message.match(/@close_tab@|@close_popup@|@goback@|@no_target_menu@/i)[0].toLowerCase()
-      res.message = res.message.replace(/@close_tab@|@close_popup@|@goback@|@no_target_menu@/i, '')
+    }
+    if (/@close_tab@|@close_popup@|@goback@|@no_target_menu@|@open_target_menu@/i.test(res.message)) {
+      sign = res.message.match(/@close_tab@|@close_popup@|@goback@|@no_target_menu@|@open_target_menu@/i)[0].toLowerCase()
+      res.message = res.message.replace(/@close_tab@|@close_popup@|@goback@|@no_target_menu@|@open_target_menu@/i, '')
     }
 
     let id = ''
@@ -2232,20 +2888,21 @@
       if (btn.formType !== 'counter' || res.message) {
         notification.success({
           top: 92,
-          message: res.message || '鎵ц鎴愬姛锛�',
+          message: res.message || dict['exc_success'] || '鎵ц鎴愬姛锛�',
           duration: btn.verify && btn.verify.stime ? btn.verify.stime : 2
         })
       }
     } else if (res.ErrCode === 'Y') { // 鎵ц鎴愬姛
-      let msg = res.message || '鎵ц鎴愬姛锛�'
+      let msg = res.message || dict['exc_success'] || '鎵ц鎴愬姛锛�'
       if (/\n|\r/.test(msg)) {
         msg = msg.replace(/\n|\r/ig, '<br/>')
         msg = <span dangerouslySetInnerHTML={{__html: msg}}></span>
       }
       Modal.success({
         title: msg,
+        okText: dict['got_it'] || '鐭ラ亾浜�',
         onOk: () => {
-          this.successContinue(sign, id)
+          this.successContinue(sign, id, res, focusField)
         }
       })
       return
@@ -2253,12 +2910,16 @@
 
     }
 
-    this.successContinue(sign, id)
+    this.successContinue(sign, id, res, focusField)
   }
 
-  successContinue = (sign, id) => {
+  successContinue = (sign, id, res, focusField) => {
     const { btn } = this.props
     const { btnconfig } = this.state
+
+    if (focusField) {
+      MKEmitter.emit('resetFocus', btn.uuid, focusField)
+    }
 
     this.setState({
       loadingNumber: '',
@@ -2278,7 +2939,7 @@
     }
 
     if (tabId && btn.$MenuID === tabId) { // 鍒锋柊褰撳墠鑿滃崟鏃讹紝鍋滄鍏朵粬鎿嶄綔
-      MKEmitter.emit('reloadMenuView', tabId, 'table')
+      MKEmitter.emit('reloadMenuView', tabId)
       return
     }
 
@@ -2308,12 +2969,19 @@
       } else if (/\$focus/.test(btn.syncComponentId)) {
         MKEmitter.emit('reloadData', btn.syncComponentId.split('$')[0], btn.syncComponentId.split('$')[1])
       } else {
-        MKEmitter.emit('reloadData', btn.syncComponentId)
+        if (btn.syncDelay) {
+          this.delayTimer && clearTimeout(this.delayTimer)
+          this.delayTimer = setTimeout(() => {
+            MKEmitter.emit('reloadData', btn.syncComponentId)
+          }, btn.syncDelay)
+        } else {
+          MKEmitter.emit('reloadData', btn.syncComponentId)
+        }
       }
     }
 
     if (tabId) {
-      MKEmitter.emit('reloadMenuView', tabId, 'table')
+      MKEmitter.emit('reloadMenuView', tabId)
     }
     
     if (btn.switchTab && btn.switchTab.length > 0) {
@@ -2350,13 +3018,41 @@
     if (btn.execSuccess === 'popclose' && btn.$tabId) { // 鏍囩鍏抽棴鍒锋柊
       MKEmitter.emit('refreshPopButton', btn.$tabId)
     }
+
+    if (btn.verify && btn.verify.linkEnable === 'true') {
+      let url = ''
+      if (window.GLOB.systemType === 'production') {
+        url = btn.verify.linkProUrl
+        if (!url) {
+          notification.warning({
+            top: 92,
+            message: window.GLOB.dict['no_prod_link'] || '灏氭湭璁剧疆姝e紡绯荤粺閾炬帴鍦板潃锛�',
+            duration: 5
+          })
+          return
+        }
+      } else {
+        url = btn.verify.linkUrl
+      }
+
+      if (/@/.test(url)) {
+        Object.keys(res).forEach(key => {
+          url = url.replace(new RegExp('@' + key + '@', 'ig'), res[key])
+        })
+      }
+      if (!/^http/.test(url)) {
+        url = window.location.origin + url
+      }
+
+      window.open(url)
+    }
   }
 
   triggerNote = (res, ID) => {
     const { btn } = this.props
 
     if (!btn.verify) return
-    if (btn.verify.noteEnable !== 'true' && btn.verify.wxNote !== 'true' && btn.verify.printEnable !== 'true') return
+    if (btn.verify.noteEnable !== 'true' && btn.verify.wxNote !== 'true' && btn.verify.printEnable !== 'true' && btn.verify.emailEnable !== 'true') return
 
     let id = ''
     if (btn.output) {
@@ -2371,6 +3067,9 @@
 
     if (btn.verify.noteEnable === 'true') {
       this.sendMessage(btn.verify, id)
+    }
+    if (btn.verify.emailEnable === 'true') {
+      this.sendEmail(btn.verify, id)
     }
     if (btn.verify.wxNote === 'true') {
       if (btn.verify.wxTemplateId === 'mk_category_temp') {
@@ -2393,16 +3092,65 @@
 
     if (!id) return
 
-    setTimeout(() => {
-      window.open('#/billprint/' + window.btoa(window.encodeURIComponent(JSON.stringify({ id: id, tempId: btn.verify.printTempId, pageId: btn.$MenuID || '', dataM: sessionStorage.getItem('dataM') }))))
-    }, 500)
+    if (btn.verify.preHandle === 'true' && btn.verify.pre_func && /#position-print/.test(btn.verify.pre_func)) {
+      MKEmitter.emit('queryModuleParam', btn.$menuId, (res) => {
+        let searches = {}
+        res.search && res.search.forEach(item => {
+          searches[item.key] = item.value
+        })
+        let _param = { id: id || '', tempId: btn.verify.printTempId, pageId: btn.$MenuID || '', dataM: sessionStorage.getItem('dataM')}
+
+        try {
+          // eslint-disable-next-line
+          let func = new Function('btn', 'searches', 'param', 'systemType', btn.verify.pre_func)
+          _param = func(btn, searches, _param, window.GLOB.systemType)
+        } catch (e) {
+          console.warn(e)
+        }
+
+        if (!_param || _param.error) {
+          notification.warning({
+            top: 92,
+            message: _param ? _param.error : '鏈幏鍙栧埌鎵撳嵃鍙傛暟锛岃嚜瀹氫箟鑴氭湰閿欒锛�',
+            duration: 5
+          })
+          return
+        }
+        
+        window.open('#/billprint/' + window.btoa(window.encodeURIComponent(JSON.stringify(_param))))
+      })
+    } else {
+      setTimeout(() => {
+        window.open('#/billprint/' + window.btoa(window.encodeURIComponent(JSON.stringify({ id: id, tempId: btn.verify.printTempId, pageId: btn.$MenuID || '', dataM: sessionStorage.getItem('dataM') }))))
+      }, 200)
+    }
   }
 
   sendWxMessage = (verify, id) => {
-    if (!window.GLOB.nginx) {
+    let domain = window.GLOB.baseurl
+    let appId = window.GLOB.WXAppID || ''
+
+    if (verify.wxAppId && verify.wxAppId !== appId) {
+      appId = verify.wxAppId
+      if (!window.GLOB.WXApps || window.GLOB.WXApps.findIndex(item => item.appId === verify.wxAppId) === -1) {
+        notification.warning({
+          top: 92,
+          message: '鎸夐挳鍏宠仈鍏紬鍙蜂笉鍦ㄥ彲鐢ㄥ垪琛ㄤ腑锛岃閲嶆柊淇濆瓨鎸夐挳閰嶇疆锛�',
+          duration: 5
+        })
+        return
+      }
+    }
+    
+    if (['8IFltwzyKcu15iA8fqSyb6m-pMa88a3ZTu0No3vDHgo', 'LOB-bbt9jVncGh7IOAUdESh1Sgzcbt62UwOqSqcK9ok'].includes(verify.wxTemplateId) && window.GLOB.sysType !== 'cloud') {
+      domain = 'https://cloud.mk9h.cn/'
+      appId = 'wx4d8a34c8d4494872'
+    }
+
+    if (!appId) {
       notification.warning({
         top: 92,
-        message: 'nginx鏈嶅姟灏氭湭寮�鍚紝涓嶅彲鍙戦�佹ā鏉挎秷鎭��',
+        message: '灏氭湭娣诲姞鍏紬鍙稩D锛屼笉鍙彂閫佹ā鏉挎秷鎭��',
         duration: 5
       })
       return
@@ -2413,16 +3161,9 @@
       upid: id
     }
 
-    param.LText = Utils.formatOptions(Utils.getuuid())
+    param.LText = Utils.getuuid()
     param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
     param.secretkey = Utils.encrypt(param.LText, param.timestamp)
-
-    let domain1 = ''
-    let domain2 = ''
-    if (['8IFltwzyKcu15iA8fqSyb6m-pMa88a3ZTu0No3vDHgo', 'LOB-bbt9jVncGh7IOAUdESh1Sgzcbt62UwOqSqcK9ok'].includes(verify.wxTemplateId) && window.GLOB.sysType !== 'cloud') {
-      domain1 = 'https://cloud.mk9h.cn/'
-      domain2 = 'https://cloud.mk9h.cn:8443/'
-    }
 
     Api.genericInterface(param).then(res => {
       // res.send_data = [{openid: 'o2E7gvoSFvQRG7I8_gZxf4y3ONkQ', send_id: Utils.getuuid(), p1: '010000000001', p2: '鏄庣', p3: 'dddd', p4: '椤洪', p5: '鎴愬姛'}]
@@ -2450,9 +3191,9 @@
 
       if (verify.wxNoteLink === 'url' && verify.wxNoteLinkUrl) {
         _param.url = verify.wxNoteLinkUrl
-      } else if (verify.wxNoteLink === 'miniProgram' && window.GLOB.WXminiAppID) {
+      } else if (verify.wxNoteLink === 'miniProgram' && (window.GLOB.WXminiAppID || verify.wxNoteMiniId)) {
         _param.miniprogram = {
-          appid: window.GLOB.WXminiAppID,
+          appid: verify.wxNoteMiniId || window.GLOB.WXminiAppID,
           pagepath: '/pages/index/index'
         }
 
@@ -2486,62 +3227,63 @@
         return m
       })
 
-      Api.wxAccessToken(domain1).then(res => {
-        if (!res.oa_access_token) return
-  
-        params.forEach(n => {
-          Api.wxNginxRequest(`${domain2}cgi-bin/message/template/send?access_token=${res.oa_access_token}`, 'post', JSON.stringify(n)).then(re => {
-            if (verify.wxNoteCallback === 'true') {
-              let msg = re.errmsg || ''
+      // cgi-bin/message/template/send
+      params.forEach(n => {
+        Api.directRequest({
+          url: domain + 'wechat/send?appid=' + appId,
+          method: 'post',
+          data: JSON.stringify(n)
+        }).then(re => {
+          if (verify.wxNoteCallback === 'true') {
+            let msg = re.errmsg || ''
 
-              if (msg.length > 50) {
-                msg = msg.substr(0, 50)
-              }
-
-              let _p = {
-                func: 's_get_sms_weixin_local_suc_err',
-                upid: id,
-                send_id: n.client_msg_id || '',
-                status_result: re.errcode === 0 ? 'S' : 'E',
-                errcode: re.errcode,
-                msg_result: msg
-              }
-
-              _p.LText = Utils.formatOptions(Utils.getuuid())
-              _p.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
-              _p.secretkey = Utils.encrypt(_p.LText, _p.timestamp)
-
-              Api.genericInterface(_p).then(result => {
-                if (!result.status) {
-                  notification.warning({
-                    top: 92,
-                    message: result.message,
-                    duration: 5
-                  })
-                }
-              })
-            } else if (re.errcode !== 0 && re.errmsg) {
-              let msgs = [
-                {errcode: -1, errmsg: '绯荤粺绻佸繖锛岃绋嶅�欏啀璇�'},
-                {errcode: 40001, errmsg: 'access_token 鏃犳晥'},
-                {errcode: 40003, errmsg: '涓嶅悎娉曠殑 OpenID'},
-                {errcode: 40014, errmsg: '涓嶅悎娉曠殑 access_token'},
-                {errcode: 40033, errmsg: '涓嶅悎娉曠殑璇锋眰瀛楃'},
-                {errcode: 43004, errmsg: '闇�瑕佹帴鏀惰�呭叧娉�'},
-                {errcode: 43019, errmsg: '闇�瑕佸皢鎺ユ敹鑰呬粠榛戝悕鍗曚腑绉婚櫎'},
-                {errcode: 50005, errmsg: '鐢ㄦ埛鏈叧娉ㄥ叕浼楀彿'}
-              ]
-
-              let msg = msgs.filter(m => m.errcode === re.errcode)[0]
-              msg = msg || re
-
-              notification.warning({
-                top: 92,
-                message: msg.errmsg,
-                duration: 5
-              })
+            if (msg.length > 50) {
+              msg = msg.substr(0, 50)
             }
-          })
+
+            let _p = {
+              func: 's_get_sms_weixin_local_suc_err',
+              upid: id,
+              send_id: n.client_msg_id || '',
+              status_result: re.errcode === 0 ? 'S' : 'E',
+              errcode: re.errcode,
+              msg_result: msg
+            }
+
+            _p.LText = Utils.getuuid()
+            _p.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
+            _p.secretkey = Utils.encrypt(_p.LText, _p.timestamp)
+
+            Api.genericInterface(_p).then(result => {
+              if (!result.status) {
+                notification.warning({
+                  top: 92,
+                  message: result.message,
+                  duration: 5
+                })
+              }
+            })
+          } else if (re.errcode !== 0 && re.errmsg) {
+            let msgs = [
+              {errcode: -1, errmsg: '绯荤粺绻佸繖锛岃绋嶅�欏啀璇�'},
+              {errcode: 40001, errmsg: 'access_token 鏃犳晥'},
+              {errcode: 40003, errmsg: '涓嶅悎娉曠殑 OpenID'},
+              {errcode: 40014, errmsg: '涓嶅悎娉曠殑 access_token'},
+              {errcode: 40033, errmsg: '涓嶅悎娉曠殑璇锋眰瀛楃'},
+              {errcode: 43004, errmsg: '闇�瑕佹帴鏀惰�呭叧娉�'},
+              {errcode: 43019, errmsg: '闇�瑕佸皢鎺ユ敹鑰呬粠榛戝悕鍗曚腑绉婚櫎'},
+              {errcode: 50005, errmsg: '鐢ㄦ埛鏈叧娉ㄥ叕浼楀彿'}
+            ]
+
+            let msg = msgs.filter(m => m.errcode === re.errcode)[0]
+            msg = msg || re
+
+            notification.warning({
+              top: 92,
+              message: msg.errmsg,
+              duration: 5
+            })
+          }
         })
       })
     })
@@ -2550,12 +3292,12 @@
   sendMessage = (verify, id) => {
     let param = {
       func: 's_get_sms_local',
-      TypeCharOne: verify.noteTemp, // N涓嶅悓鍐呭锛孻鐩稿悓鍐呭
-      TypeCharTwo: verify.noteType, // N瀹氭椂锛孻瀹炴椂
+      TypeCharOne: verify.noteTemp || 'Y', // N涓嶅悓鍐呭锛孻鐩稿悓鍐呭
+      TypeCharTwo: verify.noteType || 'N', // N瀹氭椂锛孻瀹炴椂
       upid: id
     }
 
-    param.LText = Utils.formatOptions(Utils.getuuid())
+    param.LText = Utils.getuuid()
     param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
     param.secretkey = Utils.encrypt(param.LText, param.timestamp)
 
@@ -2570,9 +3312,9 @@
       }
 
       let _param = {
-        templatecode: verify.noteCode, // 妯℃澘缂栫爜
-        TypeCharOne: verify.noteTemp,  // N涓嶅悓鍐呭锛孻鐩稿悓鍐呭
-        ID: verify.noteId || ''        // 妯℃澘Id锛屾殏鏃舵湭浣跨敤
+        templatecode: verify.noteCode,        // 妯℃澘缂栫爜
+        TypeCharOne: verify.noteTemp || 'Y',  // N涓嶅悓鍐呭锛孻鐩稿悓鍐呭
+        ID: verify.noteId || ''               // 妯℃澘Id锛屾殏鏃舵湭浣跨敤
       }
 
       _param.submitdate = res.submitdate
@@ -2580,17 +3322,17 @@
       let limit = 5 // 瀹炴椂鏈�澶т负5鏉★紝瀹氭椂鏈�澶т负100鏉�
       let mobMap = new Map()
 
-      if (verify.noteType === 'N') {
+      if (verify.noteType === 'Y') {
+        _param.func = 's_get_sms_sso_realtime'
+      } else {
         _param.func = 's_get_sms_sso_timer'
         limit = 100
-      } else if (verify.noteType === 'Y') {
-        _param.func = 's_get_sms_sso_realtime'
       }
 
       let Ltext = []
       let error = false
 
-      if (verify.noteTemp === 'Y') {
+      if (verify.noteTemp !== 'N') {
         _param.p1 = res.p1 || ''
         _param.p2 = res.p2 || ''
         _param.p3 = res.p3 || ''
@@ -2599,25 +3341,156 @@
 
         let _p = _param.p1 + _param.p2 + _param.p3 + _param.p4 + _param.p5
 
-        if (/\/|\.|.*鍏�.*浜.*涔�.*杩憒闈㈣瘯|閭�璇穦涓嬭浇|绾㈠寘|鎷涜仒|濂借瘎|璇勪环|鏀垮姟閫氱煡|缂磋垂|淇濋櫓|鑲$エ|閲戣瀺|鎴垮湴浜鏁欒偛|娓告垙|寰俊|Q/.test(_p)) {
+        if (/\/|.*鍏�.*浜.*涔�.*杩憒闈㈣瘯|閭�璇穦涓嬭浇|绾㈠寘|鎷涜仒|濂借瘎|璇勪环|鏀垮姟閫氱煡|缂磋垂|淇濋櫓|鑲$エ|閲戣瀺|鎴垮湴浜鏁欒偛|娓告垙|寰俊/.test(_p)) {
           error = true
         }
       }
 
       res.send_data && res.send_data.forEach(item => {
         if (item.mob && !mobMap.has(item.mob) && Ltext.length < limit) {
-          if (verify.noteTemp === 'Y') {
+          if (verify.noteTemp !== 'N') {
             Ltext.push(`'${item.mob}'`)
           } else {
             let _p = `'${item.p1 || ''}','${item.p2 || ''}','${item.p3 || ''}','${item.p4 || ''}','${item.p5 || ''}','${item.mob}'`
 
-            if (/\/|\.|.*鍏�.*浜.*涔�.*杩憒闈㈣瘯|閭�璇穦涓嬭浇|绾㈠寘|鎷涜仒|濂借瘎|璇勪环|鏀垮姟閫氱煡|缂磋垂|淇濋櫓|鑲$エ|閲戣瀺|鎴垮湴浜鏁欒偛|娓告垙|寰俊|Q/.test(_p)) {
+            if (/\/|.*鍏�.*浜.*涔�.*杩憒闈㈣瘯|閭�璇穦涓嬭浇|绾㈠寘|鎷涜仒|濂借瘎|璇勪环|鏀垮姟閫氱煡|缂磋垂|淇濋櫓|鑲$エ|閲戣瀺|鎴垮湴浜鏁欒偛|娓告垙|寰俊/.test(_p)) {
               error = true
             }
 
             Ltext.push(_p)
           }
           mobMap.set(item.mob, true)
+        }
+      })
+
+      if (error) {
+        notification.warning({
+          top: 92,
+          message: '娑堟伅涓惈鏈夐潪娉曞瓧绗�',
+          duration: 5
+        })
+        return
+      }
+
+      if (Ltext.length === 0) return
+
+      Ltext = Ltext.join(';')
+
+      _param.LText = window.btoa(window.encodeURIComponent(Ltext))
+      _param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
+      _param.secretkey = Utils.encrypt(_param.LText, _param.timestamp)
+
+      _param.rduri = 'https://sso.mk9h.cn/webapi/dostars'
+
+      _param.userid = 'bh0bapabtd45epsgra79segbch6c1ibk'
+      _param.LoginUID = 'bh0bapabtd45epsgra79segbch6c1ibk'
+
+      Api.genericInterface(_param).then(result => {
+        if (!result.status) {
+          notification.warning({
+            top: 92,
+            message: result.message,
+            duration: 5
+          })
+        }
+      }, (error) => {
+        if (error && error.ErrCode === 'LoginError') {
+          let param = {
+            func: 's_visitor_login',
+            timestamp: moment().format('YYYY-MM-DD HH:mm:ss'), 
+            SessionUid: 'bh0bapabtd45epsgra79segbch6c1ibk',
+            TypeCharOne: 'pc',
+            appkey: '202004041613277377A6A2456D34A4948AE84'
+          }
+
+          param.LText = md5(window.btoa('bh0bapabtd45epsgra79segbch6c1ibk' + param.timestamp))
+          param.secretkey = md5(param.LText + 'mingke' + param.timestamp)
+
+          let params = {
+            url: 'https://sso.mk9h.cn/webapi/dologon',
+            method: 'post',
+            data: JSON.stringify(param)
+          }
+
+          Api.directRequest(params)
+
+          return
+        }
+      })
+    })
+  }
+
+  sendEmail = (verify, id) => {
+    let param = {
+      func: 's_get_email_local',
+      TypeCharOne: verify.emailTemp || 'Y', // N涓嶅悓鍐呭锛孻鐩稿悓鍐呭
+      TypeCharTwo: verify.emailType || 'N', // N瀹氭椂锛孻瀹炴椂
+      upid: id
+    }
+
+    param.LText = Utils.getuuid()
+    param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss')
+    param.secretkey = Utils.encrypt(param.LText, param.timestamp)
+
+    Api.genericInterface(param).then(res => {
+      if (!res.status) {
+        notification.warning({
+          top: 92,
+          message: res.message,
+          duration: 5
+        })
+        return
+      }
+
+      let _param = {
+        msn_email_temp_no: verify.emailCode,   // 妯℃澘缂栫爜
+        TypeCharOne: verify.emailTemp || 'Y',  // N涓嶅悓鍐呭锛孻鐩稿悓鍐呭
+        ID: verify.emailId || ''               // 妯℃澘Id锛屾殏鏃舵湭浣跨敤
+      }
+
+      _param.submitdate = res.submitdate
+
+      let limit = 5 // 瀹炴椂鏈�澶т负5鏉★紝瀹氭椂鏈�澶т负100鏉�
+      let mobMap = new Map()
+
+      if (verify.emailType === 'Y') {
+        _param.func = 's_get_email_sso_realtime'
+      } else {
+        _param.func = 's_get_email_sso_timer'
+        limit = 100
+      }
+
+      let Ltext = []
+      let error = false
+
+      if (verify.emailTemp !== 'N') {
+        _param.p1 = res.p1 || ''
+        _param.p2 = res.p2 || ''
+        _param.p3 = res.p3 || ''
+        _param.p4 = res.p4 || ''
+        _param.p5 = res.p5 || ''
+
+        let _p = _param.p1 + _param.p2 + _param.p3 + _param.p4 + _param.p5
+
+        if (/\/|.*鍏�.*浜.*涔�.*杩憒闈㈣瘯|閭�璇穦涓嬭浇|绾㈠寘|鎷涜仒|濂借瘎|璇勪环|鏀垮姟閫氱煡|缂磋垂|淇濋櫓|鑲$エ|閲戣瀺|鎴垮湴浜鏁欒偛|娓告垙|寰俊/.test(_p)) {
+          error = true
+        }
+      }
+
+      res.send_data && res.send_data.forEach(item => {
+        if (item.email && !mobMap.has(item.email) && Ltext.length < limit) {
+          if (verify.emailTemp !== 'N') {
+            Ltext.push(`'${item.email}'`)
+          } else {
+            let _p = `'${item.p1 || ''}','${item.p2 || ''}','${item.p3 || ''}','${item.p4 || ''}','${item.p5 || ''}','${item.email}'`
+
+            if (/\/|.*鍏�.*浜.*涔�.*杩憒闈㈣瘯|閭�璇穦涓嬭浇|绾㈠寘|鎷涜仒|濂借瘎|璇勪环|鏀垮姟閫氱煡|缂磋垂|淇濋櫓|鑲$エ|閲戣瀺|鎴垮湴浜鏁欒偛|娓告垙|寰俊/.test(_p)) {
+              error = true
+            }
+
+            Ltext.push(_p)
+          }
+          mobMap.set(item.email, true)
         }
       })
 
@@ -2686,7 +3559,7 @@
    */
   execError = (res = {}) => {
     const { btn } = this.props
-    const { autoMatic } = this.state
+    const { autoMatic, dict } = this.state
 
     if (this.preCallback) {
       this.setState({
@@ -2698,7 +3571,7 @@
     } else if (autoMatic) {
       notification.error({
         top: 92,
-        message: res.message || '鎵ц澶辫触锛�',
+        message: res.message || dict['exc_fail'] || '鎵ц澶辫触锛�',
         duration: 10
       })
 
@@ -2732,19 +3605,20 @@
       if (!res.message) {
         res.ErrCode = '-1'
       }
-    } else if (/@close_tab@|@close_popup@|@goback@/i.test(res.message)) {
-      sign = res.message.match(/@close_tab@|@close_popup@|@goback@/i)[0].toLowerCase()
-      res.message = res.message.replace(/@close_tab@|@close_popup@|@goback@/i, '')
+    } else if (/@close_tab@|@close_popup@|@goback@|@open_target_menu@/i.test(res.message)) {
+      sign = res.message.match(/@close_tab@|@close_popup@|@goback@|@open_target_menu@/i)[0].toLowerCase()
+      res.message = res.message.replace(/@close_tab@|@close_popup@|@goback@|@open_target_menu@/i, '')
     }
 
     if (res.ErrCode === 'E') {
-      let msg = res.message || '鎵ц澶辫触锛�'
+      let msg = res.message || dict['exc_fail'] || '鎵ц澶辫触锛�'
       if (/\n|\r/.test(msg)) {
         msg = msg.replace(/\n|\r/ig, '<br/>')
         msg = <span dangerouslySetInnerHTML={{__html: msg}}></span>
       }
       Modal.error({
         title: msg,
+        okText: dict['got_it'] || '鐭ラ亾浜�',
         onOk: () => {
           this.errorContinue(sign)
         }
@@ -2753,18 +3627,25 @@
     } else if (res.ErrCode === 'N') {
       notification.error({
         top: 92,
-        message: res.message || '鎵ц澶辫触锛�',
+        message: res.message || dict['exc_fail'] || '鎵ц澶辫触锛�',
         duration: btn.verify && btn.verify.ntime ? btn.verify.ntime : 10
       })
     } else if (res.ErrCode === 'F') {
       notification.error({
         className: 'notification-custom-error',
         top: 92,
-        message: res.message || '鎵ц澶辫触锛�',
+        message: res.message || dict['exc_fail'] || '鎵ц澶辫触锛�',
         duration: btn.verify && btn.verify.ftime ? btn.verify.ftime : 10
       })
     } else if (res.ErrCode === 'NM') {
-      message.error(res.message || '鎵ц澶辫触锛�')
+      message.error(res.message || dict['exc_fail'] || '鎵ц澶辫触锛�')
+    } else if (res.ErrCode === '-2') {
+      this.setState({
+        loadingNumber: '',
+        loadingTotal: '',
+        loading: false
+      })
+      return
     }
 
     this.errorContinue(sign)
@@ -2794,8 +3675,47 @@
     } else if (btn.execError === 'closepoptab' || sign === '@close_popup@') {
       MKEmitter.emit('popclose')
     } else if (btn.execError !== 'never') {
+      let tabId = ''
+      if (btn.refreshTab && btn.refreshTab.length > 0) {
+        tabId = btn.refreshTab[btn.refreshTab.length - 1]
+      }
+      if (tabId && btn.$MenuID === tabId) { // 鍒锋柊褰撳墠鑿滃崟鏃讹紝鍋滄鍏朵粬鎿嶄綔
+        MKEmitter.emit('reloadMenuView', tabId)
+        return
+      }
+
       MKEmitter.emit('refreshByButtonResult', btn.$menuId, btn.execError, btn, '', this.state.selines)
+
+      if (btn.syncComponentId) {
+        if (btn.syncComponentId === 'multiComponent') {
+          btn.syncComponentIds.forEach((id, i) => {
+            setTimeout(() => {
+              if (/\$focus/.test(id)) {
+                MKEmitter.emit('reloadData', id.split('$')[0], id.split('$')[1])
+              } else {
+                MKEmitter.emit('reloadData', id)
+              }
+            }, 20 * i)
+          })
+        } else if (/\$focus/.test(btn.syncComponentId)) {
+          MKEmitter.emit('reloadData', btn.syncComponentId.split('$')[0], btn.syncComponentId.split('$')[1])
+        } else {
+          if (btn.syncDelay) {
+            this.delayTimer && clearTimeout(this.delayTimer)
+            this.delayTimer = setTimeout(() => {
+              MKEmitter.emit('reloadData', btn.syncComponentId)
+            }, btn.syncDelay)
+          } else {
+            MKEmitter.emit('reloadData', btn.syncComponentId)
+          }
+        }
+      }
+
+      if (tabId) {
+        MKEmitter.emit('reloadMenuView', tabId)
+      }
     }
+
     if (btn.OpenType === 'form') {
       let data = this.props.selectedData && this.props.selectedData[0] ? this.props.selectedData[0] : null
 
@@ -2816,6 +3736,35 @@
 
     if (window.GLOB.breakpoint) {
       MKEmitter.emit('refreshDebugTable')
+    }
+
+    if (sign === '@open_target_menu@' && btn.openmenu && Array.isArray(btn.openmenu) && btn.openmenu.length > 0) {
+      let id = ''
+      if (this.state.selines && this.state.selines.length > 0 && btn.Ot !== 'notRequired') {
+        if (btn.Ot === 'requiredOnce') {
+          id = this.state.selines.map(d => d.$$uuid).filter(Boolean).join(',')
+        } else {
+          id = this.state.selines[0].$$uuid
+        }
+      }
+
+      let menuId = btn.openmenu.slice(-1)[0]
+      let menu = null
+
+      if (window.GLOB.mkThdMenus.has(menuId)) {
+        menu = {...window.GLOB.mkThdMenus.get(menuId), param: { $BID: id || '' }}
+      } else if (btn.MenuID) {
+        menu = {
+          MenuID: btn.MenuID,
+          MenuName: btn.MenuName,
+          type: btn.tabType,
+          param: { $BID: id || '' }
+        }
+      }
+
+      if (menu) {
+        MKEmitter.emit('modifyTabs', menu, true)
+      }
     }
 
     if (btn.execError === 'popclose' && btn.$tabId) { // 鏍囩鍏抽棴鍒锋柊
@@ -2950,9 +3899,9 @@
   }
 
   modelconfirm = () => {
-    const { btn, BID } = this.props
-    const { btnconfig, selines } = this.state
-    let _this = this
+    const { BID } = this.props
+    const { btnconfig, selines, dict } = this.state
+    let that = this
 
     let result = []
     let _data = {}
@@ -3035,6 +3984,20 @@
               console.warn(e)
               _item.value = ''
             }
+          } else if (item.interception === 'charTure') {
+            let str = _item.value.replace(/(^\s*|\s*$)/g, '')
+            let result = ''
+            for (let i = 0 ; i < str.length; i++) {
+              let code = str.charCodeAt(i)
+              if (code >= 65281 && code <= 65373) {
+                result += String.fromCharCode(str.charCodeAt(i) - 65248)
+              } else if (code === 12288) {
+                result += String.fromCharCode(str.charCodeAt(i) - 12288 + 32)
+              } else {
+                result += str.charAt(i)
+              }
+            }
+            _item.value = result
           } else {
             _item.value = _item.value.replace(/(^\s*|\s*$)/g, '')
           }
@@ -3081,15 +4044,17 @@
       this.execSubmit(selines, () => {}, result)
     } else {
       confirm({
-        title: btn.tipTitle || '纭畾瑕佹墽琛屽悧?',
+        title: btnconfig.setting.tipTitle || dict['exec_sure'] || '纭畾瑕佹墽琛屽悧?',
+        okText: dict['ok'] || '纭畾',
+        cancelText: dict['cancel'] || '鍙栨秷',
         onOk() {
           return new Promise(resolve => {
-            _this.execSubmit(selines, resolve, result)
+            that.execSubmit(selines, resolve, result)
           })
         },
         onCancel() {
-          _this.preCallback && _this.preCallback()
-          _this.setState({ loading: false })
+          that.preCallback && that.preCallback()
+          that.setState({ loading: false })
         }
       })
     }
@@ -3100,7 +4065,7 @@
    */
   getModels = () => {
     const { BID, btn, BData } = this.props
-    const { btnconfig, visible } = this.state
+    const { btnconfig, visible, dict } = this.state
 
     if (!btnconfig || !btnconfig.setting) return null
 
@@ -3136,10 +4101,10 @@
           />
           <div className="ant-drawer-footer" style={{ position: 'absolute', zIndex: 1, right: 0, bottom: 0, width: '100%', borderTop: '1px solid #e9e9e9', padding: '10px 16px', background: '#fff', textAlign: 'right'}}>
             <Button onClick={this.handleCancel} style={{ marginRight: 8 }}>
-              {btnconfig.setting.formType !== 'check' ? '鍙栨秷' : '鍏抽棴'}
+              {btnconfig.setting.formType !== 'check' ? dict['cancel'] || '鍙栨秷' : dict['close'] || '鍏抽棴'}
             </Button>
             {btnconfig.setting.formType !== 'check' ? <Button onClick={this.handleOk} loading={this.state.confirmLoading} type="primary">
-              纭畾
+              {dict['ok'] || '纭畾'}
             </Button> : null}
           </div>
         </Drawer>
@@ -3167,6 +4132,8 @@
           wrapClassName={'action-modal' + (btnconfig.setting.moveable === 'true' ? ' moveable-modal modal-' + btn.uuid : '')}
           visible={visible}
           width={width}
+          okText={dict['ok'] || '纭畾'}
+          cancelText={dict['cancel'] || '鍙栨秷'}
           onOk={this.handleOk}
           maskStyle={btnconfig.setting.moveable === 'true' ?  {backgroundColor: 'rgba(0, 0, 0, 0.15)'} : null}
           confirmLoading={this.state.confirmLoading}
@@ -3231,7 +4198,7 @@
 
   changeLineCount = (count) => {
     const { btn, selectedData } = this.props
-    const { disabled } = this.state
+    const { disabled, dict } = this.state
 
     if (disabled) return
 
@@ -3241,7 +4208,7 @@
       // 闇�瑕侀�夋嫨琛屾椂锛屾牎楠屾暟鎹�
       notification.warning({
         top: 92,
-        message: '璇烽�夋嫨琛岋紒',
+        message: dict['select_row'] || '璇烽�夋嫨琛岋紒',
         duration: 5
       })
       return
@@ -3249,7 +4216,7 @@
       // 闇�瑕侀�夋嫨鍗曡鏃讹紝鏍¢獙鏁版嵁
       notification.warning({
         top: 92,
-        message: '璇烽�夋嫨鍗曡鏁版嵁锛�',
+        message: dict['select_single_row'] || '璇烽�夋嫨鍗曡鏁版嵁锛�',
         duration: 5
       })
       return
@@ -3261,7 +4228,7 @@
   }
 
   render() {
-    const { btn } = this.props
+    const { btn, name } = this.props
     const { loadingNumber, loadingTotal, loading, disabled, hidden, check, count } = this.state
 
     if (hidden) return null
@@ -3280,45 +4247,36 @@
     }
 
     let label = ''
-    let icon = ''
-    let type = 'link'
-    let className = ''
 
-    if (btn.show === 'button') {
-      label = btn.label
-      icon = btn.icon || ''
-    } else if (btn.show === 'link') {
-      label = <span>{btn.label}{btn.icon ? <MkIcon style={{marginLeft: '8px'}} type={btn.icon}/> : ''}</span>
-      icon = ''
+    if (btn.show === 'link') {
+      label = <span>{name || btn.label}{btn.icon ? <MkIcon style={{marginLeft: '8px'}} type={btn.icon} /> : ''}</span>
     } else if (btn.show === 'icon') {
-      icon = btn.icon || ''
-    } else if (!btn.$toolbtn) {
-      icon = btn.icon || ''
-      label = btn.label
-      className = 'mk-btn mk-' + (btn.class || 'unset')
+      label = !loading ? <MkIcon type={btn.icon} /> : null
+    } else if (btn.$toolbtn) {
+      label = <span>{!loading && btn.icon ? <MkIcon style={{marginRight: '8px'}} type={btn.icon} /> : ''}{loadingNumber && !loadingTotal ? `(${loadingNumber})` : ''}{btn.label}</span>
     } else {
-      type = ''
-      icon = btn.icon || ''
-      label = btn.label
-      className = 'mk-btn mk-' + (btn.class || 'unset')
+      label = <span>{!loading && btn.icon ? <MkIcon style={{marginRight: '8px'}} type={btn.icon} /> : ''}{name || btn.label}</span>
     }
 
-    if (loadingNumber && btn.progress !== 'progressbar' && btn.$toolbtn && (!btn.show || btn.show === 'button')) {
-      label = (loadingNumber ? `(${loadingNumber})` : '') + btn.label
+    let BTN = <Button
+      type="link"
+      id={'button' + btn.uuid}
+      title={disabled ? (btn.reason || '') : (btn.show === 'icon' ? btn.label : '')}
+      loading={loading}
+      disabled={disabled}
+      style={btn.style}
+      className={btn.hover || ''}
+      onClick={(e) => {e.stopPropagation(); this.actionTrigger()}}
+    >{label}</Button>
+
+    if (btn.hoverTitle) {
+      BTN = <Popover mouseLeaveDelay={0.3} mouseEnterDelay={0.3} content={btn.hoverTitle} trigger="hover">
+        {BTN}
+      </Popover>
     }
 
     return <>
-      <Button
-        type={type}
-        icon={icon}
-        id={'button' + btn.uuid}
-        title={disabled ? (btn.reason || '') : (btn.show === 'icon' ? btn.label : '')}
-        loading={loading}
-        disabled={disabled}
-        style={btn.style}
-        className={className}
-        onClick={(e) => {e.stopPropagation(); this.actionTrigger()}}
-      >{label}</Button>
+      {BTN}
       <span onClick={(e) => {e.stopPropagation()}}>{this.getModels()}</span>
       {loadingTotal ? <Progress className="mk-button-progress" percent={(loadingTotal - loadingNumber) / loadingTotal * 100} size="small" showInfo={false} /> : null}
     </>

--
Gitblit v1.8.0