记一次公司使用vue导出Excel表格,多层数据嵌套处理,方便后面自己查阅资料

一、安装相关依赖
npm install  file-saver xlsx  -S
npm install  script-loader  -D
二、引用文件

在src文件目录下新建vendor文件夹(可自定义文件名),并在文件中引用Blob.jsExport2Excel.js文件

可在github进行下载

vue3 实现邮件导出eml格式 vue如何导出excel_数据


并在项目目录下的build下的 webpack.base/conf.js这个webpack的配置文件中的resolve的alias中加入

'vendor': path.resolve(__dirname, '@/vendor') //可自行根据文件目录引用
// 例如:
resolve: {
    extensions: ['.js', '.vue', '.json'],
    alias: {
      'vue$': 'vue/dist/vue.esm.js',
      '@': resolve('src'),
      'vendor': path.resolve(__dirname, '@/vendor') //可自行根据文件目录引用
    }
  }
三、在项目中的使用
1、个别数据嵌套简单处理方式,在formatJson 中进行循环处理,并返回获取到的对应数据

例如:客户名称、录入人员、所属组织对有单层数据嵌套处理
handelDerive 事件中引用vendor中的Export2Excel文件
tHeader: 为表格头部信息
filterVal : 与头部信息对应的数据字段

methods:{
    // 如果想再当前页导出所有数据,可给获取接口添加最大页数
    getAll (page, pageSize = 60000) {
      this.loadingList = true
      return new Promise((resolve, reject) => {
      http.get(`/api/restful/query/__::__items.customer__items.input_user__items.organization__items.application_items.item/model.runtime.application.Application/key_search?outerjoin=model.customer.customer.Customer&columns=model.runtime.application.Application.number,model.customer.customer.Customer.name&key_word=${this.condition.key_word}&between_filter=model.runtime.application.Application.input_time__${moment(this.condition.start_time1).format('YYYY-MM-DD 00:00:00')}__${moment(this.condition.start_time2).format('YYYY-MM-DD 23:59:59')}&per_page=${pageSize}`, {
          page: page || 1
        }).then(res => {
          console.log('我先执行')
          resolve(res.items)
          this.loadingList = false
        }).catch((res) => {
          reject(res)
          this.loadingList = false
        })
      })
    },
    //导出Excel   
    handelDerive () {
      this.getAll().then(res => {
        require.ensure([], () => {
          const { exportJsonToExcel } = require('../../vendor/Export2Excel')
          const tHeader = ['申请单编号', '客户名称', '检测项目', '录入时间', '完成时间', '录入人员', '所属组织', '申请单状态']
          const filterVal = ['number', 'customer.name', 'application_items', 'input_time', 'estimated_completion_time', 'input_user.name', 'organization.name', 'state']
          const list = res // 把data里的tableData存到list
          console.log('我后执行')
          const data = this.formatJson(filterVal, list)
          exportJsonToExcel(tHeader, data, '申请单查询')  // 申请单查询是导出表格名
        })
      })
    },
    formatJson (filterVal, jsonData) {
      return jsonData.map(v => filterVal.map(j => {
        if (!j.split('.')[1]) {
          if (j === 'application_items') {
            return v[j].map(m => m.item && m.item.common_name).join('/')
          } else {
            return v[j.split('.')[0]]
          }
        } else if (v[j.split('.')[0]]) {
          return v[j.split('.')[0]][j.split('.')[1]]
        } else {
          return 0
        }
      }))
    }
}
2、对多层数据进行处理方式:
methods:{
    // 如果想再当前页导出所有数据,可给获取接口添加最大页数
    getSampleAll (page, pageSize = 60000) {
      this.loadingList = true
      return new Promise((resolve, reject) => {
        http.get(`/api/restful/query/__items.application.customer__items.application.application_items.item__items.application.input_user__items.application.organization/model.runtime.sample.Sample/key_search?columns=model.runtime.sample.Sample.model,model.runtime.sample.Sample.producer,model.runtime.sample.Sample.description&key_word=${this.condition.sample}&between_filter=model.runtime.application.Application.input_time__${moment(this.condition.start_time1).format('YYYY-MM-DD 00:00:00')}__${moment(this.condition.start_time2).format('YYYY-MM-DD 23:59:59')}`, {
          page: page || 1
        }).then(res => {
          console.log('我先执行')
          resolve(res.items)
          this.loadingList = false
        }).catch((res) => {
          reject(res)
          this.loadingList = false
        })
      })
    },
    // 导出Excel
    handelSampleDerive () {
      this.getSampleAll().then(res => {
        require.ensure([], () => {
          const { exportJsonToExcel } = require('../../vendor/Export2Excel')
          const tHeader = ['申请单编号', '客户名称', '检测项目', '录入时间', '完成时间', '录入人员', '所属组织', '申请单状态']
          const filterVal = ['application.number', 'application.customer.name', 'application.application_items', 'application.input_time', 'application.estimated_completion_time', 'application.input_user.name', 'application.organization.name', 'application.state']
          const list = res // 把data里的tableData存到list
          const data = this.formatSampleJson(filterVal, list)
          exportJsonToExcel(tHeader, data, '申请单查询')  // 申请单查询是导出表格名
        })
      })
    },
    // 当前数据嵌套几层就循环查找几层
    formatSampleJson (filterVal, jsonData) {
      return jsonData.map(v => filterVal.map(j => {
        if (!j.split('.')[2]) {
          if (j.split('.')[1] === 'application_items') {
            const val = v[j.split('.')[0]][j.split('.')[1]]
            return val.map(m => m.item && m.item.common_name).join('/')
          } else {
            return v[j.split('.')[0]][j.split('.')[1]]
          }
        } else if (v[j.split('.')[0]][j.split('.')[1]]) {
          return v[j.split('.')[0]][j.split('.')[1]][j.split('.')[2]]
        } else {
          return 0
        }
      }))
    }
}
四、特殊情况处理:

如若项目要求在导出表格顶部加入固定信息,可采取下面方式
Export2Excel.js文件中原有方法exportJsonToExcel下方可自定义添加导出方法
此处以exportJsonToExcelnumber 方法为例

export function exportJsonToExcelnumber(th, jsonData, defaultTitle) {
    /* original data */
    var data = jsonData;
    data.unshift(th);
    var ws_name = "SheetJS";
    var datas=[[`此处为顶部自定义内容`],
    [`此处为顶部自定义内容`,`此处为顶部自定义内容`]]
    data.map(res=>{
        datas.push(res)
    })
    var wb = new Workbook(), ws = sheet_from_array_of_arrays(datas);
    /* add worksheet to workbook */
    wb.SheetNames.push(ws_name);
    wb.Sheets[ws_name] = ws;
    var wbout = XLSX.write(wb, {bookType: 'xlsx', bookSST: false, type: 'binary'});
    var title = defaultTitle || '列表'
    saveAs(new Blob([s2ab(wbout)], {type: "application/octet-stream"}), title + ".xlsx")
}

在导出方法事件中使用自定义导出exportJsonToExcelnumber方法,如:

// 导出的方法
    handelDerive () {
      this.getAll().then(res => {
        require.ensure([], () => {
          const { exportJsonToExcelnumber } = require('../../vendor/Export2Excel')
          const tHeader = ['机构名称', '报告编号', '报告签发时间', '报告签名年份', '编号是否有效']
          const filterVal = ['userName', 'number', 'dateTime', 'dataYear', '']
          res.map(res => {
            let dateTime = res.sign_date.substring(0, 10)
            let dataYear = res.sign_date.substring(0, 4)
            let userName = res.application.tenant.name
            res.dateTime = dateTime
            res.dataYear = dataYear
            res.userName = userName
          })
          const list = res // 把data里的tableData存到list
          const data = this.formatJson(filterVal, list)
          exportJsonToExcelnumber(tHeader, data, '报告查询')
        })
      })
    }

顶部自定义内容效果如下,导出样式可自行百度调试

vue3 实现邮件导出eml格式 vue如何导出excel_数据_02

注:为了避免导出事件触发后,导出表格为空,此处我利用Promise处理请求数据,详情可参考请求所有数据接口代码处

主要是为了记录自己在导出表格中遇到的坑(多层数据嵌套),同时分享小伙伴共同学习,不足之处多多指教,欢迎大家留言讨论