当前位置: 首页 > news >正文

利用apache-pdfbox库修改pdf文件模板,进行信息替换

public String createSignFile(Long id) throws IOException {// 1.验证企业信息CompanyDO company = validateCompanyExists(id);// 2.验证签约状态if(company.getSignStatus()!=0){throw exception(COMPANY_SIGN_STATUS_NOT_ZERO);}// 3.获取合同模板(合同模板有独立模板管理板块)String enterType = company.getEnterCompanyType()==1?"franchisee_enter":"service_provider_enter";AgreementRespDTO agreementDTO = operateAgreementApi.getAgreementByType(enterType);if(agreementDTO==null){throw exception(COMPANY_AGREEMENT_NOT_EXISTS);}String templatePath = agreementDTO.getFile();// 4.设定合同参数SimpleDateFormat sdf = new SimpleDateFormat("yyyy年MM月dd日");String currentDate = sdf.format(new Date());Map<String, String> data = new HashMap<>();data.put("companyName", company.getName());data.put("secrecyInfo", "无");data.put("yearLimit", "一");data.put("StartDate", currentDate);// 5.生成合同文件// 5.1加载 pdf 模板和字体库文件//适用于本地资源路径(本地用于调试,信息为e:/file.pdf)
//        FileInputStream fis = new FileInputStream(templatePath);// 采用网络资源路径(系统中采用oss对象存储,所以获取的是网络路径)URL url = new URL(templatePath);URLConnection connection = url.openConnection();InputStream fis = connection.getInputStream();// 字体文件【华文仿宋】,可以自己换字体库URL fontUrl = new URL("https://你自己的地址.oss-cn-beijing.aliyuncs.com/stfangso.ttf");URLConnection fontConnection = fontUrl.openConnection();InputStream fontFile = fontConnection.getInputStream();// 开始读取//============ pdf 文件读取处理 ===============PDDocument pdf = PDDocument.load(fis);Map<COSName, PDFont> oldfont = new HashMap<COSName, PDFont>();COSName fontName = null;PDType0Font targetfont= PDType0Font.load(pdf,fontFile);for (PDPage page : pdf.getPages()) {PDFStreamParser pdfsp = new PDFStreamParser(page);pdfsp.parse();List<Object> tokens = pdfsp.getTokens();for (int j = 0; j < tokens.size(); j++) {//创建一个object对象去接收标记Object next = tokens.get( j );//instanceof判断其左边对象是否为其右边类的实例if(next  instanceof COSName) {fontName= (COSName)next;if(!oldfont.containsKey(fontName)) {oldfont.put(fontName, page.getResources().getFont(fontName));}}elseif(next  instanceof COSString) {COSString previous = (COSString)next;try(InputStream in = new ByteArrayInputStream(previous.getBytes())){StringBuffer sb = new StringBuffer();while (in.available()>0) {int rc = oldfont.get(fontName).readCode(in);sb.append(oldfont.get(fontName).toUnicode(rc));}//重置COSString对象previous.setValue(targetfont.encode(sb.toString()));}}else if(next  instanceof COSArray) {//PDF中的字符串byte[] pstring = {};int prej = 0;COSArray previous  =(COSArray)next;
//                    //循环previousfor (int k = 0; k < previous.size(); k++) {Object arrElement = previous.getObject( k );if( arrElement instanceof COSString ){//COSString对象>>创建java字符串的一个新的文本字符串。COSString cosString =(COSString)arrElement;//将此字符串的内容作为PDF文本字符串返回。if (j == prej) {byte[] thisbyte = cosString.getBytes();byte[] temp = new byte[pstring.length+thisbyte.length];System.arraycopy(pstring, 0, temp, 0, pstring.length);System.arraycopy(thisbyte, 0, temp, pstring.length, thisbyte.length);pstring=temp;} else {prej = j;pstring = cosString.getBytes();}}}try(InputStream in = new ByteArrayInputStream(pstring)){StringBuffer sb = new StringBuffer();while (in.available()>0) {int rc = oldfont.get(fontName).readCode(in);sb.append(oldfont.get(fontName).toUnicode(rc));}String str =sb.toString();for (Map.Entry<String, String> entry : data.entrySet()) {String key = "${" + entry.getKey() + "}";if (str.contains(key)) {str = str.replace(key, entry.getValue() != null ? entry.getValue() : "");break;}}COSString cosString2 = (COSString) previous.getObject(0);cosString2.setValue(targetfont.encode(str));}int total = previous.size()-1;for (int k = total; k > 0; k--) {previous.remove(k);}}}PDStream updatedStream = new PDStream(pdf);OutputStream out = updatedStream.createOutputStream();ContentStreamWriter tokenWriter = new ContentStreamWriter(out);tokenWriter.writeTokens(tokens);out.close();oldfont.forEach((k,v)->{page.getResources().put(k, targetfont);});page.setContents(updatedStream);}//保存到本地中(主要用于调试)//pdf.save("d:/1.pdf");//pdf.close();//将文件直接保存上传(由于生成后,前台展示所以要直接上传获取上传地址进行前台回显)ByteArrayOutputStream out = new ByteArrayOutputStream();pdf.save(out);pdf.close();//记得关闭资源哦// 将输出流的内容转换为Base64编码的字符串byte[] bytes = out.toByteArray();String pdfUrl =fileApi.createFile(bytes);// 将上传后的文件,存到数据库中companyMapper.updateById(new CompanyDO().setId(id).setSignFileUrl(pdfUrl));return pdfUrl;}

该板块主要用于利用模板生成入驻企业的合同信息,便于在线发起合同签署功能。
采用了模板的变量替换方式,需要将变量信息预先插入到模板的指定位置。

相关文章:

  • 北京网站建设多少钱?
  • 辽宁网页制作哪家好_网站建设
  • 高端品牌网站建设_汉中网站制作
  • 【C++高阶】解锁C++的深层魅力——探索特殊类的奥秘
  • JVM面试真题总结(八)
  • 2024年华为9月4日秋招笔试真题题解
  • pdf文件转图片,base64或保存到本地
  • Linux 离线安装 Docker
  • 网络插件 Cilium 更换 Calico
  • 产品经理如何转型为AI产品经理,如何理解AI产品工程化
  • [产品管理-2]:产品经理的职责、在企业中的位置与定位
  • 加入图书页面以及和图片相关的viewmodel代码
  • CSS学习18--伸缩布局
  • io_uring异步IO
  • TDengine 与飞腾腾锐 D2000 完成兼容互认证,推动国产软硬件深度融合
  • Azkaban、oozie、airflow、dolphinschduler 对比分析
  • Jupyter Notebook远程登录配置
  • 前端用html写excel文件直接打开
  • $translatePartialLoader加载失败及解决方式
  • 【翻译】Mashape是如何管理15000个API和微服务的(三)
  • AzureCon上微软宣布了哪些容器相关的重磅消息
  • const let
  • happypack两次报错的问题
  • java中的hashCode
  • learning koa2.x
  • leetcode讲解--894. All Possible Full Binary Trees
  • Python socket服务器端、客户端传送信息
  • windows下如何用phpstorm同步测试服务器
  • 第2章 网络文档
  • 反思总结然后整装待发
  • 记一次删除Git记录中的大文件的过程
  • 京东美团研发面经
  • 理解在java “”i=i++;”所发生的事情
  • 排序(1):冒泡排序
  • 小而合理的前端理论:rscss和rsjs
  • 学习Vue.js的五个小例子
  • 原生 js 实现移动端 Touch 滑动反弹
  • 3月27日云栖精选夜读 | 从 “城市大脑”实践,瞭望未来城市源起 ...
  • 阿里云服务器如何修改远程端口?
  • 国内开源镜像站点
  • 如何在 Intellij IDEA 更高效地将应用部署到容器服务 Kubernetes ...
  • ​​​​​​​GitLab 之 GitLab-Runner 安装,配置与问题汇总
  • ​​​​​​​开发面试“八股文”:助力还是阻力?
  • ​flutter 代码混淆
  • ​MySQL主从复制一致性检测
  • #APPINVENTOR学习记录
  • (php伪随机数生成)[GWCTF 2019]枯燥的抽奖
  • (阿里云在线播放)基于SpringBoot+Vue前后端分离的在线教育平台项目
  • (二)windows配置JDK环境
  • (二十九)STL map容器(映射)与STL pair容器(值对)
  • (十一)图像的罗伯特梯度锐化
  • (一)SvelteKit教程:hello world
  • (转)【Hibernate总结系列】使用举例
  • (转)es进行聚合操作时提示Fielddata is disabled on text fields by default
  • (转载)hibernate缓存
  • .a文件和.so文件
  • .dat文件写入byte类型数组_用Python从Abaqus导出txt、dat数据
  • .gitignore文件_Git:.gitignore