king
2020-06-08 46fa548514ba2a438908586e2b54ed742777e9b0
src/templates/sharecomponent/settingcomponent/settingform/index.jsx
@@ -1,16 +1,18 @@
import React, {Component} from 'react'
import PropTypes from 'prop-types'
import { fromJS } from 'immutable'
import { Form, Row, Col, Input, Radio, Select, Tooltip, Icon, notification, InputNumber, Modal, Button, Table, Popconfirm } from 'antd'
import { Form, Row, Col, Input, Radio, Select, Tooltip, Icon, notification, InputNumber, Modal, Table, Popconfirm, Typography, Button } from 'antd'
import moment from 'moment'
import Api from '@/api'
import Utils from '@/utils/utils.js'
import SettingUtils from './utils.jsx'
import CustomScript from './customscript'
import './index.scss'
const { TextArea } = Input
const { confirm } = Modal
const { Paragraph } = Typography
class SettingForm extends Component {
  static propTpyes = {
@@ -24,6 +26,10 @@
  state = {
    formlist: [],
    btnloading: false,
    search: '',
    arr_field: '',
    regoptions: [],
    setting: null,
    view: 'normal',
    systemScripts: [{
@@ -34,24 +40,15 @@
      {
        title: 'SQL',
        dataIndex: 'sql',
        width: '60%'
      },
      {
        title: '初始化sql',
        dataIndex: 'initsql',
        width: '12%',
        render: (text, record) => {
          if (record.initsql === 'true') {
            return '是'
          } else {
            return '否'
          }
        }
        width: '70%',
        render: (text) => (
          <Paragraph copyable ellipsis={{ rows: 5, expandable: true }}>{text}</Paragraph>
        )
      },
      {
        title: '状态',
        dataIndex: 'status',
        width: '8%',
        width: '10%',
        render: (text, record) => record.status === 'false' ?
          (
            <div>
@@ -91,6 +88,8 @@
  }
  UNSAFE_componentWillMount() {
    const { config } = this.props
    let _formlist = fromJS(this.props.formlist).toJS()
    let interType = 'inner'
@@ -106,8 +105,30 @@
    delete _setting.subtabs
    // 搜索条件
    let allSearch = Utils.initMainSearch(config.search)
    allSearch = Utils.getAllSearchOptions(allSearch)
    // 显示列字段,用于查询
    let arr_field = []
    config.columns.forEach(col => {
      if (col.field) {
        arr_field.push(col.field)
      }
    })
    arr_field = arr_field.join(',')
    let _search = this.formatSearch(config.search)
    _search = Utils.joinMainSearchkey(_search)
    _search = _search.replace(/@\$@/ig, '')
    _search = _search ? 'where ' + _search : ''
    this.setState({
      setting: _setting,
      search: _search,
      arr_field: arr_field,
      regoptions: allSearch,
      formlist: _formlist.map(item => {
        if (interType === 'inner' && ['sysInterface', 'interface', 'outerFunc'].includes(item.key)) {
          item.hidden = true
@@ -164,7 +185,7 @@
  }
  handleConfirm = (otype) => {
    const { menu, config, type } = this.props
    const { menu, type } = this.props
    const { view, setting } = this.state
    // 表单提交时检查输入值是否正确
@@ -180,15 +201,46 @@
            values = {...setting, ...values}
            // 数据源前端验证
            if (values.interType === 'inner' && !values.innerFunc && !values.dataresource) {
            if (values.interType === 'inner' && !values.innerFunc && values.default !== 'false' && !values.dataresource) {
              notification.warning({
                top: 92,
                message: '请自定义函数或填写数据源!',
                message: '请填写内部函数或数据源!',
                duration: 5
              })
              reject()
              return
            } else {
            } else if (values.interType === 'inner' && !values.innerFunc && values.default !== 'false' && values.dataresource) {
              let _quot = values.dataresource.match(/'{1}/g)
              let _lparen = values.dataresource.match(/\({1}/g)
              let _rparen = values.dataresource.match(/\){1}/g)
              _quot = _quot ? _quot.length : 0
              _lparen = _lparen ? _lparen.length : 0
              _rparen = _rparen ? _rparen.length : 0
              if (_quot % 2 !== 0) {
                notification.warning({
                  top: 92,
                  message: '数据源中\'必须成对出现',
                  duration: 5
                })
                return
              } else if (_lparen !== _rparen) {
                notification.warning({
                  top: 92,
                  message: '数据源中()必须成对出现',
                  duration: 5
                })
                return
              } else if (/--/ig.test(values.dataresource)) {
                notification.warning({
                  top: 92,
                  message: '数据源中,不可出现字符 -- ,注释请用 /*内容*/',
                  duration: 5
                })
                return
              }
              let error = Utils.verifySql(values.dataresource)
  
              if (error) {
@@ -197,6 +249,7 @@
                  message: '数据源中不可使用' + error,
                  duration: 5
                })
                reject()
                return
              }
            }
@@ -204,6 +257,7 @@
            // 数据源保存
            if (
              values.interType === 'inner' && !values.innerFunc &&
              values.default !== 'false' &&
              /[^\s]+\s+[^\s]+/ig.test(values.dataresource) &&
              this.props.config.setting.dataresource !== values.dataresource
            ) {
@@ -220,85 +274,16 @@
              Api.getLocalConfig(param)
            }
            // 合成自定义script
            let _customScript = ''
            values.scripts.forEach(item => {
              if (item.status === 'false' || item.initsql !== 'true') return
              _customScript += `
                ${item.sql}
              `
            })
            values.scripts.forEach(item => {
              if (item.status === 'false' || item.initsql === 'true') return
              _customScript += `
                ${item.sql}
              `
            })
            values.customScript = _customScript
            // 数据源后台语法验证
            if (values.interType === 'inner' && !values.innerFunc && /\s/.test(values.dataresource)) {
              if (otype === 'change') { // 切换自定义设置
                this.setState({
                  sqlVerifing: true
                })
              }
              let _dataresource = values.dataresource
              if (values.queryType === 'statistics') {
                let allSearch = Utils.initMainSearch(config.search)
                allSearch = Utils.getAllSearchOptions(allSearch)
                let options = allSearch.map(item => {
                  return {
                    reg: new RegExp('@' + item.key + '@', 'ig'),
                    value: item.value
                  }
                })
                options.forEach(item => {
                  _dataresource = _dataresource.replace(item.reg, `'${item.value}'`)
                })
              }
              let param = {
                func: 's_debug_sql',
                LText: _dataresource
              }
              param.LText = Utils.formatOptions(param.LText)
              param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss') + '.000'
              param.secretkey = Utils.encrypt(param.LText, param.timestamp)
              Api.getLocalConfig(param).then(result => {
                if (result.status) {
                  if (otype === 'change') {
                    this.setState({
                      sqlVerifing: false,
                      setting: values
                    }, () => {
                      resolve()
                    })
                  } else {
                    resolve(values)
                  }
                } else {
                  this.setState({sqlVerifing: false})
                  Modal.error({
                    title: result.message
                  })
                }
              })
            } else if (otype === 'change') {
            if (otype === 'change') {
              this.setState({
                setting: values,
              }, () => {
                resolve()
              })
            } else {
              resolve(values)
              values.customScript = this.getCustomScript(values)
              this.sqlverify(values, resolve, reject)
            }
          } else {
            reject(err)
@@ -306,46 +291,85 @@
        })
      })
    } else {
      let _loading = false
      let _setting = fromJS(this.state.setting).toJS()
      _setting.customScript = this.getCustomScript(_setting)
      if (this.scriptsForm && this.scriptsForm.props.form.getFieldValue('sql')) {
        _loading = true
      }
      let _customScript = ''
      _setting.scripts.forEach(item => {
        if (item.status === 'false' || item.initsql !== 'true') return
        _customScript += `
          ${item.sql}
        `
      })
      _setting.scripts.forEach(item => {
        if (item.status === 'false' || item.initsql === 'true') return
        _customScript += `
          ${item.sql}
        `
      })
      _setting.customScript = _customScript
      let _this = this
      return new Promise((resolve, reject) => {
        if (_loading) {
        if (this.scriptsForm && this.scriptsForm.props.form.getFieldValue('sql')) {
          confirm({
            content: `存在未保存项,确定提交吗?`,
            okText: this.props.dict['model.confirm'],
            cancelText: this.props.dict['header.cancel'],
            onOk() {
              resolve(_setting)
              _this.sqlverify(_setting, resolve, reject)
            },
            onCancel() {
              reject()
            }
          })
        } else {
          resolve(_setting)
          this.sqlverify(_setting, resolve, reject)
        }
      })
    }
  }
  getCustomScript = (setting) => {
    let _customScript = ''
    if (setting.scripts && setting.scripts.length > 0) {
      setting.scripts.forEach(item => {
        if (item.status === 'false') return
        _customScript += `
          ${item.sql}
        `
      })
    }
    if (_customScript) {
      _customScript = `declare @ErrorCode nvarchar(50),@retmsg nvarchar(4000) select @ErrorCode='',@retmsg =''
        ${_customScript}
      `
    }
    return _customScript
  }
  sqlverify = (_setting, _resolve, _reject, isChange = false) => {
    const { arr_field, regoptions, search } = this.state
    if (!isChange && _setting.interType === 'inner' && !_setting.innerFunc && _setting.default === 'false' && !_setting.customScript) {
      notification.warning({
        top: 92,
        message: '不执行默认sql时,请添加自定义脚本!',
        duration: 5
      })
      _reject()
      return
    }
    if (_setting.interType === 'inner' && !_setting.innerFunc && _setting.default !== 'false') {
      let param = {
        func: 's_debug_sql',
        LText: SettingUtils.getDebugSql(_setting, arr_field, regoptions, search)
      }
      param.LText = Utils.formatOptions(param.LText)
      param.timestamp = moment().format('YYYY-MM-DD HH:mm:ss') + '.000'
      param.secretkey = Utils.encrypt(param.LText, param.timestamp)
      Api.getLocalConfig(param).then(result => {
        if (result.status) {
          _resolve(_setting)
        } else {
          _reject()
          Modal.error({
            title: result.message
          })
        }
      })
    } else {
      _resolve(_setting)
    }
  }
@@ -444,11 +468,11 @@
  }
  changeView = () => {
    const { view } = this.state
    const { view, arr_field, regoptions, search } = this.state
    let _this = this
    if (view === 'normal') {
      this.handleConfirm('change').then(() => {
        const { config } = this.props
        const { setting } = this.state
        if (setting.interType !== 'inner' || (setting.interType === 'inner' && setting.innerFunc)) {
@@ -460,20 +484,7 @@
          return
        }
        let _search = this.formatSearch(config.search)
        _search = Utils.joinMainSearchkey(_search)
        _search = _search.replace(/@\$@/ig, '')
        _search = _search ? 'where ' + _search : ''
        let arr_field = []
        config.columns.forEach(col => {
          if (col.field) {
            arr_field.push(col.field)
          }
        })
        arr_field = arr_field.join(',')
        let _search = search
        
        let _dataresource = setting.dataresource
@@ -482,18 +493,15 @@
        }
        if (setting.queryType === 'statistics') { // 统计数据源,内容替换
          let allSearch = Utils.initMainSearch(config.search)
          allSearch = Utils.getAllSearchOptions(allSearch)
          let options = allSearch.map(item => {
          // 正则替换
          let _regoptions = regoptions.map(item => {
            return {
              reg: new RegExp('@' + item.key + '@', 'ig'),
              value: item.value
              value: `'${item.value}'`
            }
          })
          options.forEach(item => {
            _dataresource = _dataresource.replace(item.reg, `'${item.value}'`)
          _regoptions.forEach(item => {
            _dataresource = _dataresource.replace(item.reg, item.value)
          })
          _search = ''
@@ -503,18 +511,36 @@
        let _scripts = fromJS(this.state.systemScripts).toJS()
        _scripts[0].value = LText
        this.setState({
          view: 'custom',
          systemScripts: _scripts
        })
        this.scrolltop()
      }, () => {
        this.setState({sqlVerifing: false})
        if (setting.default === 'false') {
          this.setState({
            view: 'custom',
            btnloading: false,
            systemScripts: _scripts
          })
          this.scrolltop()
        } else {
          this.setState({
            btnloading: true
          })
          new Promise((resolve, reject) => {
            this.sqlverify(setting, resolve, reject, true)
          }).then(() => {
            this.setState({
              view: 'custom',
              btnloading: false,
              systemScripts: _scripts
            })
            this.scrolltop()
          }, () => {
            this.setState({
              btnloading: false
            })
          })
        }
      })
    } else {
      let _loading = false
      let _this = this
      if (this.scriptsForm && this.scriptsForm.props.form.getFieldValue('sql')) {
        _loading = true
@@ -535,11 +561,11 @@
          onCancel() {}
        })
      } else {
        this.setState({
        _this.setState({
          view: 'normal'
        })
        this.scrolltop()
        _this.scrolltop()
      }
    }
  }
@@ -819,8 +845,8 @@
  }
  render() {
    const { config } = this.props
    const { formlist, view, setting, scriptsColumns, systemScripts } = this.state
    const { config, type } = this.props
    const { formlist, view, setting, scriptsColumns, systemScripts, arr_field, regoptions, search, btnloading } = this.state
    const formItemLayout = {
      labelCol: {
        xs: { span: 24 },
@@ -835,10 +861,14 @@
    return (
      <div className="model-table-setting-form-box" id="model-table-setting-form-box">
        {view ==='custom' ? <div>
          <Icon className="setting-custom-back" onClick={this.changeView} type="arrow-left" />
          <CustomScript
            dict={this.props.dict}
            type={type}
            setting={setting}
            customScripts={setting.scripts}
            swhere={search}
            arr_field={arr_field}
            regoptions={regoptions}
            dict={this.props.dict}
            searches={config.search}
            systemScripts={systemScripts}
            scriptsChange={this.scriptsChange}
@@ -856,7 +886,7 @@
        <Form {...formItemLayout} className="model-table-setting-form" id="model-table-setting-form">
          {view !=='custom' ? <Row gutter={24}>{this.getFields(formlist)}</Row> : null}
          <Row gutter={24}>
            {view !=='custom' ? <Button loading={this.state.sqlVerifing} onClick={this.changeView} style={{border: 0, boxShadow: 'unset',float: 'right', color: '#1890ff', marginRight: 12, cursor: 'pointer'}}>自定义设置<Icon style={{marginLeft: 5}} type="right" /></Button> : null}
            {view !=='custom' ? <Button onClick={this.changeView} className="to-custom-script" loading={btnloading}>自定义设置<Icon style={{marginLeft: 5}} type="right" /></Button> : null}
            {view ==='custom' ? <span onClick={this.changeView} style={{float: 'left', color: '#1890ff', marginLeft: 12, marginTop: 15, cursor: 'pointer'}}><Icon style={{marginRight: 5}} type="left" />基础设置</span> : null}
          </Row>
        </Form>