必须在导出前将时间字段转为标准字符串,用parseData钩子调用layui.util.toDateString格式化;身份证等长数字需加单引号或设type:'string';CSV乱码需加BOM或改用xlsx格式。
导出后日期变成时间戳或1900/1/1
本质是 layexcel 没识别出字段类型,把时间戳数字(如 1712345678000)当普通数值写进 excel 单元格,excel 自动按“常规格式”渲染成日期 1900/1/1 或科学计数法。
必须在导出前把时间字段转成标准字符串,而不是只靠 templet 渲染表格界面:
- 用
parseData钩子统一处理原始响应数据,例如:parseData: function(res) { res.data.forEach(function(item) { if (item.createTime) { item.createTime = layui.util.toDateString(item.createTime, 'yyyy-MM-dd HH:mm:ss'); } }); return res; } - 如果后端返回的是 ISO 字符串(如
"2026-04-21T09:35:00.000Z"),先用new Date()解析再格式化,避免直接传 ISO 字符串给toDateString导致解析失败 - 不要依赖
table.exportFile(),它不走parseData,也不处理时间字段;改用layExcel.exportExcel()并传入已格式化的数据数组
导出后日期显示为“45032”这类整数
这是 Excel 把时间戳当成了“天数”,从 1900-1-1 开始算的序列值。说明数据没被转成字符串,而是以数字形式写进了单元格。
关键动作是「强制类型转换」:
- 对每个时间字段做显式字符串拼接:
item.createTime + ''或String(item.createTime) - 更稳妥的做法是用
layui.util.toDateString,它内部做了容错,即使传入null或无效值也不会报错 - 若字段可能为空,加一层判断:
item.createTime = item.createTime ? layui.util.toDateString(item.createTime, 'yyyy-MM-dd') : '';
中文表头+时间内容打开全是乱码或问号
不是字体问题,是文件编码和 Excel 解析机制冲突。layExcel 默认生成 CSV,而 Windows 版 Excel 打开 UTF-8 编码的 CSV 时默认用 ANSI 解析,必然乱码。
解决路径很窄,只有两个有效选择:
- 放弃 CSV,改用真正的
.xlsx格式:确保引入的是支持 xlsx 的lay-excel版本(非阉割版),调用layExcel.exportExcel({ type: 'xlsx', ... }) - 如果必须用 CSV,在 Blob 构造时加 BOM 头:
'\ufeff' + csvContent,但仅对部分 Excel 有效,兼容性差 - 服务端配合最稳:前端只传结构化 JSON,由后端用
exceljs或Apache POI生成带格式、UTF-8 BOM、正确单元格类型的 .xlsx 文件
身份证、手机号等长数字导出后变科学计数法
这和时间问题同源:Excel 自动类型推断把长数字当数值处理。时间戳是数字,身份证也是数字,Excel 一视同仁。
通用解法就是「让 Excel 明白这是文本」:
- 在导出前给对应字段值加制表符或单引号前缀:
'" + item.idCard或\t + item.idCard(注意:加单引号仅对 CSV 有效,对 xlsx 需设单元格格式为文本) - 使用
layExcel.exportExcel()时,通过cols配置项指定字段类型:{ field: 'idCard', title: '身份证', type: 'string' } - 若用自定义导出(如
exceljs),需手动设置列格式:column.width = 20; column.style.numFmt = '@';
parseData 对它的改造时机、以及 exportExcel 接收的数据是否已“脱敏”成纯字符串。漏掉任意一环,Excel 就会按自己的理解重新解释数据。


















