使用Freemarker模版导出xls文件使用excel打开提示文件损坏
本文是通过一步步的还原事件的发生并解决的一个过程记录,如果想知道如何解决的可以直接跳转文章末尾结论部分
提示一下,关注一下
Table标签中的ss:ExpandedRowCount属性
解决的问题
在项目中使用freemarker的xml模板导出xls格式的Excel文件时,使用国产Office工具可以打开查看,使用Excel打开提示文件已损坏
关键词
国产office,Excel,freemarker
环境信息
-
Windows 11 -
office 2019 -
永中office2022体验版 -
JDK8 -
springboot 2.6.13 -
freemarker 2.6.13
事件还原
1、首先使用Excel创建一个空白excel文件,输入我们要导出的表格模板,如下图所示,我们创建一个表格,表格中导出姓名、年龄、电话、住址等信息的这样一个表格,并且添加了一行示例数据
2、点击另存为,选中xml格式导出
3、打开xml文件,修改添加数据的地方,使用freemarker语法遍历输出数据
修改前如下图所示
修改后如下图所示
其中的#list为固定语法,resultList为获取输入模板数据的key,该值是一个List,as item是*List**中的每一个对象以item来遍历
item.name为获取姓名,item.age为获取年龄,item.phont为获取电话,item.address为获取住址
${item.name!''}的完整意思就是输出用户名,为空时输出为空
4、创建springboot程序,并在resources下创建freemarker目录,继续创建test.xml模板文件,test.xml文件内容就是上一步我们修改完成之后的xml文件,结构如下
文件内容如下(本内容为Excel打开异常的,如需正常的,需跳转文章末尾)
提示一下,关注一下
Table标签中的ss:ExpandedRowCount属性
<?xml version="1.0"?>
<?mso-application progid="Excel.Sheet"?>
<Workbook xmlns="urn:schemas-microsoft-com:office:spreadsheet"xmlns:o="urn:schemas-microsoft-com:office:office"xmlns:x="urn:schemas-microsoft-com:office:excel"xmlns:ss="urn:schemas-microsoft-com:office:spreadsheet"xmlns:html="http://www.w3.org/TR/REC-html40"><DocumentProperties xmlns="urn:schemas-microsoft-com:office:office"><Author>zuiyu</Author><LastAuthor>zuiyu</LastAuthor><Created>2023-07-26T02:16:31Z</Created><LastSaved>2023-07-26T02:18:00Z</LastSaved><Version>16.00</Version></DocumentProperties><OfficeDocumentSettings xmlns="urn:schemas-microsoft-com:office:office"><AllowPNG/></OfficeDocumentSettings><ExcelWorkbook xmlns="urn:schemas-microsoft-com:office:excel"><WindowHeight>5880</WindowHeight><WindowWidth>14400</WindowWidth><WindowTopX>32767</WindowTopX><WindowTopY>32767</WindowTopY><ProtectStructure>False</ProtectStructure><ProtectWindows>False</ProtectWindows></ExcelWorkbook><Styles><Style ss:ID="Default" ss:Name="Normal"><Alignment ss:Vertical="Center"/><Borders/><Font ss:FontName="等线" x:CharSet="134" ss:Size="11" ss:Color="#000000"/><Interior/><NumberFormat/><Protection/></Style></Styles><Worksheet ss:Name="Sheet1"><Table ss:ExpandedColumnCount="4" ss:ExpandedRowCount="2" x:FullColumns="1"x:FullRows="1" ss:DefaultColumnWidth="51" ss:DefaultRowHeight="13.875"><Row><Cell><Data ss:Type="String">姓名</Data></Cell><Cell><Data ss:Type="String">年龄</Data></Cell><Cell><Data ss:Type="String">电话</Data></Cell><Cell><Data ss:Type="String">住址</Data></Cell></Row><#list resultList as item><Row><Cell><Data ss:Type="String">${item.name!''}</Data></Cell><Cell><Data ss:Type="Number">${item.age!''}</Data></Cell><Cell><Data ss:Type="Number">${item.phone!''}</Data></Cell><Cell><Data ss:Type="String">${item.address!''}</Data></Cell></Row></#list></Table><WorksheetOptions xmlns="urn:schemas-microsoft-com:office:excel"><PageSetup><Header x:Margin="0.3"/><Footer x:Margin="0.3"/><PageMargins x:Bottom="0.75" x:Left="0.7" x:Right="0.7" x:Top="0.75"/></PageSetup><Selected/><Panes><Pane><Number>3</Number><ActiveRow>4</ActiveRow><ActiveCol>5</ActiveCol></Pane></Panes><ProtectObjects>False</ProtectObjects><ProtectScenarios>False</ProtectScenarios></WorksheetOptions>
</Worksheet></Workbook> 5、编写导出excel文件的代码,都是测试数据,看看就好,只是举个例子
需要关注的点是,我们此处导出的用户数据为100,而上文中提示需要关注的参数
ss:ExpandedRowCount参数值为2,这就是后文要探讨的关键所在
package com.example.exceldemo.demos.excel;import freemarker.template.Configuration;
import freemarker.template.Template;
import freemarker.template.TemplateException;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletResponse;
import java.io.BufferedWriter;
import java.io.IOException;
import java.io.OutputStreamWriter;
import java.net.URLEncoder;
import java.util.*;/*** @Author zuiyu* @Date 2023/7/26 10:26*/
@RestController
@RequestMapping("/excel")
public class ExcelController {@GetMapping("/export")public void export(HttpServletResponse response) throws IOException, TemplateException {Configuration configuration = new Configuration(Configuration.VERSION_2_3_26);configuration.setDefaultEncoding("utf-8");configuration.setClassForTemplateLoading(getClass(),"/freemarker");Template template = configuration.getTemplate("test.xml");List<Person> list = new ArrayList<>();for (int i = 0; i < 100; i++) {Person person1 = new Person();person1.setName("测试用户名:"+i);person1.setAge((i+1)*2);person1.setPhone(new Random().nextInt(100));person1.setAddress("地址:"+i);list.add(person1);}Map<String,Object> map = new HashMap<>();map.put("resultList",list);ServletOutputStream outputStream = response.getOutputStream();response.setContentType("application/octet-stream");response.setHeader("Content-Disposition", "attachment; filename=" + URLEncoder.encode("测试xml导出excel.xls", "UTF-8"));BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(outputStream));template.process(map,bw);bw.flush();bw.close();System.out.println("导出成功");}
} 6、下面执行接口http://localhost:8080/excel/export导出xls文件进行查看文件内容,我们的预期就是国产Office可以打开观看,而Excel打开时提示文件已损坏。打开结果就不进行展示了,感兴趣的可以使用上面的代码进行一下测试
7、下面我们修改ss:ExpandedRowCount="2"为ss:ExpandedRowCount="9999",这样就可以容纳我们的100条记录。此时重启程序进行导出我们就可以发现不管是使用Excel查看还是国产Office查看都可以进行正常的显示了
8、下面是修改之后的完整的xml文件内容
<?xml version="1.0"?>
<?mso-application progid="Excel.Sheet"?>
<Workbook xmlns="urn:schemas-microsoft-com:office:spreadsheet"xmlns:o="urn:schemas-microsoft-com:office:office"xmlns:x="urn:schemas-microsoft-com:office:excel"xmlns:ss="urn:schemas-microsoft-com:office:spreadsheet"xmlns:html="http://www.w3.org/TR/REC-html40"><DocumentProperties xmlns="urn:schemas-microsoft-com:office:office"><Author>zuiyu</Author><LastAuthor>zuiyu</LastAuthor><Created>2023-07-26T02:16:31Z</Created><LastSaved>2023-07-26T02:18:00Z</LastSaved><Version>16.00</Version></DocumentProperties><OfficeDocumentSettings xmlns="urn:schemas-microsoft-com:office:office"><AllowPNG/></OfficeDocumentSettings><ExcelWorkbook xmlns="urn:schemas-microsoft-com:office:excel"><WindowHeight>5880</WindowHeight><WindowWidth>14400</WindowWidth><WindowTopX>32767</WindowTopX><WindowTopY>32767</WindowTopY><ProtectStructure>False</ProtectStructure><ProtectWindows>False</ProtectWindows></ExcelWorkbook><Styles><Style ss:ID="Default" ss:Name="Normal"><Alignment ss:Vertical="Center"/><Borders/><Font ss:FontName="等线" x:CharSet="134" ss:Size="11" ss:Color="#000000"/><Interior/><NumberFormat/><Protection/></Style></Styles><Worksheet ss:Name="Sheet1"><Table ss:ExpandedColumnCount="4" ss:ExpandedRowCount="9999" x:FullColumns="1"x:FullRows="1" ss:DefaultColumnWidth="51" ss:DefaultRowHeight="13.875"><Row><Cell><Data ss:Type="String">姓名</Data></Cell><Cell><Data ss:Type="String">年龄</Data></Cell><Cell><Data ss:Type="String">电话</Data></Cell><Cell><Data ss:Type="String">住址</Data></Cell></Row><#list resultList as item><Row><Cell><Data ss:Type="String">${item.name!''}</Data></Cell><Cell><Data ss:Type="Number">${item.age!''}</Data></Cell><Cell><Data ss:Type="Number">${item.phone!''}</Data></Cell><Cell><Data ss:Type="String">${item.address!''}</Data></Cell></Row></#list></Table><WorksheetOptions xmlns="urn:schemas-microsoft-com:office:excel"><PageSetup><Header x:Margin="0.3"/><Footer x:Margin="0.3"/><PageMargins x:Bottom="0.75" x:Left="0.7" x:Right="0.7" x:Top="0.75"/></PageSetup><Selected/><Panes><Pane><Number>3</Number><ActiveRow>4</ActiveRow><ActiveCol>5</ActiveCol></Pane></Panes><ProtectObjects>False</ProtectObjects><ProtectScenarios>False</ProtectScenarios></WorksheetOptions>
</Worksheet></Workbook> 总结
通过这次实验可以得知,文件的打开失败的根本原因就是数据行超过了设置的ExpandedRowCount属性值。而我们要做的就是修改该值到能容纳我们要导出的数据即可。甚至是可以改为变量读取数据长度是否可行 。
如果感觉有用的话欢迎点赞、收藏、转发,关注公众号《醉鱼Java》获取一手面试资料,一起学编程
本文由 mdnice 多平台发布
相关文章:
使用Freemarker模版导出xls文件使用excel打开提示文件损坏
本文是通过一步步的还原事件的发生并解决的一个过程记录,如果想知道如何解决的可以直接跳转文章末尾结论部分 提示一下,关注一下 Table 标签中的 ss:ExpandedRowCount 属性 解决的问题 在项目中使用freemarker的xml模板导出xls格式的Excel文件时…...
初识Linux
今天简单了解了关于操作系统的发展史,学习了在Linux中如何远程连接云服务器的指令,以及在Linux中创建多个用户的指令。 1. ssh root 服务器远程地址 作用是用来连接XShell与云服务器,输入该指令后会自动生成输入密码的窗口,如…...
python——案例六:清空列表用clear()方法实现
案例六:清空列表用clear()方法实现LIST[0,1,2,3,4,5] print(清空前:,LIST) LIST.clear() print(清空后:,LIST)...
测试|Selenium之WebDriver常见API使用
测试|Selenium之WebDriver常见API使用 文章目录 测试|Selenium之WebDriver常见API使用1.定位对象(findElement)css定位xpath定位css选择器语法:xpath语法:校验结果 2.操作对象鼠标点击对象在对象上模拟按键输入clear清除对象输入的文本内容su…...
手把手教你uniapp和小程序分包
分包目的在于提高小程序的体积,多一个包就多2M,最多20M 常规的分包: 小程序一打开首先加载主包,然后再加载分包 分包可以用主包内的资源,主包不可以使用分包的资源 分包A不可以使用分包B里面的内容 分包可以使用a…...
Java中的代理模式
Java中的代理模式 1. 静态代理2. JDK动态代理3. CGLib动态代理 1. 静态代理 接口 public interface ICeo {void meeting(String name) throws InterruptedException; }目标类 public class Ceo implements ICeo{public void meeting(String name) throws InterruptedExcepti…...
LeetCode每日一题——1331.数组序号转换
题目传送门 题目描述 给你一个整数数组 arr ,请你将数组中的每个元素替换为它们排序后的序号。 序号代表了一个元素有多大。序号编号的规则如下: 序号从 1 开始编号。一个元素越大,那么序号越大。如果两个元素相等,那么它们的…...
2、Tomcat介绍(下)
组件分类 在Apache Tomcat中,有几个顶级组件,它们是Tomcat的核心组件,负责整个服务器的运行和管理。这些顶级组件包括: Server(服务器):Tomcat的server.xml配置文件中的<Server>元素代表整个Tomcat服务器实例。每…...
JAVA 正则表达式(heima)
JAVA 正则表达式(heima) public class RegexDemo01 {/** 正则表达式介绍:本质来说就是一个字符串,字符串中可以指定规则,来对其他字符串进行校验。* public boolean matches(String regex):根据传入的正则表达式&#…...
布瑞特单圈绝对值旋转编码器串口数据读取
布瑞特单圈绝对值旋转编码器串口数据读取 数据手册:http://briter.net/col.jsp?id109 (2.1版本RS485说明书通信协议 单圈.pdf) 绝对式编码器为布瑞特BRT38-ROM16384-RT1,采用RS485通信。 该绝对式编码器共有5根线:红、黄、黑、绿、白 由…...
Linux第六章之vim与gcc使用
一、Linux编辑器-vim使用 vi/vim的区别简单点来说,它们都是多模式编辑器,不同的是vim是vi的升级版本,它不仅兼容vi的所有指令,而且还有一些新的特性在里面。例如语法加亮,可视化操作不仅可以在终端运行,也…...
【Golang】Golang进阶系列教程--为什么说 Go 语言字符串是不可变的?
文章目录 前言推荐阅读 前言 最近有读者留言说,平时在写代码的过程中,是会对字符串进行修改的,但网上都说 Go 语言字符串是不可变的,这是为什么呢? 这个问题本身并不困难,但对于新手来说确实容易产生困惑…...
ES开启身份认证
文章目录 X-Pack简介之前的安全方案ES开启认证ES服务升级https协议开启集群节点之间的证书认证 X-Pack简介 X-Pack是Elastic Stack扩展功能,提供安全性,警报,监视,报告,机器学习和许多其他功能。 X-Pack的发展演变&am…...
Docker安装es以及ik分词器
1、拉取镜像 docker pull elasticsearch:7.10.12、下载对应版本的ik分词、并将它们解压到ik文件夹下,如图 https://github.com/medcl/elasticsearch-analysis-ik/releases 3、在服务器上创建文件夹 mkdir /usr/elklog/elk/es mkdir /usr/elklog/elk/es/data mkdi…...
中断、进程调度、进程切换、系统调用,模式切换的那些事情
提示:风萧声动,玉壶光转,一夜鱼龙舞 文章目录 前言中断进程调度进程切换线程切换模式切换所以他们有什么关系? 前言 本文内容主要参考以下几个博文中学得 进程与线程(中)的2.2.7 进程切换VS模式切换&#…...
使用web-view实现网页端和uni-app端是数据传输
要实现这个功能 第一步:要在vue的public文件夹下面引入 <script type"text/javascript" src"https://js.cdn.aliyun.dcloud.net.cn/dev/uni-app/uni.webview.1.5.2.js"></script> 第二步:建立一个新的空的uni-app项目…...
Ajax快速入门
Ajax Ajax就是前端访问服务器端数据的一个技术 还有主要就是异步交互 就是在不刷新整页面的情况下,和服务器交换部分我也数据 比如搜索的联想技术 同步和异步的概念 一个是客户端需要等待服务器完成处理,才能进行别的事 一个是客户端不需要等待服务器处…...
Google OAuth 2 authorization - Error: redirect_uri_mismatch 400
出现这个问题,一般是因为google授权origin地址和重定向redirect_uri地址没有匹配上。 请仔细检查重定向地址的url中origin部分和授权origin部分是否能够匹配:...
Qt 中操作xml文件和JSON字符串
文章目录 1、概述1.1、xml介绍1.2、json介绍 2、xml文件增删改查2.1、写xml文件内容2.2、读xml文件内容2.3、删除xml文件内容2.4、修改xml文件内容 3、构建JSON字符串3.1、JSON字符串排版4、剪切板操作 1、概述 1.1、xml介绍 XML 指可扩展标记语言(EXtensible Mark…...
React 基础篇(二)
💻 React 基础篇(二)🏠专栏:React 👀个人主页:繁星学编程🍁 🧑个人简介:一个不断提高自我的平凡人🚀 🔊分享方向:目前主攻…...
突破性创新:Midscene.js如何用AI视觉驱动重塑跨平台自动化测试
突破性创新:Midscene.js如何用AI视觉驱动重塑跨平台自动化测试 【免费下载链接】midscene AI-powered, vision-driven UI automation for every platform. 项目地址: https://gitcode.com/GitHub_Trending/mid/midscene 在当今复杂的软件生态中,跨…...
LaserGRBL:5分钟掌握开源激光雕刻控制软件的核心功能
LaserGRBL:5分钟掌握开源激光雕刻控制软件的核心功能 【免费下载链接】LaserGRBL Laser optimized GUI for GRBL 项目地址: https://gitcode.com/gh_mirrors/la/LaserGRBL LaserGRBL是一款专为GRBL控制器优化的开源激光雕刻控制软件,为Windows用户…...
别再对着示波器数NOP了!用STM32的SPI+DMA驱动WS2812灯带,一个CubeMX配置就搞定
用STM32的SPIDMA高效驱动WS2812灯带:告别手动调时序的工程化方案 在嵌入式开发中,驱动WS2812灯带一直是个让人又爱又恨的挑战。这种智能RGB灯带以其简单的单线控制和丰富的色彩表现广受欢迎,但精确的时序要求也让不少开发者头疼不已。传统方法…...
环境配置与基础教程:保姆级教程:在 Mac M 芯片上利用 MPS 加速 YOLO 训练与推理的完整环境搭建
写在前面:为什么你的 Mac 也能跑深度学习? 几年前,如果有人告诉你用 MacBook 训练深度学习模型,你大概会笑出声。那时候 Mac 上的 PyTorch 只能依赖 CPU 吭哧吭哧地算,训练一个小模型都要等到天荒地老。但自从 Apple Silicon 芯片(M1、M2、M3、M4,以及最新的 M5)横空出…...
Arm架构在中国市场的机遇、挑战与实战指南
1. 项目概述:Arm架构的“中国故事”与我的观察最近几年,在技术圈和投资圈里,“Arm架构”和“中国市场”这两个词的组合热度一直居高不下。作为一名长期关注处理器架构和产业生态的从业者,我几乎每周都能在行业交流、客户会议甚至供…...
PlayAI多语种翻译能力边界实测(含方言识别、专业术语库热加载、混合语种断句逻辑),你敢信它已通过ISO/IEC 24615标准认证?
更多请点击: https://intelliparadigm.com 第一章:PlayAI多语种同步翻译功能详解 PlayAI 的多语种同步翻译功能基于端到端神经机器翻译(NMT)架构与实时语音流处理引擎深度融合,支持中、英、日、韩、法、西、德、俄等 …...
PYTHON基础入门----商品库存管理系统
如果商品信息只保存在程序运行过程中,那么程序关闭后,所有数据都会丢失。因此,我们需要将商品数据保存到文件中,下次运行程序时还能继续读取和使用。本题要求你编写一个简单的商品库存管理系统,实现商品的添加、查看、…...
ZoneMinder开源监控系统:30分钟打造专业级安防解决方案,支持IP/USB/模拟摄像头全兼容
ZoneMinder开源监控系统:30分钟打造专业级安防解决方案,支持IP/USB/模拟摄像头全兼容 【免费下载链接】zoneminder ZoneMinder is a free, open source Closed-circuit television software application developed for Linux which supports IP, USB and…...
从零搭建CFD-DEM耦合环境:OpenFOAM与PFC3D在WSL2下的实战部署指南
1. 环境准备:WSL2与Ubuntu基础配置 第一次接触CFD-DEM耦合仿真的同学,建议从Windows系统起步。微软的WSL2(Windows Subsystem for Linux)现在已经能完美支持Ubuntu环境,实测比虚拟机流畅得多。我去年在联想小新Pro16上…...
Nintendo Switch大气层破解系统终极指南:从入门到精通完整教程
Nintendo Switch大气层破解系统终极指南:从入门到精通完整教程 【免费下载链接】Atmosphere-stable 大气层整合包系统稳定版 项目地址: https://gitcode.com/gh_mirrors/at/Atmosphere-stable 大气层整合包系统是为Nintendo Switch设备提供的一站式定制化固件…...
