nodej实现Excel解析上传、导出

        <el-upload
          ref="upload"
          :limit="limit"
          :auto-upload="false"
          :on-exceed="handleExceed"
          :file-list="filelist"
          :on-change="handleChansge"
          :on-remove="removeFile"
          name="file"
          action="接口地址"
          accept=".xls,.xlsx"
        >
          <el-button slot="trigger" size="small" type="primary">选取文件</el-button>
          <el-button
            :disabled="btn.disable"
            style="margin-left: 10px;"
            size="small"
            type="success"
            @click="postfile"
          >{{ btn.message }}</el-button>
          <div slot="tip" class="el-upload__tip">上传文件只能为excel文件,且为xlsx,xls格式</div>
        </el-upload>
data() {
	return {
	  file: '',
      filename: '',
      filelist: [],
      limit: 1,
      errmesg: [],
      btn: {
        disable: false,
        message: '上传模板'
      },
	}
}

    handleExceed(e) {
      // 文件超出个数限制时提示报错
      this.$message.error('只能上传一个文件')
    },
    handleChansge(file, fileList) {
      if (!/\.(xlsx|xls)$/i.test(file.name)) {
        this.$message.error('上传文件只能为excel文件,且为xlsx,xls格式')
        this.filelist = []
        this.file = ''
        return false
      }
      this.file = file.raw
      this.filename = file.name
    },
    removeFile(file, fileList) {
      this.file = ''
      this.filename = ''
    },
    postfile() {
      if (this.file === '') {
        this.$message.error('上传文件不能为空')
        return false
      }
      // 文件形式的需要用 formData形式
      const formData = new FormData()
      formData.append('file', this.file)
      this.btn.disable = true
      this.btn.message = '上传中,请等待'
      parsingUploadExcel(formData).then(data => {
        this.btn.disable = false
        this.btn.message = '上传模板'
        this.$message.success(`上传成功`)
        this.matchList = data
      }).catch(err => {
        this.filelist = []
        this.btn.disable = false
        this.btn.message = '上传模板'
        this.matchList = []
        console.log(err)
      })
    },
import * as R from 'ramda';
const XLSX = require('xlsx');
import xlsx from 'node-xlsx';
/**
* @description: 下载模板
* @param {*}
* @return {*}
*/
  async download() {
    const options = {
      '!cols': [
        { wpx: 140 },
        { wpx: 140 },
        { wpx: 140 },
        { wpx: 140 },
        { wpx: 140 }
      ]
    }
    const { ctx } = this;
    ctx.set('Content-Type', 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet');
    ctx.response.attachment(`召回通道填写模板.xlsx`);
    const data = [['channel_id', 'name', 'guarantee', 'pri', 'size']];
    const buffer = xlsx.build([{ name: 'sheet', data }], options);
    ctx.body = buffer;
}
/**
* @description: 导出
* @param {*}
* @return {*}
*/
async exportDetail() {
    const options = {
      '!cols': [
        { wpx: 140 },
        { wpx: 140 },
        { wpx: 140 },
        { wpx: 140 },
        { wpx: 140 }
      ]
    }
    const { ctx, service } = this;
    const results: any[] = await service.content.delivery.channelWhite.detail(ctx.query);
    const table = R.map(item => ({ channel_id: item.channel_id, name: item.name, guarantee: item.guarantee, pri: item.pri, size: item.size }), results)
    const firstRecord = table[0] || {}; // 第一条记录
    const columns = R.keys(firstRecord); // 提取出列
    const values = R.map(R.values, table); // 提取行
    const data = R.prepend(columns, values); // 组装表格数据
    ctx.set('Content-Type', 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet');
    ctx.response.attachment(`${ctx.query.name}.xlsx`);
    const buffer = xlsx.build([{ name: 'sheet', data }], options);
    ctx.body = buffer;
}
/**
* @description: 解析上传的Excel内容
* @param {*}
* @return {*}
*/
async parsingExcel() {
    const { ctx } = this;
    // try {
    //   // 存储获取到的数据
    //   let exceldata = [];
    //   const file = this.ctx.request.files[0];
    //   const workbook = XLSX.readFile(file.filepath);
    //   // 获取 Excel 中所有表名
    //   const sheetNames = workbook.SheetNames; // 返回 ['sheet1', 'sheet2']
    //   // 根据表名获取对应某张表
    //   const worksheet = workbook.Sheets[sheetNames[0]];
    //   // 获取 A1 B1 ... 单元格值
    //   let A1 = worksheet['A1'].v
    //   let B1 = worksheet['B1'].v
    //   let C1 = worksheet['C1'].v
    //   let D1 = worksheet['D1'].v
    //   let E1 = worksheet['E1'].v
    //   for (const sheet in workbook.Sheets) {
    //     if (workbook.Sheets.hasOwnProperty(sheet)) {
    //       // 利用 sheet_to_json 方法将 excel 转成 json 数据
    //       exceldata = exceldata.concat(XLSX.utils.sheet_to_json(workbook.Sheets[sheet]));
    //       //break; // 如果只取第一张表,就取消注释这行
    //     }
    //   }
    //   if (A1 !== 'channel_id' || B1 !== 'name' || C1 !== 'guarantee' || D1 !== 'pri' || E1 !== 'size') {
    //     ctx.helper.error(1,'请使用正确的模板!')
    //     return false
    //   }
    //   ctx.helper.success(exceldata);
    // } catch (error) {
    //   ctx.helper.error(1,'请使用正确的模板!')
    // }

    try {
      const file = this.ctx.request.files[0];
      const excelObj = xlsx.parse(file.filepath);
      let _data: any[] = []
      if(excelObj[0]) {
        const workSheets = excelObj[0].data
        const tableTitle = workSheets[0]
        if (tableTitle[0] !== 'channel_id' || tableTitle[1] !== 'name' || tableTitle[2] !== 'guarantee' || tableTitle[3] !== 'pri' || tableTitle[4] !== 'size') {
          ctx.helper.error(1,'请使用正确的模板!')
          return false
        }
        workSheets.forEach((item: any[],index: Number) => {
          //从第二行开始插入,避免连表头也插入_data里面
          if ( index > 0) {
            let channelItem = {
              channel_id: item[0],
              name: item[1],
              guarantee: item[2],
              pri: item[3],
              size: item[4]
            }
            //往_data插入单元格个值
            _data.push(channelItem)
          }
        });
      }
      ctx.helper.success(_data);
    } catch (error) {
      ctx.helper.error(1,'请使用正确的模板!')
    }
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
首先,在后端使用Express框架创建API接口,包括登录接口和注册接口,另外还需要创建获取留言列表和添加留言的接口。 在前端页面中,用户需要先登录或注册才能使用留言板功能,可以在登录/注册成功后使用cookie或localStorage等方式将用户信息保存起来,然后发送带有用户信息的Ajax请求到后端获取留言列表或添加留言。 下面是一个示例代码,仅供参考: 后端代码: ``` const express = require('express'); const bodyParser = require('body-parser'); const cookieParser = require('cookie-parser'); const app = express(); app.use(bodyParser.urlencoded({extended: false})); app.use(bodyParser.json()); app.use(cookieParser()); // 假设已经定义好用户列表users和留言列表messages // 登录接口 app.post('/login', (req, res) => { const {username, password} = req.body; const user = users.find(u => u.username === username && u.password === password); if (user) { res.cookie('user', JSON.stringify(user)); // 将用户信息保存到cookie中 res.json({code: 0, message: '登录成功'}); } else { res.json({code: 1, message: '用户名或密码错误'}); } }); // 注册接口 app.post('/register', (req, res) => { const {username, password} = req.body; const user = users.find(u => u.username === username); if (user) { res.json({code: 1, message: '用户名已存在'}); } else { users.push({username, password}); res.json({code: 0, message: '注册成功'}); } }); // 获取留言列表接口(需要登录才能访问) app.get('/messages', (req, res) => { const user = JSON.parse(req.cookies.user || '{}'); if (user.username) { res.json({code: 0, messages}); } else { res.json({code: 1, message: '请先登录'}); } }); // 添加留言接口(需要登录才能访问) app.post('/addMessage', (req, res) => { const user = JSON.parse(req.cookies.user || '{}'); if (user.username) { const {content} = req.body; messages.push({id: messages.length + 1, content, username: user.username}); res.json({code: 0, message: '添加成功'}); } else { res.json({code: 1, message: '请先登录'}); } }); app.listen(3000, () => console.log('Server is running...')); ``` 前端代码: ``` <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>留言板</title> <script src="https://cdn.bootcdn.net/ajax/libs/jquery/3.6.0/jquery.min.js"></script> <style> .message-item { margin-bottom: 10px; padding: 10px; border: 1px solid #ddd; border-radius: 5px; } </style> </head> <body> <div class="register"> <h3>注册</h3> <form id="registerForm"> <input type="text" name="username" placeholder="用户名"> <input type="password" name="password" placeholder="密码"> <button type="submit">注册</button> </form> </div> <div class="login" style="display:none"> <h3>登录</h3> <form id="loginForm"> <input type="text" name="username" placeholder="用户名"> <input type="password" name="password" placeholder="密码"> <button type="submit">登录</button> </form> </div> <div class="messages" style="display:none"> <h3>留言板</h3> <form id="addMessageForm"> <textarea name="content" placeholder="请输入留言内容"></textarea> <button type="submit">提交留言</button> </form> <div class="message-list"></div> </div> <script> function showMessage(message) { $('.message-list').prepend(`<div class="message-item">${message.username}: ${message.content}</div>`); } $('#registerForm').submit(function(event) { event.preventDefault(); const username = $('input[name=username]', this).val(); const password = $('input[name=password]', this).val(); $.post('/register', {username, password}, function(res) { alert(res.message); }); }); $('#loginForm').submit(function(event) { event.preventDefault(); const username = $('input[name=username]', this).val(); const password = $('input[name=password]', this).val(); $.post('/login', {username, password}, function(res) { alert(res.message); if (res.code === 0) { $('.register, .login').hide(); $('.messages').show(); // 登录成功后获取留言列表 $.get('/messages', function(res) { if (res.code === 0) { res.messages.forEach(showMessage); } else { alert(res.message); } }); } }); }); $('#addMessageForm').submit(function(event) { event.preventDefault(); const content = $('textarea[name=content]', this).val(); $.post('/addMessage', {content}, function(res) { alert(res.message); if (res.code === 0) { showMessage({username: JSON.parse(document.cookie).user.username, content}); } }); }); </script> </body> </html> ```

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值