专栏电商日志财经减肥爱情
投稿投诉
爱情常识
搭配分娩
减肥两性
孕期塑形
财经教案
论文美文
日志体育
养生学堂
电商科学
头戴业界
专栏星座
用品音乐

Java根据Freemarker模板生成Word文件

  1。准备模板
  模板数据模型
  1、将准备好的Word模板文件另存为。xml文件(PS:建议使用WPS来创建Word文件,不建议用Office)
  2、将。xml文件重命名为。ftl文件
  3、用文本编辑器打开。ftl文件,将内容复制出来,格式化一下,再覆盖原来的内容
  (PS:格式化一下是为了方便查找并设置变量占位符,当然设置好模板参数变量以后可以再压缩后再写会。ftl文件)
  另外,强烈不建议在word文件中去编辑设置模板变量,因为。docx文件在另存为。xml文件后,原先好好的一个变量可能就被拆开了,建议另存为之后再用文本编辑器打开去编辑。
  4、设置模板参数(变量占位符)
  2。代码实现
  pom。xmllt;?xmlversion1。0encodingUTF8?projectxmlnshttp:maven。apache。orgPOM4。0。0xmlns:xsihttp:www。w3。org2001XMLSchemainstancexsi:schemaLocationhttp:maven。apache。orgPOM4。0。0https:maven。apache。orgxsdmaven4。0。0。xsdmodelVersion4。0。0modelVersionparentgroupIdorg。springframework。bootgroupIdspringbootstarterparentartifactIdversion2。7。3versionrelativePath!lookupparentfromrepositoryparentgroupIdcom。examplegroupIddemo920artifactIdversion0。0。1SNAPSHOTversionnamedemo920namedescriptiondemo920descriptionpropertiesjava。version1。8java。versionpropertiesdependenciesdependencygroupIdorg。springframework。bootgroupIdspringbootstarterfreemarkerartifactIddependencydependencygroupIdorg。springframework。bootgroupIdspringbootstarterwebartifactIddependencydependencygroupIdcn。hutoolgroupIdhutoolcoreartifactIdversion5。8。7versiondependencydependencygroupIdcom。itextpdfgroupIditextpdfartifactIdversion5。5。13。3versiondependency!dependencygroupIdcom。asposegroupIdasposewordsartifactIdversion22。9versionclassifierjdk17classifierdependencydependencygroupIdorg。projectlombokgroupIdlombokartifactIdoptionaltrueoptionaldependencydependencygroupIdorg。springframework。bootgroupIdspringbootstartertestartifactIdscopetestscopedependencydependenciesbuildpluginsplugingroupIdorg。springframework。bootgroupIdspringbootmavenpluginartifactIdconfigurationexcludesexcludegroupIdorg。projectlombokgroupIdlombokartifactIdexcludeexcludesconfigurationpluginpluginsbuildproject
  写个类测试一下packagecom。example。demo920;importcom。example。demo920。domain。LoanReceipt;importfreemarker。template。Configuration;importfreemarker。template。Template;importorg。junit。jupiter。api。Test;importorg。springframework。boot。test。context。SpringBootTest;importjava。io。BufferedWriter;importjava。io。File;importjava。io。FileOutputStream;importjava。io。OutputStreamWriter;importjava。math。BigDecimal;importjava。nio。file。Path;importjava。nio。file。Paths;importjava。time。LocalDateTime;importjava。time。format。DateTimeFormatter;importjava。util。HashMap;importjava。util。Locale;importjava。util。Map;SpringBootTestclassDemo920ApplicationTests{privateDateTimeFormatterDTFDateTimeFormatter。ofPattern(yyyyMMddHHmmss,Locale。CHINA);TestvoidcontextLoads(){}TestvoidtestGenerateWord()throwsException{ConfigurationconfigurationnewConfiguration(Configuration。VERSION2331);configuration。setDefaultEncoding(UTF8);configuration。setClassForTemplateLoading(this。getClass(),templates);Templatetemplateconfiguration。getTemplate(借条。ftl);PathpathPaths。get(tmp,contract);FilefileDirpath。toFile();if(!fileDir。exists()){fileDir。mkdirs();}Stringfilename借条LocalDateTime。now()。format(DTF)。docx;filenamepath。toFile()File。separatorfilename;BufferedWriterwriternewBufferedWriter(newOutputStreamWriter(newFileOutputStream(filename)));template。process(getDataMap(),writer);template。process(getData(),writer);writer。flush();writer。close();}MapString,ObjectgetDataMap(){MapString,ObjectdataMapnewHashMap();dataMap。put(borrowerName,李白);dataMap。put(borrowerIdCard,421302199001012426);dataMap。put(lenderName,杜甫);dataMap。put(amount,100);dataMap。put(amountInWords,壹佰);dataMap。put(startDate,2022年8月15日);dataMap。put(endDate,2022年11月11日);dataMap。put(borrowingMonths,3);dataMap。put(interestRate,1。23);dataMap。put(guarantorName,白居易);dataMap。put(guarantorIdCard,421302199203152412);returndataMap;}LoanReceiptgetData(){LoanReceiptreceiptnewLoanReceipt();receipt。setBorrowerName(狄仁杰);receipt。setBorrowerIdCard(421302198710121234);receipt。setBorrowingMonths(6);receipt。setLenderName(李元芳);receipt。setAmount(newBigDecimal(101));receipt。setAmountInWords(壹佰零壹);receipt。setInterestRate(newBigDecimal(0。6));receipt。setStartDate(2022年1月1日);receipt。setEndDate(2022年6月30日);receipt。setGuarantorName(武则天);receipt。setGuarantorIdCard(421302199101014567);returnreceipt;}}
  最主要的是下面两行加载模板Templatetemplateconfiguration。getTemplate(借条。ftl);填充数据template。process(getData(),writer);
  数据可以是Map也可以是一个对象
  改进一下,将生成文件的操作单独写成一个工具方法packagecom。example。demo920。util;importcn。hutool。core。io。IoUtil;importfreemarker。template。Configuration;importfreemarker。template。Template;importfreemarker。template。TemplateException;importjava。io。;publicclassFreemarkerUtils{生成WordparamtemplateDir模板所在的目录paramtemplateName模板文件名称paramfilename生成的文件(含路径)paramdataModel模板参数数据publicstaticvoidgenerateWord(FiletemplateDir,StringtemplateName,Stringfilename,ObjectdataModel){BufferedWriterwriternull;ConfigurationconfigurationnewConfiguration(Configuration。VERSION2331);configuration。setDefaultEncoding(UTF8);try{configuration。setDirectoryForTemplateLoading(templateDir);Templatetemplateconfiguration。getTemplate(templateName);writernewBufferedWriter(newOutputStreamWriter(newFileOutputStream(filename)));template。process(dataModel,writer);writer。flush();}catch(IOExceptione){thrownewRuntimeException(e);}catch(TemplateExceptione){thrownewRuntimeException(e);}finally{IoUtil。close(writer);}}}
  再测试一下packagecom。example。demo920;importcn。hutool。core。io。IoUtil;importcom。example。demo920。util。FreemarkerUtils;importcom。example。demo920。util。PdfUtils;importorg。junit。jupiter。api。Test;importorg。springframework。util。ResourceUtils;importjava。io。;importjava。nio。file。Files;importjava。nio。file。Path;importjava。nio。file。Paths;importjava。time。LocalDateTime;importjava。util。HashMap;importjava。util。Map;publicclassWordTest{1、从文件服务器下载模板文件2、根据业务类型获取需要填充模板的数据3、模板数据再经过处理生成新的文件4、将生成后的文件上传到文件服务器,并返回一个文件ID5、业务可以保存这个文件ID或者文件的路径TestvoidtestGenerateWordV1()throwsException{PathtempPathPaths。get(tmp,contract2);FilepathtempPath。toFile();if(!path。exists()){path。mkdirs();}FiletempFileFiles。createTempFile(tempPath,qiantiao,。docx)。toFile();System。out。println(tempFile。getParent());System。out。println(tempFile。getName());FileOutputStreamfosnewFileOutputStream(tempFile);FiletemplateFileResourceUtils。getFile(classpath:templates借条。ftl);FileInputStreamfisnewFileInputStream(templateFile);IoUtil。copy(fis,fos);Stringfilename借条System。currentTimeMillis()。docx;filenametmpcontractFile。separatorfilename;FreemarkerUtils。generateWord(newFile(tempFile。getParent()),tempFile。getName(),filename,getDataMap());}获取数据MapString,ObjectgetDataMap(){MapString,ObjectdataMapnewHashMap();dataMap。put(borrowerName,李白2);dataMap。put(borrowerIdCard,421302199001012426);dataMap。put(lenderName,杜甫);dataMap。put(amount,100);dataMap。put(amountInWords,壹佰);dataMap。put(startDate,2022年8月15日);dataMap。put(endDate,2022年11月11日);dataMap。put(borrowingMonths,3);dataMap。put(interestRate,1。23);dataMap。put(guarantorName,白居易);dataMap。put(guarantorIdCard,421302199203152412);returndataMap;}TestvoidtestGenerateWord2()throwsException{FiletemplateDirResourceUtils。getFile(ResourceUtils。CLASSPATHURLPREFIXtemplates);StringtemplateName借条。ftl;StringdestFilename借条System。currentTimeMillis()。docx;MapString,ObjectdatagetDataMap();FreemarkerUtils。generateWord(templateDir,templateName,destFilename,data);}}
  3。PDF文件加水印
  有时候,生成或者从服务器下载的文件是需要加水印的,比如标识这个文件是谁下载的之类的
  pdf加水印还是比较方便的,用itext组件可以轻松实现
  另外,如果最终需要pdf文件,建议直接生成pdf文件,跳过word转pdf的步骤packagecom。example。demo920。util;importcn。hutool。core。io。IoUtil;importcom。aspose。words。Document;importcom。aspose。words。SaveFormat;importcom。itextpdf。text。BaseColor;importcom。itextpdf。text。DocumentException;importcom。itextpdf。text。Element;importcom。itextpdf。text。Image;importcom。itextpdf。text。pdf。;importjava。io。File;importjava。io。FileInputStream;importjava。io。FileOutputStream;importjava。io。IOException;importjava。time。LocalDateTime;authorchengjianshengdate20220921publicclassPdfUtils{Word转PDFhttps:www。aspose。com注意:Aspose。Words这个组件是收费的,如果购买的话生成的PDF会有水印。可以去找相应的破解版本,但是我感觉完全可以跳过Word直接生成PDF。比如,可以通过Freemarker直接生成PDF,或者利用iText通过模板生成PDFparamsrcparamdestpublicstaticvoidwordToPdf(Stringsrc,Stringdest){FilefilenewFile(src);if(!file。exists()){thrownewRuntimeException(文件不存在);}FileInputStreamfisnull;try{fisnewFileInputStream(file);DocumentwpdnewDocument(fis);wpd。save(dest,SaveFormat。PDF);}catch(Exceptione){thrownewRuntimeException(e);}finally{IoUtil。close(fis);}}加水印paramsrc源文件paramdest目标文件paramtext文字paramimagePath图片地址publicstaticvoidaddWatermark(Stringsrc,Stringdest,Stringtext,StringimagePath){try{待加水印的文件PdfReaderreadernewPdfReader(src);加完水印的文件PdfStamperstampernewPdfStamper(reader,newFileOutputStream(dest));字体BaseFontbaseFontBaseFont。createFont(STSongLight,UniGBUCS2H,BaseFont。NOTEMBEDDED);透明度PdfGStategsnewPdfGState();gs。setFillOpacity(0。4f);PDF文件总页数inttotalreader。getNumberOfPages()1;循环对每一页都加水印PdfContentBytecontent;for(inti1;itotal;i){水印在文本之上contentstamper。getOverContent(i);content。setGState(gs);if(null!imagePath){ImageimageImage。getInstance(imagePath);image。setAbsolutePosition(150,150);image。scaleToFit(300,300);content。addImage(image);for(intx0;x700;xx300){for(inty0;y900;yy200){image。setAbsolutePosition(x50,y50);image。scaleToFit(100,100);content。addImage(image);}}}if(null!text){content。beginText();content。setColorFill(BaseColor。RED);content。setFontAndSize(baseFont,20);content。showTextAligned(Element。ALIGNCENTER,text,50,50,45);for(intx0;x700;xx300){for(inty0;y900;yy200){水印内容和水印位置content。showTextAligned(Element。ALIGNCENTER,哈哈哈哈哈,x20,y10,30);content。showTextAligned(Element。ALIGNCENTER,LocalDateTime。now()。toString(),x,y,30);}}content。endText();}}stamper。close();reader。close();}catch(IOExceptione){thrownewRuntimeException(e);}catch(DocumentExceptione){thrownewRuntimeException(e);}}}
  跑一下TestvoidtestWatermark(){Stringsrc2D:借条2。pdf;Stringdest2D:借条3。pdf;StringimagePathD:1。jpg;PdfUtils。addWatermark(src2,dest2,哈哈哈哈哈,imagePath);}
  加完水印后效果如图
  最后,示例项目结构如图
  原文链接:https:www。cnblogs。comcjsblogp16715294。html?utmsourcetuicoolutmmediumreferral

面积2。7万亩,海口经济圈又一个片区控规出炉,居住用地约2923亩范围面积2。7万亩,海口经济圈又一个片区控规出炉,居住用地约2923亩!近年来,依托海口经济圈发展格局,定安县坚定海口都市圈卫星城城市定位,积极建设精致定安,定安社会经济发展取得稳冬春游甘肃长城边关欢乐世界畅享游线路酒泉嘉峪关肃云香庄鸿翔孔雀苑峪泉镇黄草营村嘉峪关关城里景区玉门铁人纪念馆时间3日肃州肃云香庄民宿狗吠深巷中,鸡鸣桑树颠。诗情画境的乡村环境,曾是很多人对中国传统村落的深刻记忆。历史上,岳飞的满江红怎么流传下来的?岳飞,字鹏举,南宋抗金名将,最杰出的兵马统帅,所率领的岳家军纪律严整,号称冻死不拆屋饿死不打掳。岳母刺字精忠报国,岳飞几度挥师北伐,同民间各地义军打配合,夹击金军收复失地。宋高宗绍北魏冯太后称得上超越武则天慈禧的超一流权后吗?大有学问上世纪70年代,山西省大同市博物馆和山西省文物工作委员会的考古人员对大同市北部的梁山进行了一次重要发掘,发掘对象是一座坐北朝南的庞大陵墓,也就是著名的北魏冯太后永固陵。永固日本选错方向!哪怕现在燃料电池比中国强,未来氢能车也很难赢?丰田等日系车选错发展方向?中国电动车汽车碾压性价格优势打入日本,日本哀叹没有阻止中国电动车前进的步伐。这个地球分成两个世界。一个是热衷于推行纯电动或者是作势假装要推纯电动的世界,包石油过境中国,为什么将中哈油气管道延伸到日本的计划失败了?很多中国人也许还不知道,在20多年前,中日两国曾经规划建设一条石油和天然气管道从中亚起始横跨中国北方直达日本,最后为什么没有成功实施呢?期间遇到的太多波折,且听我慢慢道来。200450岁左右的女人,尽量不要穿打底裤烫羊毛卷,其实这样打扮更美五十岁见过校服短裙的青春飞扬,也感受过有女初长成的聘聘婷婷,接下来的时光里,更不能用杂乱的发型老气的穿搭将就!打底裤羊毛卷都是绊脚石,用穿搭加分,用发型定胜负,不必再找50岁左右的马蓉的闺蜜王丽君,一个比马蓉更狠的女人2011年,50岁的刘斌三婚娶了小25岁的王丽君,却不想王丽君是马蓉的闺蜜,做的比马蓉更狠。刘斌是知名的主持人,他的一生三婚三离,一段比一段惨。刘斌的第一任妻子是史兰芽,小刘斌15婚姻里过得好的女人,大多数具有以下的几条典型特征文酸辣柠檬果在别人的眼里,王子娴是一个妥妥的异类,不在乎别人的看法,有点像王小波笔下的特立独行的猪。王子娴不属于早慧的一类人,但绝对是过早活得通透的一群人。年轻时内耗很重,成年后看56岁的日本大妈不想再为别人而活了,退休后我这样生活,更充实每个人都只有一个一生一世,要努力一点,再努力一点,为自己活一次。只要有了这样的想法,那么,不管你什么时候开始,都不算太晚。今年56岁的日本大妈就是其中的一员,曾经的她也和我们万万千继续领跑!孙颖莎三项世界排名均第一,日本张本美和双线晋级1月24日,国际乒联公布了今年第四期世界排名。国乒传来好消息,00后小将孙颖莎继续领跑3项世界排名。从公布的名单看,因近期女乒主力及主要对手缺席国际比赛,女单前十没有变化,孙颖莎名
西安古镇排名是怎样的?哪里最推荐去?要搞清楚西安古镇的排名,首先要明确西安有哪些古镇,然后才能考虑排名的问题。一西安有哪些古镇呢?1啥是古镇古镇应该包括两方面的含义,首先要古,至少得有上百年以上才能算古吧,如果没有超房地产进入寒冬,面临失业,工程人改行做什么好?1我倒不认为房地产业进入了寒冬了,前两天还有几个一线城市的相关领导出来说话,要大力新建廉租房,北上广深今后五年的廉租房建设都要达到一个新的高峰单说上海一市,预计在十四五末,将建设6在德阳工作5000元一月是什么水平?不晓得是到手5000还是应得5000,如果是前者应该超过了7080的德阳人了。德阳是个重工业城市,城里以二重东电东汽美丰等企业最为出名,工人应得工资超过5000,可他们光是公积金就如何优雅的发朋友圈旅行照片?旅行中能拍摄的实在太多了,如何优雅的发朋友圈旅行照片呢那么一步一步来,首先是交通工具,不管是自驾游开车还是坐高铁火车飞机大巴,其实这些都是非常好拍摄地点,借助丰富的自然光进行拍摄。我在农商银行工作,已年过50,应该坚持还是放弃?年过50还考虑什么放弃?按照国务院关于工人退休退职的暂行办法文件所规定的退休年龄,目前我国男性法定退休年龄为60周岁,女性法定退休年龄为50周岁,既然你都已过50周岁了,那么距离退去丰宁坝上自由行要带多少钱够了?作为草原旅游区酒店人我可以透露点秘密给你哦。太深入的不说,毕竟我在别人地盘做生意。从以下几个方面给你讲吧。1,住宿淡季是30100的,住宿看两点,1是否24小时热水器,热水器不是太你见过的最不孝顺的子女是什么样的?75岁的老父亲睡露天猪圈,唯一的心愿是吃顿肉,44岁的女儿却说吃肉可以猪圈还得继续住。而老人9岁外孙女的一个举动,让女儿无地自容。2016年的某天,成都的贺先生回老家办事时,偶然经养生站桩每天什么时间最好?养生站桩,养的是精气神,站桩养精养的是我们的丹田之精,最好是阳气旺盛的时候。遵循天道,太阳升起到太阳最高的时间点都可以,但是盛夏不要选择中午,这个时候阳气太盛,站桩反而伤身。站桩的吴梦洁被吹的神乎其神,是否有能力担任国家女排主力?江苏女排的吴梦洁,也被球迷们誉为小朱婷。与同年龄段的朱婷李盈莹相比,朱婷在19岁已经荣膺世锦赛最佳主攻,成为国家队的首发主力李盈莹在19岁之前就已经拿到了联赛的得分王。吴梦洁在排超异地恋的情侣好不容易见面了,应该如何安排一天的行程?关起门来做不可描述的事,然后睡觉,睡醒叫外卖,吃饱喝足继续做不可描述的事,然后一天就过完了,哈哈哈两个字自信,自信就好,不要担心自己会做不好。我跟我对象也是异地恋,要对明天充满信心早上起床后,空腹锻炼俯卧撑有什么好处和坏处?锻炼是一种维持健康的行为,但是任何一种行为,都要讲究时度人,不然只会适得其反!曾经接诊过一位40多岁的女病人,为了减肥,她每天坚持晨练,每次都是一起床就出去慢跑,突然有一天感觉心慌
友情链接:快好找快生活快百科快传网中准网文好找聚热点快软网