king
7 天以前 a1e9b18a4dbfd21e1bf4d5cb60974ac2f0115efd
src/tabviews/zshare/actionList/normalbutton/index.jsx
@@ -13,7 +13,8 @@
import MKEmitter from '@/utils/events.js'
import MkIcon from '@/components/mk-icon'
import MkCounter from './mkcounter'
// import './index.scss'
import './index.scss'
const MutilForm = asyncSpinComponent(() => import('@/tabviews/zshare/mutilform'))
const { confirm } = Modal
@@ -45,7 +46,8 @@
    autoMatic: false,
    check: false,
    count: 0,
    dict: window.GLOB.dict
    dict: window.GLOB.dict,
    submitType: ''
  }
  preCallback = null
@@ -307,16 +309,16 @@
      }
    }
    // 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) => {
@@ -411,7 +413,7 @@
    if (setting.supModule && !BID) {
      notification.warning({
        top: 92,
        message: dict['sup_key_req'] || '需要上级主键值!',
        message: setting.supModTip || dict['sup_key_req'] || '需要上级主键值!',
        duration: 5
      })
      return false
@@ -420,6 +422,13 @@
      notification.warning({
        top: 92,
        message: dict['select_row'] || '请选择行!',
        duration: 5
      })
      return false
    } else if (btn.Ot !== 'notRequired' && data[0] && !data[0].$$uuid) {
      notification.warning({
        top: 92,
        message: dict['id_required'] || '未获取到ID值!',
        duration: 5
      })
      return false
@@ -445,6 +454,7 @@
  getSystemParam = (data, formdata, retmsg) => {
    const { setting, columns, btn } = this.props
    const { submitType } = this.state
    let _params = []
    if ( btn.Ot === 'notRequired' || btn.Ot === 'requiredSgl' || btn.Ot === 'requiredOnce' ) {
@@ -468,11 +478,11 @@
        param.ID = primaryId
        if (retmsg) {
          const { sql, callbacksql } = getSysDefaultSql(btn, setting, '', param, data[0], columns, retmsg) // 数据源
          const { sql, callbacksql } = getSysDefaultSql(btn, setting, '', param, data[0], columns, retmsg, submitType) // 数据源
          param.LText = sql
          param.$callbacksql = callbacksql
        } else {
          param.LText = getSysDefaultSql(btn, setting, '', param, data[0], columns, false) // 数据源
          param.LText = getSysDefaultSql(btn, setting, '', param, data[0], columns, false, submitType) // 数据源
          if (btn.output) {
            param.key_back_type = 'Y'
          }
@@ -495,11 +505,11 @@
          param.ID = Utils.getguid()
          if (retmsg) {
            const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, retmsg) // 数据源
            const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, retmsg, submitType) // 数据源
            param.LText = sql
            param.$callbacksql = callbacksql
          } else {
            param.LText = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, false) // 数据源
            param.LText = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, false, submitType) // 数据源
            if (btn.output) {
              param.key_back_type = 'Y'
            }
@@ -521,11 +531,11 @@
          param.ID = primaryId
          if (retmsg) {
            const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, retmsg) // 数据源
            const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, retmsg, submitType) // 数据源
            param.LText = sql
            param.$callbacksql = callbacksql
          } else {
            param.LText = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, false) // 数据源
            param.LText = getSysDefaultSql(btn, setting, formdata, param, data[0], columns, false, submitType) // 数据源
            if (btn.output) {
              param.key_back_type = 'Y'
            }
@@ -587,11 +597,11 @@
          param.ID = primaryId
          if (retmsg) {
            const { sql, callbacksql } = getSysDefaultSql(btn, setting, '', param, cell, columns, retmsg) // 数据源
            const { sql, callbacksql } = getSysDefaultSql(btn, setting, '', param, cell, columns, retmsg, submitType) // 数据源
            param.LText = sql
            param.$callbacksql = callbacksql
          } else {
            param.LText = getSysDefaultSql(btn, setting, '', param, cell, columns, false) // 数据源
            param.LText = getSysDefaultSql(btn, setting, '', param, cell, columns, false, submitType) // 数据源
            if (btn.output) {
              param.key_back_type = 'Y'
            }
@@ -627,11 +637,11 @@
            param.ID = Utils.getguid()
            if (retmsg) {
              const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, cell, columns, retmsg) // 数据源
              const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, cell, columns, retmsg, submitType) // 数据源
              param.LText = sql
              param.$callbacksql = callbacksql
            } else {
              param.LText = getSysDefaultSql(btn, setting, formdata, param, cell, columns, false) // 数据源
              param.LText = getSysDefaultSql(btn, setting, formdata, param, cell, columns, false, submitType) // 数据源
              if (btn.output) {
                param.key_back_type = 'Y'
              }
@@ -653,11 +663,11 @@
            param.ID = primaryId
            if (retmsg) {
              const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, cell, columns, retmsg) // 数据源
              const { sql, callbacksql } = getSysDefaultSql(btn, setting, formdata, param, cell, columns, retmsg, submitType) // 数据源
              param.LText = sql
              param.$callbacksql = callbacksql
            } else {
              param.LText = getSysDefaultSql(btn, setting, formdata, param, cell, columns, false) // 数据源
              param.LText = getSysDefaultSql(btn, setting, formdata, param, cell, columns, false, submitType) // 数据源
              if (btn.output) {
                param.key_back_type = 'Y'
              }
@@ -808,6 +818,8 @@
  getExps = (ex, formdata, cell, id, process) => {
    const { columns, BID, btn } = this.props
    const { submitType } = this.state
    let exps = []
    let values = {
      time_id: Utils.getguid(),
@@ -826,6 +838,7 @@
      datam: sessionStorage.getItem('dataM') === 'true' ? 'Y' : '',
      datam_begin: sessionStorage.getItem('dataM') === 'true' ? 'Y' : '',
      datam_end: sessionStorage.getItem('dataM') === 'true' ? 'Y' : '',
      mk_submit_type: submitType || ''
      // mk_check_begin: '',
      // mk_check_end: ''
    }
@@ -836,13 +849,11 @@
    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)) {
        if (isNaN(val) || val === '') {
          val = 0
        }
      } else if (['date', 'datemonth'].includes(form.type)) {
@@ -889,6 +900,13 @@
        })
      }
    })
    if (btn.verify && btn.verify.printEnable === 'true' && !btn.output && !ex.reps.includes('ID') && values.id) {
      exps.push({
        key: 'ID',
        value: values.id
      })
    }
    if (process && btn.verify.workFlow === 'true') {
      let flow = window.GLOB.UserCacheMap.get(btn.$flowId)
@@ -1080,6 +1098,10 @@
        error = '行信息中无工作流参数'
      }
      if (!error && btn.verify.flowSql !== 'true' && btn.verify.flowType !== 'start' && line && line.approvalMethod === 'countersign') {
        error = '会签流程需要使用默认脚本'
      }
      if (error) {
        status = 0
        statusName = '异常'
@@ -1105,23 +1127,25 @@
      } else {
        let works_flow_countersign = ''
        let works_flow_sign_values = ''
        let works_flow_sign_field = ''
        let works_flow_sign_field = 'statuscharone'
        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' : ''
        if (line) {
          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(
@@ -1285,9 +1309,10 @@
   * @description 获取回调脚本的字段定义
   */
  getSysDeclareSql = (btn, formdata, data, columns, BID = '') => {
    let datavars = {}                 // 声明的变量,表单及显示列
    const { submitType } = this.state
    // 需要声明的变量集
    let _vars = ['tbid', 'errorcode', 'retmsg', 'billcode', 'bvoucher', 'fibvoucherdate', 'fiyear', 'username', 'fullname', 'modulardetailcode', 'roleid', 'mk_departmentcode', 'mk_organization', 'mk_user_type', 'mk_nation', 'mk_province', 'mk_city', 'mk_district', 'mk_address', 'mk_deleted', 'bid']
    let _vars = ['tbid', 'errorcode', 'retmsg', 'billcode', 'bvoucher', 'fibvoucherdate', 'fiyear', 'username', 'fullname', 'modulardetailcode', 'roleid', 'mk_departmentcode', 'mk_organization', 'mk_user_type', 'mk_nation', 'mk_province', 'mk_city', 'mk_district', 'mk_address', 'mk_deleted', 'bid', 'mk_submit_type']
  
    // sql语句
    let _sql = ''
@@ -1300,14 +1325,13 @@
    // 获取字段键值对
    formdata && formdata.forEach(form => {
      let _key = form.key.toLowerCase()
      datavars[_key] = form.value
  
      if (!_initvars.includes(_key)) {
        _initvars.push(_key)
        let val = form.value
  
        if (form.type === 'number' || form.type === 'rate') {
          if (isNaN(val)) {
          if (isNaN(val) || val === '') {
            val = 0
          }
          _initFormfields.push(`@${_key}=${val}`)
@@ -1355,14 +1379,12 @@
  
    // 添加数据中字段,表单值优先(按钮不选行或多行拼接时跳过)
    if (data && btn.Ot !== 'notRequired' && columns && columns.length > 0) {
      datavars = {..._data, ...datavars}
      const setField = (col) => {
        if (!col.field) return
        let _key = col.field.toLowerCase()
  
        if (!_initvars.includes(_key)) {
          let _val = datavars.hasOwnProperty(_key) ? datavars[_key] : ''
          let _val = _data.hasOwnProperty(_key) ? _data[_key] : ''
  
          if (col.datatype && /^date/ig.test(col.datatype) && !_val) {
            _val = '1949-10-01'
@@ -1417,7 +1439,7 @@
      _declarefields = ',' + _declarefields
    }
    _sql = `/* 系统生成 */
        Declare @tbid nvarchar(50),@ErrorCode nvarchar(50),@retmsg nvarchar(4000),@BillCode nvarchar(50),@BVoucher nvarchar(50),@FIBVoucherDate nvarchar(50), @FiYear nvarchar(50),@ModularDetailCode nvarchar(50), @UserName nvarchar(50),@FullName nvarchar(50),@RoleID nvarchar(512),@mk_departmentcode nvarchar(512),@mk_organization nvarchar(512),@mk_user_type nvarchar(20),@mk_nation nvarchar(50),@mk_province nvarchar(50),@mk_city nvarchar(50),@mk_district nvarchar(50),@mk_address nvarchar(100),@mk_deleted int,@bid nvarchar(50)${_declarefields}
        Declare @tbid nvarchar(50),@ErrorCode nvarchar(50),@retmsg nvarchar(4000),@BillCode nvarchar(50),@BVoucher nvarchar(50),@FIBVoucherDate nvarchar(50), @FiYear nvarchar(50),@ModularDetailCode nvarchar(50), @UserName nvarchar(50),@FullName nvarchar(50),@RoleID nvarchar(512),@mk_departmentcode nvarchar(512),@mk_organization nvarchar(512),@mk_user_type nvarchar(20),@mk_nation nvarchar(50),@mk_province nvarchar(50),@mk_city nvarchar(50),@mk_district nvarchar(50),@mk_address nvarchar(100),@mk_deleted int,@bid nvarchar(50),@mk_submit_type nvarchar(50)${_declarefields}
      `
  
    let userName = sessionStorage.getItem('User_Name') || ''
@@ -1435,7 +1457,7 @@
    // 初始化凭证及用户信息字段
    _sql += `
        /* 凭证及用户信息初始化赋值 */
        select @BVoucher='',@FIBVoucherDate='',@FiYear='',@ErrorCode='',@retmsg='',@UserName='${userName}', @FullName='${fullName}', @RoleID='${RoleID}', @mk_departmentcode='${departmentcode}', @mk_organization='${organization}', @mk_user_type='${mk_user_type}', @mk_nation='${nation}', @mk_province='${province}', @mk_city='${city}', @mk_district='${district}', @mk_address='${address}', @mk_deleted=1, @bid='${BID}', @BillCode='', @ModularDetailCode=''
        select @BVoucher='',@FIBVoucherDate='',@FiYear='',@ErrorCode='',@retmsg='',@UserName='${userName}', @FullName='${fullName}', @RoleID='${RoleID}', @mk_departmentcode='${departmentcode}', @mk_organization='${organization}', @mk_user_type='${mk_user_type}', @mk_nation='${nation}', @mk_province='${province}', @mk_city='${city}', @mk_district='${district}', @mk_address='${address}', @mk_deleted=1, @bid='${BID}', @mk_submit_type='${submitType}', @BillCode='', @ModularDetailCode=''
        `
  
    // 表单变量赋值
@@ -1511,7 +1533,7 @@
    if (setting.supModule && !BID) {
      notification.warning({
        top: 92,
        message: window.GLOB.dict['sup_key_req'] || '需要上级主键值!',
        message: setting.supModTip || window.GLOB.dict['sup_key_req'] || '需要上级主键值!',
        duration: 5
      })
      _resolve()
@@ -1571,7 +1593,7 @@
              }, 600)
            }
            this.triggerNote(res, _param.ID) // 消息
            this.triggerNote(res, _param) // 消息
            this.execSuccess(res)
          } else {
            this.execError(res)
@@ -1596,7 +1618,7 @@
            setTimeout(() => {
              Api.genericInterface(param).then(res => {
                if (res.status) {
                  this.triggerNote(res, param.ID) // 消息
                  this.triggerNote(res, param) // 消息
                }
                resolve(res)
              }, (error) => {
@@ -1726,11 +1748,23 @@
      record.mk_api_key = res.mk_api_key || ''
      if (res.status) {
        if (res.mk_ex_invoke + '' === 'false' && params.length === 0) {
          this.execSuccess(res)
          _resolve()
        } else if (res.mk_ex_invoke + '' === 'false' && params.length > 0) {
          this.customLoopRequest(params, _resolve)
        res.mk_ex_invoke = res.mk_ex_invoke + ''
        if (res.mk_ex_invoke === 'false') {
          if (params.length === 0) {
            this.execSuccess(res)
            _resolve()
          } else {
            this.customLoopRequest(params, _resolve)
          }
        } else if (res.mk_ex_invoke === 'true_inside') {
          let data = res.mk_in_api && typeof(res.mk_in_api) === 'object' ? res.mk_in_api : {}
          if (!data.hasOwnProperty('mk_api_key')) {
            data.mk_api_key = record.mk_api_key
          }
          this.customCallbackRequest(params, data, record, _resolve)
        } else {
          if (res.mk_ex_data) { // 数据分批执行
            if (Array.isArray(res.mk_ex_data) && res.mk_ex_data.length > 0) {
@@ -1787,6 +1821,7 @@
      url = btn.interface
    }
    url = url.replace(/@mydomain@/ig, window.GLOB.location)
    
    let param = {}
@@ -1805,6 +1840,16 @@
      Object.keys(result).forEach(key => {
        key = key.replace(/^mk_/ig, '')
        param[key] = result[key]
      })
    }
    if (/@.*@/.test(url)) {
      Object.keys(param).forEach(key => {
        let reg = new RegExp('@' + key + '@', 'ig')
        if (reg.test(url)) {
          url = url.replace(reg, param[key])
          delete param[key]
        }
      })
    }
@@ -1920,6 +1965,10 @@
        if (params.length === 0) {
          this.execSuccess(result)
          _resolve()
        } else if (btn.execInterval) {
          setTimeout(() => {
            this.customLoopRequest(params, _resolve)
          }, btn.execInterval)
        } else {
          this.customLoopRequest(params, _resolve)
        }
@@ -1957,6 +2006,10 @@
        if (params.length === 0) {
          this.execSuccess(result)
          _resolve()
        } else if (btn.execInterval) {
          setTimeout(() => {
            this.customLoopRequest(params, _resolve)
          }, btn.execInterval)
        } else {
          this.customLoopRequest(params, _resolve)
        }
@@ -1974,11 +2027,15 @@
    Api.genericInterface(param, btn.$callbackScript, 'callback').then(res => {
      if (res.status) {
        this.triggerNote(res, param.ID) // 消息
        this.triggerNote(res, param) // 消息
        if (params.length === 0) {
          this.execSuccess(res)
          _resolve()
        } else if (btn.execInterval) {
          setTimeout(() => {
            this.customLoopRequest(params, _resolve)
          }, btn.execInterval)
        } else {
          this.customLoopRequest(params, _resolve)
        }
@@ -2321,11 +2378,15 @@
    Api.genericInterface(param).then(res => {
      if (res.status) {
        this.triggerNote(res, param.ID) // 消息
        this.triggerNote(res, param) // 消息
        if (params.length === 0) {
          this.execSuccess(res)
          _resolve()
        } else if (btn.execInterval) {
          setTimeout(() => {
            this.innerLoopRequest(params, btn, _resolve)
          }, btn.execInterval)
        } else {
          this.innerLoopRequest(params, btn, _resolve)
        }
@@ -2355,7 +2416,7 @@
    Api.genericInterface(param).then(res => {
      if (res.status) {
        this.triggerNote(res, param.ID) // 消息
        this.triggerNote(res, param) // 消息
        if (params.length === 0) {
          this.execSuccess(res)
@@ -2379,7 +2440,7 @@
            return new Promise(resolve => {
              Api.genericInterface(unCheckParam).then(result => {
                if (result.status) {
                  that.triggerNote(result, param.ID) // 消息
                  that.triggerNote(result, param) // 消息
          
                  if (params.length === 0) {
                    that.execSuccess(result)
@@ -2415,7 +2476,7 @@
   * @description 外部请求循环执行
   */
  outerLoopRequest = (params, _resolve) => {
    const { setting, btn } = this.props
    const { setting, btn, BID } = this.props
    let param = params.shift()
@@ -2444,11 +2505,29 @@
    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)
          _resolve()
        } else if ((res.mk_ex_invoke === 'false' || res.mk_ex_invoke === false) && params.length > 0) {
          this.outerLoopRequest(params, _resolve)
        res.mk_ex_invoke = res.mk_ex_invoke + ''
        if (res.mk_ex_invoke === 'false') {
          if (params.length === 0) {
            this.execSuccess(res)
            _resolve()
          } else {
            this.outerLoopRequest(params, _resolve)
          }
        } else if (res.mk_ex_invoke === 'true_inside') {
          let data = res.mk_in_api && typeof(res.mk_in_api) === 'object' ? res.mk_in_api : {}
          if (!data.hasOwnProperty('mk_api_key')) {
            data.mk_api_key = res.mk_api_key || ''
          }
          // 使用处理后的数据调用外部接口
          let keys = Object.keys(data) // 提交外部接口前,添加BID
          if (BID && keys.filter(key => key.toLowerCase() === 'bid').length === 0) {
            data.BID = BID
          }
          this.outerCallbackRequest(params, data, record, {}, _resolve)
        } else {
          delete res.mk_ex_invoke
          delete res.ErrCode
@@ -2458,8 +2537,8 @@
          // 使用处理后的数据调用外部接口
          let keys = Object.keys(res) // 提交外部接口前,添加BID
          if (this.props.BID && keys.filter(key => key.toLowerCase() === 'bid').length === 0) {
            res.BID = this.props.BID
          if (BID && keys.filter(key => key.toLowerCase() === 'bid').length === 0) {
            res.BID = BID
          }
          if (res.mk_api_key) {
@@ -2575,6 +2654,10 @@
        if (params.length === 0) {
          this.execSuccess(result)
          _resolve()
        } else if (btn.execInterval) {
          setTimeout(() => {
            this.outerLoopRequest(params, _resolve)
          }, btn.execInterval)
        } else {
          this.outerLoopRequest(params, _resolve)
        }
@@ -2619,6 +2702,10 @@
        if (params.length === 0) {
          this.execSuccess(result)
          _resolve()
        } else if (btn.execInterval) {
          setTimeout(() => {
            this.outerLoopRequest(params, _resolve)
          }, btn.execInterval)
        } else {
          this.outerLoopRequest(params, _resolve)
        }
@@ -2636,12 +2723,16 @@
    Api.genericInterface(param, btn.$callbackScript, 'callback').then(res => {
      if (res.status) {
        this.triggerNote(res, param.ID) // 消息
        this.triggerNote(res, param) // 消息
        // 一次请求成功,进行下一项请求
        if (params.length === 0) {
          this.execSuccess(res)
          _resolve()
        } else if (btn.execInterval) {
          setTimeout(() => {
            this.outerLoopRequest(params, _resolve)
          }, btn.execInterval)
        } else {
          this.outerLoopRequest(params, _resolve)
        }
@@ -2779,7 +2870,11 @@
          duration: 5
        })
      } else if (window.GLOB.localSystemApi) {
        Api.cacheInterface({rduri: window.GLOB.localSystemApi.replace('dostars', 'excache')}).then(result => {
        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,
@@ -2854,7 +2949,7 @@
      res.message = res.message.replace(/\s*<<.*>>\s*/g, '')
      val = val ? val[0].replace(/<<|>>/g, '') : ''
      if (/^http/.test(val)) {
      if (/^(http|\/\/)/.test(val)) {
        let audio = document.createElement('audio')
        audio.src = val
        audio.play()
@@ -2864,9 +2959,9 @@
        res.ErrCode = '-1'
      }
    }
    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 = ''
@@ -2930,12 +3025,37 @@
    }
    let tabId = ''
    let menu = null
    if (btn.refreshTab && btn.refreshTab.length > 0) {
      tabId = btn.refreshTab[btn.refreshTab.length - 1]
    }
    if (window.backend && btn.outerFunc && ['bd_workers_create_user_sso', 's_susers_del', 's_susers_add', 's_susers_update', 's_susers_start', 's_susers_admin'].includes(btn.outerFunc.toLowerCase())) {
      setTimeout(() => {
        this.clearBackSqlCache()
      }, 300)
    }
    if (btn.openmenu && Array.isArray(btn.openmenu) && btn.openmenu.length > 0 && sign !== '@no_target_menu@') {
      let menuId = btn.openmenu.slice(-1)[0]
      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 (tabId && btn.$MenuID === tabId) { // 刷新当前菜单时,停止其他操作
      MKEmitter.emit('reloadMenuView', tabId)
      MKEmitter.emit('reloadMenuView', tabId, btn.urlPar === 'true')
      if (menu) {
        MKEmitter.emit('modifyTabs', menu, true)
      }
      return
    }
@@ -2953,15 +3073,30 @@
    
    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)
        })
        if (btn.syncDelay) {
          this.delayTimer && clearTimeout(this.delayTimer)
          this.delayTimer = setTimeout(() => {
            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)
            })
          }, btn.syncDelay)
        } else {
          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 {
@@ -2977,7 +3112,7 @@
    }
    if (tabId) {
      MKEmitter.emit('reloadMenuView', tabId)
      MKEmitter.emit('reloadMenuView', tabId, btn.urlPar === 'true')
    }
    
    if (btn.switchTab && btn.switchTab.length > 0) {
@@ -2991,24 +3126,8 @@
      node && node.scrollIntoView({behavior: 'smooth', block: 'center', inline: 'nearest'})
    }
    if (btn.openmenu && Array.isArray(btn.openmenu) && btn.openmenu.length > 0 && sign !== '@no_target_menu@') {
      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 (menu) {
      MKEmitter.emit('modifyTabs', menu, true)
    }
    if (btn.execSuccess === 'popclose' && btn.$tabId) { // 标签关闭刷新
@@ -3044,11 +3163,23 @@
    }
  }
  triggerNote = (res, ID) => {
  clearBackSqlCache = () => {
    Api.cacheInterface({}).then(res => {
      if (!res.status) {
        notification.warning({
          top: 92,
          message: res.message || '缓存清空失败!',
          duration: 5
        })
      }
    })
  }
  triggerNote = (res, param) => {
    const { btn } = this.props
    if (!btn.verify) return
    if (btn.verify.noteEnable !== 'true' && btn.verify.wxNote !== 'true' && btn.verify.printEnable !== 'true' && btn.verify.emailEnable !== 'true') return
    if (btn.verify.noteEnable !== 'true' && btn.verify.wxNote !== 'true' && btn.verify.printEnable !== 'true' && btn.verify.emailEnable !== 'true' && btn.verify.DeepSeekable !== 'true') return
    let id = ''
    if (btn.output) {
@@ -3056,7 +3187,16 @@
    }
    if (btn.verify.printEnable === 'true') {
      this.billPrint(id || ID)
      let _id = id || param.ID
      if (!_id && param.data && param.data[0] && param.data[0].exps) {
        param.data[0].exps.forEach(cell => {
          if (cell.key === 'ID') {
            _id = cell.value
          }
        })
      }
      this.billPrint(_id)
    }
    if (!id) return
@@ -3066,6 +3206,9 @@
    }
    if (btn.verify.emailEnable === 'true') {
      this.sendEmail(btn.verify, id)
    }
    if (btn.verify.DeepSeekable === 'true') {
      this.openDeepSeek(id)
    }
    if (btn.verify.wxNote === 'true') {
      if (btn.verify.wxTemplateId === 'mk_category_temp') {
@@ -3547,6 +3690,38 @@
    })
  }
  openDeepSeek = (id) => {
    let param = {
      func: 's_get_deepseek_local',
      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
      }
      if (res.deepseek_text) {
        sessionStorage.setItem('deepseek_sql', res.deepseek_text)
        window.open('#/ai')
        setTimeout(() => {
          sessionStorage.removeItem('deepseek_sql')
        }, 0)
      }
    })
  }
  /**
   * @description 操作失败后处理
   * 1、状态码为 E、N、F、NM 时,显示相应提示信息
@@ -3592,7 +3767,7 @@
      res.message = res.message.replace(/\s*<<.*>>\s*/g, '')
      val = val ? val[0].replace(/<<|>>/g, '') : ''
      if (/^http/.test(val)) {
      if (/^(http|\/\/)/.test(val)) {
        let audio = document.createElement('audio')
        audio.src = val
        audio.play()
@@ -3601,9 +3776,9 @@
      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') {
@@ -3662,7 +3837,11 @@
      loadingTotal: '',
    })
    if (btnconfig && btnconfig.setting && btnconfig.setting.errFocus) {
    if (window.CACHE.errFocusId && (btnconfig || btn.OpenType === 'formSubmit')) {
      MKEmitter.emit('mkFC', 'focus', window.CACHE.errFocusId)
      window.CACHE.errFocusId = ''
    } else if (btnconfig && btnconfig.setting && btnconfig.setting.errFocus) {
      MKEmitter.emit('mkFC', 'focus', btnconfig.setting.errFocus)
    }
@@ -3676,7 +3855,7 @@
        tabId = btn.refreshTab[btn.refreshTab.length - 1]
      }
      if (tabId && btn.$MenuID === tabId) { // 刷新当前菜单时,停止其他操作
        MKEmitter.emit('reloadMenuView', tabId)
        MKEmitter.emit('reloadMenuView', tabId, btn.urlPar === 'true')
        return
      }
@@ -3684,15 +3863,30 @@
      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)
          })
          if (btn.syncDelay) {
            this.delayTimer && clearTimeout(this.delayTimer)
            this.delayTimer = setTimeout(() => {
              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)
              })
            }, btn.syncDelay)
          } else {
            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 {
@@ -3708,7 +3902,7 @@
      }
      if (tabId) {
        MKEmitter.emit('reloadMenuView', tabId)
        MKEmitter.emit('reloadMenuView', tabId, btn.urlPar === 'true')
      }
    }
@@ -3732,6 +3926,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) { // 标签关闭刷新
@@ -3842,11 +4065,11 @@
  /**
   * @description 模态框(表单),确认
   */
  handleOk = () => {
  handleOk = (submitType = '') => {
    if (!this.formRef) return
    
    this.formRef.handleConfirm().then(res => {
      this.setState({ confirmLoading: true })
      this.setState({ confirmLoading: true, submitType: submitType })
      this.execSubmit(this.state.selines, () => { this.setState({ confirmLoading: false }) }, res)
    })
@@ -3859,7 +4082,8 @@
    this.setState({
      loading: false,
      visible: false,
      confirmLoading: false
      confirmLoading: false,
      submitType: ''
    })
    this.preCallback && this.preCallback()
@@ -3901,6 +4125,10 @@
      let key = item.field.toLowerCase()
      let _readin = item.readin !== 'false'
      if (item.type === 'linkMain' && item.verifyVal === 'true') {
        _item.$verify = true
        _item.label = item.label
      }
      if (_item.type === 'date') { // 时间兼容
        _item.precision = item.precision || 'day'
      } else if (_item.type === 'datetime') {
@@ -3969,8 +4197,13 @@
            _item.value = _item.value.replace(/(^\s*|\s*$)/g, '')
          }
        }
        if (_item.type === 'text' && /@appkey@|@SessionUid@|@bid@/ig.test(_item.value)) { // 特殊字段替换
          _item.value = _item.value.replace(/^(\s*)@appkey@(\s*)$/ig, window.GLOB.appkey).replace(/^(\s*)@SessionUid@(\s*)$/ig, (localStorage.getItem('SessionUid') || '')).replace(/^(\s*)@bid@(\s*)$/ig, (BID || ''))
        if (_item.type === 'text') {
          if (/@appkey@|@SessionUid@|@bid@/ig.test(_item.value)) { // 特殊字段替换
            _item.value = _item.value.replace(/^(\s*)@appkey@(\s*)$/ig, window.GLOB.appkey).replace(/^(\s*)@SessionUid@(\s*)$/ig, (localStorage.getItem('SessionUid') || '')).replace(/^(\s*)@bid@(\s*)$/ig, (BID || ''))
          }
          if (/@currentYear@/ig.test(_item.value)) { // 系统变量替换
            _item.value = _item.value.replace(/@currentYear@/ig, moment().format('YYYY'))
          }
        }
        if (_item.type === 'text' && item.lenControl && item.lenControl !== 'limit') {
          if (item.lenControl === 'left') {
@@ -4032,13 +4265,14 @@
   */
  getModels = () => {
    const { BID, btn, BData } = this.props
    const { btnconfig, visible, dict } = this.state
    const { btnconfig, visible, dict, confirmLoading, submitType, loadingNumber, loadingTotal } = this.state
    if (!btnconfig || !btnconfig.setting) return null
    let title = btn.label
    let width = btnconfig.setting.width > 100 ? btnconfig.setting.width : btnconfig.setting.width + 'vw'
    let clickouter = btnconfig.setting.clickouter === 'close'
    let num = loadingNumber && !loadingTotal ? `(${loadingNumber}) ` : ''
    if (btnconfig.setting.display === 'drawer') {
      let height = '100vh'
@@ -4061,19 +4295,23 @@
          <MutilForm
            BID={BID}
            action={btnconfig}
            inputSubmit={this.handleOk}
            inputSubmit={() => this.handleOk()}
            data={this.state.selines[0]}
            BData={BData}
            wrappedComponentRef={(inst) => this.formRef = inst}
          />
          <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'}}>
          {btnconfig.setting.formType === 'check' ? <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' ? dict['cancel'] || '取消' : dict['close'] || '关闭'}
              {dict['close'] || '关闭'}
            </Button>
            {btnconfig.setting.formType !== 'check' ? <Button onClick={this.handleOk} loading={this.state.confirmLoading} type="primary">
              {dict['ok'] || '确定'}
            </Button> : null}
          </div>
          </div> : <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 }}>
              {dict['cancel'] || '取消'}
            </Button>
            {btn.extBtn === 'true' ? <Button className={'extend-btn ' + (btn.extStyle || '')} disabled={confirmLoading && submitType !== btn.extValue} loading={confirmLoading && submitType === btn.extValue} onClick={() => this.handleOk(btn.extValue)}>{btn.extLabel}</Button> : null}
            {btn.extBtn === 'true' ? <Button className={'confirm-btn ' + (btn.confStyle || '')} disabled={confirmLoading && submitType !== ''} loading={confirmLoading && submitType === ''} onClick={() => this.handleOk()}>{btn.confLabel || dict['ok'] || '确定'}</Button> : null}
            {btn.extBtn !== 'true' ? <Button type="primary" loading={confirmLoading} onClick={() => this.handleOk()}>{dict['ok'] || '确定'}</Button> : null}
          </div>}
        </Drawer>
      )
    } else {
@@ -4099,18 +4337,20 @@
          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}
          onCancel={this.handleCancel}
          footer={[
            <Button key="cancel" onClick={this.handleCancel}>{dict['cancel'] || '取消'}</Button>,
            btn.extBtn === 'true' ? <Button key="extend" className={'extend-btn ' + (btn.extStyle || '')} disabled={confirmLoading && submitType !== btn.extValue} loading={confirmLoading && submitType === btn.extValue} onClick={() => this.handleOk(btn.extValue)}>{submitType === btn.extValue ? num : ''}{btn.extLabel}</Button> : null,
            btn.extBtn === 'true' ? <Button key="confirm" className={'confirm-btn ' + (btn.confStyle || '')} disabled={confirmLoading && submitType !== ''} loading={confirmLoading && submitType === ''} onClick={() => this.handleOk()}>{submitType === '' ? num : ''}{btn.confLabel || dict['ok'] || '确定'}</Button> : null,
            btn.extBtn !== 'true' ? <Button key="confirm" type="primary" loading={confirmLoading} onClick={() => this.handleOk()}>{num}{dict['ok'] || '确定'}</Button> : null
          ]}
          destroyOnClose
        >
          <MutilForm
            BID={BID}
            action={btnconfig}
            inputSubmit={this.handleOk}
            inputSubmit={() => this.handleOk()}
            data={this.state.selines[0]}
            BData={BData}
            wrappedComponentRef={(inst) => this.formRef = inst}