king
2021-02-05 b2298c8c996dd176c2bd7d424a1aa709cbb97965
2021-02-05
14个文件已修改
2个文件已添加
436 ■■■■ 已修改文件
src/api/cacheutils.js 25 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/api/index.js 33 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/assets/css/viewstyle.scss 7 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/Image/index.jsx 2 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/breadview/index.jsx 160 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/breadview/index.scss 73 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/header/index.jsx 63 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/components/tabview/index.jsx 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/index.js 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/router/index.js 3 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/tabviews/zshare/actionList/tabbutton/index.jsx 26 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/templates/sharecomponent/actioncomponent/actionform/index.jsx 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/login/index.jsx 4 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/main/index.jsx 11 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/menudesign/index.jsx 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/views/menudesign/menuform/index.jsx 20 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/api/cacheutils.js
@@ -306,6 +306,31 @@
  }
  /**
   * @description 删除IndexedDB中保存的配置信息-批量
   */
  static delIndexDBConfig (keys) {
    if (!window.GLOB.IndexDB || !keys) return
    let objectStore = window.GLOB.IndexDB.transaction(['configs'], 'readwrite').objectStore('configs')
    objectStore.openCursor().onsuccess = (event) => {
      let cursor = event.target.result
      if (cursor) {
        if (cursor.value && keys.includes(cursor.value.menuid)) {
          let request = objectStore.delete(cursor.key)
          request.onerror = () => {
            window.GLOB.IndexDB = null
          }
        }
        cursor.continue()
      }
    }
  }
  /**
   * @description 获取IndexedDB中的配置信息
   */
  static getIndexDBMenuConfig (MenuID, userid) {
src/api/index.js
@@ -274,14 +274,15 @@
                  clear = true
                }
              })
              if (clear) {
                CacheUtils.clearWebSqlConfig()
              } else {
                let keys = res.menu_data.map(mid => `'${mid.menuid}'`).join(',')
                CacheUtils.delWebSqlConfig(keys)
              }
            }
            if (clear) {
              CacheUtils.clearWebSqlConfig()
            } else if (res.menu_data && res.menu_data.length > 0) {
              let keys = res.menu_data.map(mid => `'${mid.menuid}'`).join(',')
              CacheUtils.delWebSqlConfig(keys)
            }
            if (msg.version) {
              CacheUtils.updateWebSqlTime(curTime)
            } else {
@@ -303,21 +304,33 @@
            func: 's_get_app_version',
            modifydate: msg.createDate || curTime,
          }
          this.getSystemConfig(param).then(res => {
            if (!res.status) {
              reject()
              return
            }
            let clear = false
            let version = res.app_version || '1.00'
            appVersion.newVersion = version
            appVersion.oldVersion = appVersion.oldVersion || version
  
            if (res.menu_data && res.menu_data.length > 0) {
              CacheUtils.clearIndexDBConfig()
              res.menu_data.forEach(mid => {
                if (systemMenuKeys.indexOf(mid.menuid) > -1) {
                  clear = true
                }
              })
              if (clear) {
                CacheUtils.clearIndexDBConfig()
              } else if (res.menu_data && res.menu_data.length > 0) {
                let keys = res.menu_data.map(mid => `'${mid.menuid}'`)
                CacheUtils.delIndexDBConfig(keys)
              }
            }
            CacheUtils.updateIndexDBversion({version: version, createDate: curTime})
            CacheUtils.updateIndexDBversion({version: appVersion.oldVersion, createDate: curTime})
  
            resolve(appVersion)
          })
src/assets/css/viewstyle.scss
@@ -167,6 +167,13 @@
        color: $color5;
      }
    }
    >.mk-breadview-wrap {
      >.ant-breadcrumb {
        .anticon-redo:hover, .anticon-home:hover {
          color: $color5;
        }
      }
    }
  }
  .custom-data-card-box, .custom-prop-card-box {
    .data-zoom.radio .card-row-list > .ant-col:not(.active):not(.selected):hover > .card-item-box, .data-zoom.checkbox .card-row-list > .ant-col:not(.active):not(.selected):hover > .card-item-box {
src/components/Image/index.jsx
@@ -6,6 +6,8 @@
    let Img = new Image()
    Img.src = this.props.url
    
    if (!this.ImageWrapDom) return
    if (Img.complete) {
      this.setSize(Img.width, Img.height)
    } else {
src/components/breadview/index.jsx
New file
@@ -0,0 +1,160 @@
import React, {Component} from 'react'
import {connect} from 'react-redux'
import { is, fromJS } from 'immutable'
import { BackTop, Breadcrumb, Icon} from 'antd'
import moment from 'moment'
import 'moment/locale/zh-cn'
import asyncComponent from '@/utils/asyncLoadComponent'
import NotFount from '@/components/404'
import mzhCN from '@/locales/zh-CN/main.js'
import menUS from '@/locales/en-US/main.js'
import MKEmitter from '@/utils/events.js'
import './index.scss'
const Home = asyncComponent(() => import('@/tabviews/home'))
const CustomPage = asyncComponent(() => import('@/tabviews/custom'))
const CommonTable = asyncComponent(() => import('@/tabviews/commontable'))
const CalendarPage = asyncComponent(() => import('@/tabviews/calendar'))
const TreePage = asyncComponent(() => import('@/tabviews/treepage'))
const Iframe = asyncComponent(() => import('@/tabviews/iframe'))
const RoleManage = asyncComponent(() => import('@/tabviews/rolemanage'))
const FormTab = asyncComponent(() => import('@/tabviews/formtab'))
let service = ''
if (process.env.NODE_ENV === 'production') {
  service = document.location.origin + '/' + window.GLOB.service + 'zh-CN/'
} else {
  service = window.GLOB.location + '/' + window.GLOB.service + 'zh-CN/'
}
class BreadView extends Component {
  state = {
    tabview: null, // 标签
    dict: localStorage.getItem('lang') !== 'en-US' ? mzhCN : menUS,
  }
  refreshTabview = () => {
    const { tabview } = this.state
    window.GLOB.CacheMap = new Map()
    MKEmitter.emit('reloadMenuView', tabview.MenuID)
  }
  selectcomponent = (view) => {
    // 根据tab页中菜单信息,选择所需的组件
    if (view.type === 'Home') {
      return (<Home MenuNo={view.MenuNo} MenuID={view.MenuID} MenuName={view.MenuName} key={view.MenuID}/>)
    } else if (view.type === 'CommonTable' || view.type === 'ManageTable') {
      return (<CommonTable MenuNo={view.MenuNo} MenuID={view.MenuID} MenuName={view.MenuName} key={view.MenuID} param={view.param}/>)
    } else if (view.type === 'CustomPage') {
      return (<CustomPage MenuNo={view.MenuNo} MenuID={view.MenuID} MenuName={view.MenuName} key={view.MenuID} param={view.param}/>)
    } else if (view.type === 'TreePage') {
      return (<TreePage MenuNo={view.MenuNo} MenuID={view.MenuID} MenuName={view.MenuName} key={view.MenuID} param={view.param}/>)
    } else if (view.type === 'CalendarPage') {
      return (<CalendarPage MenuNo={view.MenuNo} MenuID={view.MenuID} MenuName={view.MenuName} key={view.MenuID} param={view.param}/>)
    } else if (view.type === 'RolePermission') {
      return (<RoleManage MenuNo={view.MenuNo} MenuID={view.MenuID} MenuName={view.MenuName} key={view.MenuID}/>)
    } else if (view.type === 'FormTab') {
      return (<FormTab MenuNo={view.MenuNo} MenuID={view.MenuID} MenuName={view.MenuName} key={view.MenuID} param={view.param}/>)
    } else if (view.type === 'iframe') {
      return (<Iframe key={view.MenuID} MenuID={view.MenuID} MenuNo={view.MenuNo} title={view.MenuName} MenuName={view.MenuName} url={service + view.LinkUrl}/>)
    } else {
      return (<NotFount key={view.MenuID} />)
    }
  }
  UNSAFE_componentWillMount () {
    if (!sessionStorage.getItem('lang') || sessionStorage.getItem('lang') === 'zh-CN') {
      moment.locale('zh-cn')
    } else {
      moment.locale('en')
    }
    let home = {
      MenuID: 'home_page_id',
      MenuName: this.state.dict['main.homepage'],
      selected: true,
      type: 'Home'
    }
    this.setState({tabview: home})
  }
  gotoHome = () => {
    let home = {
      MenuID: 'home_page_id',
      MenuName: this.state.dict['main.homepage'],
      selected: true,
      type: 'Home'
    }
    this.setState({tabview: home})
  }
  UNSAFE_componentWillReceiveProps (nextProps) {
    if (nextProps.tabviews && !is(fromJS(this.state.tabviews), fromJS(nextProps.tabviews))) {
      // 保存修改标签集
      this.setState({
        tabview: nextProps.tabviews[nextProps.tabviews.length - 1]
      })
      let node = document.getElementById('root').parentNode.parentNode
      if (node) {
        node.scrollTop = 0
      }
    }
  }
  /**
   * @description 组件销毁,清除state更新
   */
  componentWillUnmount () {
    this.setState = () => {
      return
    }
  }
  render () {
    const { tabview } = this.state
    return (
      <section id="mk-breadview-wrap" className="mk-breadview-wrap">
        {tabview ? <Breadcrumb separator="">
          <Breadcrumb.Item>
            <Icon type="home" onClick={this.gotoHome} />
          </Breadcrumb.Item>
          {tabview.ParentNames && tabview.ParentNames[0] ?
            <Breadcrumb.Item>{tabview.ParentNames[0]}</Breadcrumb.Item> : null}
          {tabview.ParentNames && tabview.ParentNames[0] ?
              <Breadcrumb.Separator children={<Icon type="right" />} /> : null}
          {tabview.ParentNames && tabview.ParentNames[1] ?
            <Breadcrumb.Item>{tabview.ParentNames[1]}</Breadcrumb.Item> : null}
          {tabview.ParentNames && tabview.ParentNames[1] ?
              <Breadcrumb.Separator children={<Icon type="right" />} /> : null}
          <Breadcrumb.Item><Icon type="redo" onClick={this.refreshTabview}/>{tabview.MenuName}</Breadcrumb.Item>
        </Breadcrumb> : null}
        {tabview ? this.selectcomponent(tabview) : null}
        <BackTop>
          <div className="ant-back-top">
            <div className="ant-back-top-content">
              <div className="ant-back-top-icon"></div>
            </div>
          </div>
        </BackTop>
      </section>
    )
  }
}
const mapStateToProps = (state) => {
  return {
    tabviews: state.tabviews
  }
}
const mapDispatchToProps = () => {
  return {}
}
export default connect(mapStateToProps, mapDispatchToProps)(BreadView)
src/components/breadview/index.scss
New file
@@ -0,0 +1,73 @@
.mk-breadview-wrap {
  min-height: 100%;
  padding-top: 48px;
  width: 100%;
  box-sizing: content-box;
  >.ant-breadcrumb {
    padding: 10px;
    .anticon-home {
      cursor: pointer;
      margin-right: 10px;
    }
    .anticon-redo {
      cursor: pointer;
      margin-right: 5px;
    }
    .ant-breadcrumb-link + .ant-breadcrumb-separator {
      display: none;
    }
  }
  >.commontable, >.calendar-page {
    padding-left: 15px;
    padding-right: 15px;
  }
  >.commontable, >.calendar-page {
    > .top-search {
      padding-left: 0;
      padding-right: 0;
      margin: 0 24px;
    }
  }
  iframe {
    width: 100%;
    height: calc(100vh - 115px);
    overflow-y: scroll;
    border: 0;
    margin-top: 16px;
  }
  .main-copy {
    position: fixed;
    z-index: 20;
    bottom: 65px;
    right: 30px;
    width: 40px;
    height: 40px;
    i {
      font-size: 18px;
    }
  }
  .main-copy.ifr-copy {
    bottom: 65px;
    right: 40px;
    width: 30px;
    height: 32px;
    border: 2px solid #687991;
    opacity: 0.6;
    i {
      font-size: 14px;
      color: #687991;
    }
  }
  .main-copy.ifr-copy:hover {
    opacity: 1;
  }
  .ant-back-top {
    bottom: 20px;
    right: 30px;
  }
}
.ant-message {
  top: 50px;
  z-index: 1080;
}
src/components/header/index.jsx
@@ -48,7 +48,8 @@
    thdMenuList: [],
    oriVersion: '',
    newVersion: '',
    debug: sessionStorage.getItem('debug') === 'true'
    debug: sessionStorage.getItem('debug') === 'true',
    navBar: window.GLOB.navBar
  }
  handleCollapse = () => {
@@ -126,10 +127,10 @@
  changeMenu (value) {
    // 主菜单切换
    if (value.PageParam.OpenType === 'menu') {
    if (value.OpenType === 'outpage' && value.linkUrl) {
      window.open(value.linkUrl)
    } else if (value.OpenType === 'menu') {
      this.props.modifyMainMenu(value)
    } else if (value.PageParam.OpenType === 'outpage') {
      window.open(value.PageParam.linkUrl)
    }
  }
@@ -227,14 +228,19 @@
        let tabs = fromJS(this.props.tabviews).toJS()
        let menu = fromJS(response[1]).toJS()
        tabs = tabs.map(tab => {
          tab.selected = false
          return tab
        })
        if (this.state.navBar === 'topmenu') {
          menu.selected = true
          this.props.modifyTabview([menu])
        } else {
          tabs = tabs.map(tab => {
            tab.selected = false
            return tab
          })
        menu.selected = true
        tabs.push(menu)
        this.props.modifyTabview(tabs)
          menu.selected = true
          tabs.push(menu)
          this.props.modifyTabview(tabs)
        }
      }
    })
  }
@@ -247,14 +253,18 @@
      let fstItem = {
        MenuID: fst.MenuID,
        MenuName: fst.MenuName,
        PageParam: {OpenType: 'menu', linkUrl: ''},
        OpenType: 'menu',
        children: []
      }
      if (fst.PageParam) {
        try {
          fstItem.PageParam = JSON.parse(fst.PageParam)
        } catch (e) {
          fstItem.PageParam = {OpenType: 'menu', linkUrl: ''}
          fstItem.PageParam = null
        }
        if (fstItem.PageParam && fstItem.PageParam.OpenType === 'outpage' && fstItem.PageParam.linkUrl) {
          fstItem.OpenType = 'outpage'
          fstItem.linkUrl = fstItem.PageParam.linkUrl
        }
      }
@@ -287,6 +297,7 @@
            debug: sessionStorage.getItem('debug'),
            role_id: sessionStorage.getItem('role_id'),
            mainlogo: window.GLOB.mainlogo,
            navBar: window.GLOB.navBar || '',
            mstyle: window.GLOB.style
          }
@@ -297,6 +308,7 @@
                ParentId: snd.MenuID,
                MenuID: trd.MenuID,
                MenuName: trd.MenuName,
                ParentNames: [fst.MenuName, snd.MenuName],
                MenuNo: trd.MenuNo,
                EasyCode: trd.EasyCode,
                type: 'CommonTable',            // 默认值为常用表
@@ -541,15 +553,18 @@
  changeVerMenu(menu, type) {
    if (type === 'first') {
      if (menu.PageParam.OpenType === 'menu') {
      if (menu.OpenType === 'outpage' && menu.linkUrl) {
        window.open(menu.linkUrl)
      } else if (menu.OpenType === 'menu') {
      } else if (menu.PageParam.OpenType === 'outpage') {
        window.open(menu.PageParam.linkUrl)
      }
    } else {
      if (menu.OpenType === 'newpage' || menu.OpenType === 'NewPage') {
      if (menu.OpenType === 'newpage' || menu.OpenType === 'NewPage') { // NewPage为打开外部页面地址,newpage为打开系统菜单
        window.open(menu.src)
      } else if (menu.OpenType === 'blank') {
        menu.selected = true
        this.props.modifyTabview([menu])
      } else if (this.state.navBar === 'topmenu') {
        menu.selected = true
        this.props.modifyTabview([menu])
      } else {
@@ -578,7 +593,7 @@
  render () {
    const { mainMenu, collapse } = this.props
    const { thdMenuList, searchkey, oriVersion, newVersion, debug, menulist } = this.state
    const { thdMenuList, searchkey, oriVersion, newVersion, debug, menulist, navBar } = this.state
    const menu = (
      <Menu className="header-dropdown">
@@ -602,12 +617,12 @@
    return (
      <header className="header-container ant-menu-dark" id="main-header-container">
        <div className={'header-logo ' + (collapse ? 'collapse' : '')}><img src={this.state.logourl} alt=""/></div>
        <div className={'header-collapse ' + (collapse ? 'collapse' : '')}>
          {menulist && menulist.length ? <Icon type={collapse ? 'menu-unfold' : 'menu-fold'} onClick={this.handleCollapse}/> : null}
        <div className={'header-logo ' + (collapse && navBar !== 'topmenu' ? 'collapse' : '')}><img src={this.state.logourl} alt=""/></div>
        <div className={'header-collapse ' + (collapse && navBar !== 'topmenu' ? 'collapse' : '')}>
          {navBar !== 'topmenu' ? <Icon type={collapse ? 'menu-unfold' : 'menu-fold'} onClick={this.handleCollapse}/> : null}
        </div>
        {/* 正常菜单 */}
        {menulist ?
        {navBar !== 'topmenu' && menulist ?
          <ul className="header-menu">{
            menulist.map(item => {
              return (
@@ -619,7 +634,7 @@
          </ul> : null
        }
        {/* 正常菜单 */}
        {/* {menulist ?
        {navBar === 'topmenu' && menulist ?
          <ul className="header-menu vertical-menu">{
            menulist.map(item => {
              if (item.children && item.children.length > 0) {
@@ -661,7 +676,7 @@
              }
            })}
          </ul> : null
        } */}
        }
        {/* 头像、用户名 */}
        <Dropdown className="header-setting" overlay={menu}>
          <div>
src/components/tabview/index.jsx
@@ -35,7 +35,7 @@
  service = window.GLOB.location + '/' + window.GLOB.service + 'zh-CN/'
}
class Header extends Component {
class TabViews extends Component {
  static propTpyes = {
    collapse: PropTypes.bool,
    tabviews: PropTypes.array // 标签页数组
@@ -269,4 +269,4 @@
  }
}
export default connect(mapStateToProps, mapDispatchToProps)(Header)
export default connect(mapStateToProps, mapDispatchToProps)(TabViews)
src/index.js
@@ -154,6 +154,7 @@
        GLOB.webSite = _systemMsg.webSite
        GLOB.style = _systemMsg.style
        GLOB.showline = _systemMsg.showline || ''
        GLOB.navBar = _systemMsg.navBar || 'sidemenu'
        if (GLOB.favicon) {
          let link = document.querySelector("link[rel*='icon']") || document.createElement('link')
src/router/index.js
@@ -58,6 +58,9 @@
          if (_param.mainlogo) {
            window.GLOB.mainlogo = _param.mainlogo
          }
          if (_param.navBar) {
            window.GLOB.navBar = _param.navBar
          }
          if (_param.mstyle && styles[_param.mstyle]) {
            document.body.className = styles[_param.mstyle]
          }
src/tabviews/zshare/actionList/tabbutton/index.jsx
@@ -134,18 +134,22 @@
      return tab.MenuID !== newtab.MenuID
    })
    if (tabviews.length !== tabs.length) {
      this.props.modifyTabview(fromJS(tabs).toJS())
    }
    this.setState({}, () => {
      if (MenuID) {
        tabs.splice(index + 1, 0, newtab)
      } else {
        tabs.push(newtab)
    if (window.GLOB.navBar === 'topmenu') {
      this.props.modifyTabview([newtab])
    } else {
      if (tabviews.length !== tabs.length) {
        this.props.modifyTabview(fromJS(tabs).toJS())
      }
      this.props.modifyTabview(tabs)
    })
      this.setState({}, () => {
        if (MenuID) {
          tabs.splice(index + 1, 0, newtab)
        } else {
          tabs.push(newtab)
        }
        this.props.modifyTabview(tabs)
      })
    }
    MKEmitter.emit('openNewTab')
    if (window.GLOB.systemType === 'production') {
src/templates/sharecomponent/actioncomponent/actionform/index.jsx
@@ -665,7 +665,7 @@
                  }
                ]
              })(
                <Cascader options={item.options || []} placeholder="" />
                <Cascader allowClear options={item.options || []} placeholder="" />
              )}
            </Form.Item>
          </Col>
src/views/login/index.jsx
@@ -291,7 +291,8 @@
              doclogo: res.doclogo || '',
              style: res.CSS || '',
              showline: res.split_line_show || 'true',
              webSite: res.WebSite || ''
              webSite: res.WebSite || '',
              navBar: res.NavBar !== 'topmenu' ? 'sidemenu' : 'topmenu'
            }
            sessionStorage.setItem('home_background', res.index_background_color)
@@ -344,6 +345,7 @@
            window.GLOB.mainlogo = systemMsg.mainlogo
            window.GLOB.style = systemMsg.style
            window.GLOB.navBar = systemMsg.navBar
        
            if (window.GLOB.style && styles[window.GLOB.style]) {
              document.body.className = styles[window.GLOB.style] + ' ' + (res.split_line_show === 'false' ? 'hidden-split-line' : '')
src/views/main/index.jsx
@@ -11,16 +11,23 @@
import './index.scss'
const Tabview = asyncComponent(() => import('@/components/tabview'))
const Breadview = asyncComponent(() => import('@/components/breadview'))
const _locale = localStorage.getItem('lang') !== 'en-US' ? zhCN : enUS
class Main extends Component {
  state = {
    navBar: window.GLOB.navBar
  }
  render () {
    const { navBar } = this.state
    return (
      <div className="mk-main-view">
        <ConfigProvider locale={_locale}>
          <Header key="header"/>
          <Sidemenu key="sidemenu"/>
          <Tabview key="tabview"/>
          {navBar !== 'topmenu' ? <Sidemenu key="sidemenu"/> : null}
          {navBar !== 'topmenu' ? <Tabview key="tabview"/> : null}
          {navBar === 'topmenu' ? <Breadview key="breadview"/> : null}
          <QueryLog />
        </ConfigProvider>
      </div>
src/views/menudesign/index.jsx
@@ -508,7 +508,7 @@
        EasyCode: _config.easyCode || '',
        Template: 'CustomPage',
        MenuName: _config.MenuName || '',
        PageParam: JSON.stringify({Template: 'CustomPage', OpenType: 'newtab'}),
        PageParam: JSON.stringify({Template: 'CustomPage', OpenType: _config.OpenType || 'newtab'}),
        LongParam: window.btoa(window.encodeURIComponent(JSON.stringify(_config))),
        LText: '',
        LTexttb: ''
src/views/menudesign/menuform/index.jsx
@@ -143,6 +143,8 @@
      this.props.updateConfig({...config, cacheUseful: value})
    } else if (key === 'timeUnit') {
      this.props.updateConfig({...config, timeUnit: value})
    } else if (key === 'OpenType') {
      this.props.updateConfig({...config, OpenType: value})
    }
  }
@@ -255,6 +257,24 @@
            </Form.Item>
          </Col>
          <Col span={24}>
            <Form.Item label="打开方式">
              {getFieldDecorator('OpenType', {
                initialValue: config.OpenType || 'newtab',
                rules: [
                  {
                    required: true,
                    message: dict['form.required.select'] + dict['model.openway'] + '!'
                  }
                ]
              })(
                <Select onChange={(value) => {this.selectChange('OpenType', value)}}>
                  <Select.Option value="newtab">标签页</Select.Option>
                  <Select.Option value="newpage">新页面</Select.Option>
                </Select>
              )}
            </Form.Item>
          </Col>
          <Col span={24}>
            <Form.Item label={
              <Tooltip placement="topLeft" title="对于不经常性变动的信息,缓存数据有助于提高查询效率。">
                <Icon type="question-circle" />