让后台查询+表格这种页面更加快速和简便

简介: 让后台查询+表格这种页面更加快速和简便

让后台查询+表格这种页面更加快速和简便


做后台项目,很多页面类似下面

这种页面有时候逻辑也是有点麻烦,要是每个页面一遍遍想,就有点尬,所以想了个偷懒的法子,将通用逻辑抽离出来,需要这种页面的时候,只需要适当的配置即可,不用再关心相同的逻辑。

对于表单,需要的方法有:设置表单数据、拿到表单的参数、设置表单项其他的属性等。

对于ajax请求回来的数据,需要的方法:拿到请求需要的参数,此参数分为两块,一个是表单提供的,一个分页和排序这种的,第一次的请求可以保留参数,为重置表单数据或者分页排序值做准备。

主要实现的通用功能:请求数据、查询逻辑、重置逻辑、导出逻辑。

enhanced-tableenhanced-form

query作为mixins的代码

github地址,运行node server.js还有yarn install;yarn dev,之后打开http://localhost:8080/single-query即可看到效果

<script>
/* 此页面最适合 上面是简单的表单,下面是表格,主要是查询 翻页 重置 导出功能
1. mixins写入此文件,import Query from 'xx';mixins:[Query]
2. formConfig colConfigs ajaxApis均需要特定配置,其他的根据情况吧
3. init里面一般是当前页面具体的初始化,一般需要重写
4. computed:tableData一般是需要重新写的
5. 放好html,基本可以玩起来了
 */
import EnhancedTable from '@/components/EnhancedTable'
import EnhancedForm from '@/components/EnhancedForm'
export default {
  components: { EnhancedTable, EnhancedForm },
  data () {
    const formConfig = {
      year: { label: '年份', category: 'date-picker', default: (new Date()).getFullYear() + '', type: 'year', format: 'yyyy', valueFormat: 'yyyy' },
      term: { label: '季度', category: 'select', options: [{ value: '春', label: '春' }, { value: '夏', label: '夏' }, { value: '秋', label: '秋' }, { value: '冬', label: '冬' }] },
      area: { label: '大区', category: 'select', filterable: true, default: '', options: null },
      name: { label: '姓名', category: 'input' },
      code: { label: '编号', category: 'input' }
    }
    const formAttr = {
      // 行内显示
      inline: true,
      // 每个label宽
      labelWidth: '100px',
      // label右对齐
      labelPosition: 'right'
    }
    const colConfigs = [
      { prop: 'orderNumber', label: '序号', sortable: false, align: 'center' },
      { slot: 'projectName', prop: 'projectName', label: '教研组', sortable: false, align: 'center' },
      { prop: 'teacherCount', label: '教师数量', sortable: false, align: 'center' },
      { prop: 'lessonCount', label: '总课次', sortable: false, align: 'center' },
      { prop: 'uploadPercent', label: '上传率', sortable: false, align: 'center' },
      { prop: 'passPercent', label: '合格率', sortable: false, align: 'center' }
    ]
    const ajaxApis = {
      query: 'AjaxQuery',
      export: 'AjaxExport'
    }
    return {
      // 查询表单项的配置
      formConfig,
      // 整个表单的统一配置
      formAttr,
      // 表格每列的配置
      colConfigs,
      // 这个是 请求的方法,不同页面的请求方法名肯定是不一样的 需要配置
      ajaxApis,
      // 表格的加载图标
      isShowTableLoading: false,
      // 表格请求的原始数据
      tableDataNative: [],
      // 有数据就意味着可能分页
      otherParams: {
        pageIndex: 0,
        pageSize: 10,
        isAsc: '',
        sortBy: ''
      },
      // 数据总长度,基本只给分页组件用的
      dataLength: 0,
      // 为了方便重置,将首次请求表格数据的参数保存
      initialParams: null
    }
  },
  computed: {
    // 处理之后的数据
    tableData () {
      return this.tableDataNative
    }
  },
  mounted () {
    this.init()
  },
    methods: {
    // 页面加载执行的方法
    async init () {
      // 这个有异步操作,需要用await
      await this.setAreaOptions()
      this.setInitialParams()
      this.getTableData()
    },
    setInitialParams () {
      let formParams = this.getFormData()
      // 设置首次查询的参数,这里注意对象是引用,必须深度复制下
      this.initialParams = { formParams: { ...formParams }, otherParams: { ...this.otherParams } }
    },
    async setAreaOptions () {
      let res = await this.$api.AjaxGetAreas()
      let options = res.data.data
      this.setSingleFormItem({ prop: 'area', attr: 'options', value: options })
      this.setSingleFormItem({ prop: 'area', attr: 'default', value: options[1].value })
    },
    clickSearchBtn () {
      // 重置页数的相关参数,这个是,比如你在点击第二页之后,pageIndex=2,但是当点击查询的时候,需要重新重置
      this.otherParams = this.initialParams.otherParams
      this.getTableData()
    },
    clickExportBtn () {
      // 导出的参数和查询的参数基本一样,但是数据不分页
      let params = { ...this.getAjaxQueryParams() }
      params.pageSize = 0
      this.$api[this.ajaxApis.export](params)
    },
    clickResetBtn () {
      // 重置表单
      this.setFormData(this.initialParams.formParams)
      // 重置页数的相关参数
      this.otherParams = this.initialParams.otherParams
      // 查询
      this.getTableData()
    },
    // ajax请求表格数据,并赋值,因为后端的数据很多时候前端需要处理下,在computed那边加一层过滤
    async ajaxQuery (params) {
      // 显示表单加载
      this.isShowTableLoading = true
      let res = await this.$api[this.ajaxApis.query](params)
      this.isShowTableLoading = false
      this.tableDataNative = res.data.data
      this.dataLength = res.data.dataCount
    },
    // 将表单元素设置成特定的值,params  = {year:2019,...}
    setFormData (params, refForm = 'queryForm') {
      // 表单
      for (let key in params) {
        this.$refs[refForm].$data.form.props[key] = params[key]
      }
    },
    // 得到表单各项的值
    getFormData (refForm = 'queryForm') {
      return this.$refs[refForm].$data.form.props
    },
    // 设置单个表单元素的属性,除了默认值,常用的是options
    setSingleFormItem ({ prop, attr, value, formConfig = 'formConfig', refForm = 'queryForm' }) {
      this[formConfig][prop][attr] = value
      // 默认值的话 需要变动form的属性
      if (attr === 'default') {
        this.$refs[refForm].$data.form.props[prop] = value
      }
    },
    getTableData () {
      let params = this.getAjaxQueryParams()
      this.ajaxQuery(params)
    },
    // 请求的参数 包括表单和页数相关的数据
    getAjaxQueryParams () {
      let formParams = this.getFormData()
      let params = { ...this.otherParams, ...formParams }
      return params
    },
    // 改变页数
    changeTablePage (page) {
      this.otherParams.pageIndex = page
      this.getTableData()
    }
  }
}
</script>

引用query的页面

<template lang="pug">
section
  //- 表单区域
  enhanced-form.app-query-form(ref="queryForm" :form-config="formConfig" :form-attr="formAttr")
    template(v-slot:districtName="{config,form}")
      el-form-item(:label="config.label" prop="districtName")
        el-select(v-model="form.props.districtName" v-bind="config" @change="changeDistrict(form.props.districtName)")
          el-option(v-for="item in config.options" :key="item.value" :value="item.value" :label="item.label" )
    template(#btns)
      el-form-item.app-btns-box
        el-button.btn(type='primary', @click='clickSearchBtn') 查询
        el-button.btn(type='primary', @click='clickResetBtn', plain='') 重置
        el-button.btn(type='warning',plain='', @click='clickExportBtn') 导出
  //- 表格区域
  enhanced-table(:is-load='isShowTableLoading', :table-data='tableData', :col-configs='colConfigs')
  //- 分页 没有数据的时候不显示
  .pagination-box(v-if="tableData.length")
    el-pagination(@current-change='changeTablePage', :current-page.sync='otherParams.pageIndex', :page-size='otherParams.pageSize', layout='prev, pager, next, jumper', :total='dataLength')
</template>
<script>
import Query from '@/mixins/Query'
export default {
  mixins: [Query],
  data () {
    const formConfig = {
      year: { label: '年份', category: 'date-picker', default: (new Date()).getFullYear() + '', type: 'year', format: 'yyyy', valueFormat: 'yyyy' },
      term: { label: '季度', category: 'select', options: [{ value: '春', label: '春' }, { value: '夏', label: '夏' }, { value: '秋', label: '秋' }, { value: '冬', label: '冬' }] },
      area: { label: '大区', category: 'select', filterable: true, default: '', options: null },
      name: { label: '姓名', category: 'input' },
      code: { label: '编号', category: 'input' }
    }
    const colConfigs = [
      { prop: 'orderNumber', label: '序号', sortable: false, align: 'center' },
      { slot: 'projectName', prop: 'projectName', label: '教研组', sortable: false, align: 'center' },
      { prop: 'teacherCount', label: '教师数量', sortable: false, align: 'center' },
      { prop: 'lessonCount', label: '总课次', sortable: false, align: 'center' },
      { prop: 'uploadPercent', label: '上传率', sortable: false, align: 'center' },
      { prop: 'passPercent', label: '合格率', sortable: false, align: 'center' }
    ]
    const ajaxApis = {
      query: 'AjaxQuery',
      export: 'AjaxExport'
    }
    return {
      // 查询表单项的配置
      formConfig,
      // 表格每列的配置
      colConfigs,
      // 这个是 请求的方法,不同页面的请求方法名肯定是不一样的 需要配置
      ajaxApis
    }
  },
  computed: {
    // 处理之后的数据
    tableData () {
      return this.tableDataNative
    }
  },
  methods: {
    // 页面加载执行的方法
    async init () {
      // 这个有异步操作,需要用await
      await this.setAreaOptions()
      this.setInitialParams()
      this.getTableData()
    },
    async setAreaOptions () {
      let res = await this.$api.AjaxGetAreas()
      let options = res.data.data
      this.setSingleFormItem({ prop: 'area', attr: 'options', value: options })
      this.setSingleFormItem({ prop: 'area', attr: 'default', value: options[1].value })
    }
  }
}
</script>
<style>
.el-table{
  border:1px solid #e8e8e8;
  width: 90%;
  margin: auto;
}
.pagination-box{
  margin-top: 20px;
  text-align: center;
}
</style>

不足

水平有限,即便这样还是有点麻烦,嗯,继续加油

目录
相关文章
|
5月前
|
小程序 API 数据库
【微信小程序-原生开发】实用教程09 - 可滚动选项,动态列表-步骤条(含事件传参),动态详情(含微信云查询单条数据 doc)
【微信小程序-原生开发】实用教程09 - 可滚动选项,动态列表-步骤条(含事件传参),动态详情(含微信云查询单条数据 doc)
86 0
|
4月前
|
SQL 开发框架 前端开发
在Winform系统开发中,对表格列表中的内容进行分组展示
在Winform系统开发中,对表格列表中的内容进行分组展示
|
5月前
|
开发框架 JavaScript 前端开发
在Vue前端界面中,几种数据表格的展示处理,以及表格编辑录入处理操作。
在Vue前端界面中,几种数据表格的展示处理,以及表格编辑录入处理操作。
|
5月前
|
前端开发 JavaScript 数据库
分页,快捷链接表单,分页表单,常用软件开发之分页,快捷链接分页表单添加显示,可以做的分页统计,一个简单的添加页面,数据条理清晰呈现如何设计,如何修改成自己想要的,要会编写接口文档,一边写接口
分页,快捷链接表单,分页表单,常用软件开发之分页,快捷链接分页表单添加显示,可以做的分页统计,一个简单的添加页面,数据条理清晰呈现如何设计,如何修改成自己想要的,要会编写接口文档,一边写接口
|
小程序 前端开发
【易售小程序项目】项目介绍、小程序页面展示与系列文章集合
【易售小程序项目】项目介绍、小程序页面展示与系列文章集合
126 2
|
SQL Java 关系型数据库
从系统报表页面导出20w条数据到本地只用了4秒,我是如何做到的
最近有个学弟找到我,跟我描述了以下场景: 他们公司内部管理系统上有很多报表,报表数据都有分页显示,浏览的时候速度还可以。但是每个报表在导出时间窗口稍微大一点的数据时,就异常缓慢,有时候多人一起导出时还会出现堆溢出。 他知道是因为数据全部加载到jvm内存导致的堆溢出。所以只能对时间窗口做了限制。以避免因导出过数据过大而引起的堆溢出。最终拍脑袋定下个限制为:导出的数据时间窗口不能超过1个月。
|
前端开发 JavaScript 数据可视化
数据可视化大屏人员停留系统的开发实录(默认加载条件筛选、单击加载、自动刷新加载、异步加载数据)
数据可视化大屏人员停留系统的开发实录(默认加载条件筛选、单击加载、自动刷新加载、异步加载数据)
142 0
|
人工智能 前端开发
「前端技巧总结」多个页面的操作聚合到某个页面的实现方案
用技术实现梦想,用梦想打开前端技术之门。分享我在日常开发中总结的前端技巧,今天是多个页面的操作聚合到某个页面的实现方案。
285 0
|
前端开发
前端工作总结108-修改新增按钮显示逻辑
前端工作总结108-修改新增按钮显示逻辑
108 0
前端工作总结108-修改新增按钮显示逻辑
(简易)测试数据构造平台: 17 (首页临时美化)
(简易)测试数据构造平台: 17 (首页临时美化)
(简易)测试数据构造平台: 17 (首页临时美化)
下一篇
DataWorks