React Excel批量上传中需为表格列添加日期选择器以选择库存日期
在React Excel上传功能中为表格列添加日期选择器的解决方案
方案一:使用第三方UI组件库(以Ant Design为例)
这种方式适合快速实现,利用成熟的表格和日期选择器组件,兼顾交互体验和兼容性。
步骤说明
- 解析上传的Excel文件为JSON格式,使用
xlsx库处理文件解析。 - 渲染表格时,为“库存日期”列绑定日期选择器组件,实现实时编辑。
- 维护表格数据状态,同步用户选择的日期值。
- 提交修改后的数据到后端或重新生成Excel文件。
完整代码示例
import React, { useState } from 'react'; import { Upload, Button, Table, DatePicker, message } from 'antd'; import moment from 'moment'; import * as XLSX from 'xlsx'; const InventoryDateEditor = () => { const [tableData, setTableData] = useState([]); const [columns, setColumns] = useState([]); // 解析上传的Excel文件 const handleFileParse = (file) => { const reader = new FileReader(); reader.onload = (e) => { try { const data = new Uint8Array(e.target.result); const workbook = XLSX.read(data, { type: 'array' }); const sheetName = workbook.SheetNames[0]; const worksheet = workbook.Sheets[sheetName]; // 将Excel转为数组格式,第一行作为表头 const excelData = XLSX.utils.sheet_to_json(worksheet, { header: 1 }); const headers = excelData[0]; const rows = excelData.slice(1); // 生成表格列配置,匹配库存日期列 const tableColumns = headers.map(header => { if (header.includes('库存日期')) { return { title: header, dataIndex: header, render: (text, record) => ( <DatePicker value={text ? moment(text, 'YYYY-MM-DD') : null} onChange={(date) => { const updatedRows = [...tableData]; const targetRow = updatedRows.find(r => r[headers[0]] === record[headers[0]]); if (targetRow) { targetRow[header] = date ? date.format('YYYY-MM-DD') : ''; setTableData([...updatedRows]); } }} /> ) }; } return { title: header, dataIndex: header }; }); // 转换数据为对象格式,处理Excel日期序列号 const formattedRows = rows.map(row => { const rowObj = {}; headers.forEach((header, idx) => { if (headers[idx].includes('库存日期') && typeof row[idx] === 'number') { rowObj[header] = XLSX.SSF.format('yyyy-mm-dd', row[idx]); } else { rowObj[header] = row[idx]; } }); return rowObj; }); setColumns(tableColumns); setTableData(formattedRows); message.success('Excel文件解析完成'); } catch (err) { message.error('文件解析失败,请检查文件格式'); } }; reader.readAsArrayBuffer(file); return false; // 阻止默认上传行为 }; // 提交修改后的数据 const handleSubmit = () => { // 此处可将tableData提交到后端,或转换为Excel文件下载 console.log('最终数据:', tableData); message.success('数据已提交'); }; return ( <div style={{ padding: '2rem' }}> <Upload beforeUpload={handleFileParse} accept=".xlsx,.xls" showUploadList={false} > <Button type="primary">上传商品列表Excel</Button> </Upload> {tableData.length > 0 && ( <div style={{ marginTop: '2rem' }}> <Table columns={columns} dataSource={tableData} rowKey={record => record[columns[0].dataIndex]} bordered pagination={false} /> <Button type="primary" style={{ marginTop: '1rem' }} onClick={handleSubmit}> 确认库存日期并提交 </Button> </div> )} </div> ); }; export default InventoryDateEditor;
方案二:原生HTML表格+日期输入框
如果不需要复杂的UI组件,可直接使用原生input[type="date"]实现,更轻量化。
核心代码片段
// 渲染表格部分 {tableData.length > 0 && ( <table border="1" style={{ borderCollapse: 'collapse', marginTop: '2rem' }}> <thead> <tr> {columns.map(col => <th key={col} style={{ padding: '0.5rem' }}>{col}</th>)} </tr> </thead> <tbody> {tableData.map((row, idx) => ( <tr key={idx}> {columns.map(col => ( <td key={col} style={{ padding: '0.5rem' }}> {col.includes('库存日期') ? ( <input type="date" value={row[col]} onChange={(e) => { const updatedRows = [...tableData]; updatedRows[idx][col] = e.target.value; setTableData(updatedRows); }} /> ) : ( row[col] )} </td> ))} </tr> ))} </tbody> </table> )}
关键注意事项
- Excel日期格式处理:Excel中的日期会被解析为数字(序列号),需用
XLSX.SSF.format('yyyy-mm-dd', 日期数字)转换为标准日期字符串。 - 列匹配灵活性:如果“库存日期”列名不固定,可添加下拉框让用户手动选择目标列,提升兼容性。
- 兼容性:原生
input[type="date"]在部分浏览器(如IE)不支持,建议用第三方日期选择器组件兜底。
内容的提问来源于stack exchange,提问作者Mohammed Sajid F
相关产品推荐
相关产品推荐

