在Web应用中动态创建PDF文件-Java基础-Java-编程开发

深入体验Java Web开发内目-核心基础 PDF篇 前言: 当您翻开这本文的时候,几乎会很难理解它是如何经过了数千个小时的倾心写作与推敲才得以面世的。本文里的每一个字、每一条语句都是经过我长时间的思索和琢磨,我曾因用脑过度而导致一夜又一夜的失眠;曾经因长时间坐着工作,导致臀部、大腿等与凳子有接触的部位疼痛难忍,而最后只能跪着或蹲着写书;曾经因各种原因使得写作进度缓慢而使得脾气变得更加暴躁,而很少给我的妻儿温暖和关爱。正因为如此,我可以大胆地说: “本文里100%的每一句话都是经过推敲和自己辛苦‘扣’出来的! 力求达到“多一句没用,少--句不行”的效.. 阅读详情
<script type="text/javascript" src="http://pagead2.googlesyndication.com/pagead/show_ads.js"> </script>

在一个最近的后勤项目中,客户要求我们建一个能让用户能从一个遗留系统查询出货信息的Web站点,有三个主要的需求:
1.出货信息必须以PDF文档的格式返回;
2.PDF文件必须能通过浏览器下载;
3.PDF文件必须能用Adobe Acrobat Reader阅读;
尽管我们的团队有很多J2EE Web应用的开发经验,但在PDF文档处理上却没有多少经验。我们需要找一个能在服务器端Web应用里产生复杂的PDF文档的纯Java类库。最后,我们发现iText(http://www.lowagie.com/iText/)能完全满足我们的需要。

1.iText类库

iText是一个创建和处理PDF文档的开源纯Java类库。Bruno Lowagie和Paulo Soares领导着这个项目。IText API能让Java开发人员以编程的方式创建PDF文档。iText提供了很多的特性:

支持PDF和FDF文档

各种页面尺寸

横向和竖向布局

页边距

表格

断字

页头

页脚

页码

条形码

字体

颜色

文档加密

JPEG,GIF,PNG和WMF图片

有序和无序列表

阴影

水印

文档模板
iText是一个开源库。在写本文的时候,iText可以在两个许可协议下使用:Mozilla Public License和LGPL。如果想了解详细信息,请参考iText站点。在本文中,你将会看到iText API的应用。我们将阐述如何在服务器端应用中使用iText和servlet动态生成PDF文档。

2.开始(Getting Started)

首先,你需要一个iText Jar文件。访问iText站点并下载最新的版本。在写本文时,最新的版本是使0.99。iText站点提供了API文档和一个全面的指南。
除了iText,我们还要用servlet.如果你不熟悉servlet,你可以通过Jason Hunter的书《Java Servlet Programming》来学习它。你需要一个J2EE应用服务器或可以独立运行的servlet引擎。开源软件Tomcat,Jetty和Jboss是不错的选择。下文假设你使用的是Jakarta Tomcat 4.1。

1.iText API

iText API简单易用。通过使用iText,你能创建自定义的PDF文档。iText库由下边的一些包组成:

com.lowagie.servlets
com.lowagie.text
com.lowagie.text.html
com.lowagie.text.markup
com.lowagie.text.pdf
com.lowagie.text.pdf.codec
com.lowagie.text.pdf.hyphenation
com.lowagie.text.pdf.wmf
com.lowagie.text.rtf
com.lowagie.text.xml
com.lowagie.tools
为了生成PDF文件,你只需要com.lowagie.text和com.lowagie.text.pdf两个包。
我们的例子使用了这些iText类:
com.lowagie.text.pdf.PdfWriter
com.lowagie.text.Document
com.lowagie.text.HeaderFooter
com.lowagie.text.Paragraph
com.lowagie.text.Phrase
com.lowagie.text.Table
com.lowagie.text.Cell
关键的类是Document和PdfWriter。在创建PDF文档时,你将经常使用这两个类。Document是PDF文档基于对象的描述。你可以通过调用Document类提供的方法往文档中加入内容。PdfWriter对象通过java.io.OutputStream对象与Document关联在一起。

3.在Web应用中使用iText

在设计阶段,你必须决定如何使用iText。我们使用了下边的技术开发了我们的Web应用。

1.A技术

在服务器文件系统上创建PDF文件。应用使用java.io.FileOutputStream把文件写到服务器文件系统上。用户通过HTTP GET方法下载该文件。

2.B技术

使用java.io.ByteArrayOutputStream在内存中创建PDF文件。应用通过servlet的输出流将该PDF文件字节发送到客户端。
由于应用不需要把文件写到文件系统上,这样能保证在集群服务环境中能正常工作,所以我更倾向于使用B技术。如果你的应用运行在集群环境中且服务器集群不提供会话亲和的功能,A技术可能会导致失败。

3.例子:PDFServlet

我们的例子应用由一个类组成:PDFServlet。这个servlet采用B技术。输出流OutputStream是java.io.ByteArryOutputStream。用ByteArrayOutputStream,PDF文档字节将存储在内存中。当PDFServlet接收到一个HTTP请求时,它将动态地生成一个PDF文档并将该文档发送到客户端。
PDFServlet类扩展了javax.servlet.http.HttpServlet类并导入了两个iText包:com.lowagie.text和com.lowagie.text.pdf。
doGet方法
大多数servlet覆盖了doPost和doGet方法中的一个方法。我们的servlet没有什么不同。PDFServlet类覆盖了doGet方法。该servlet将在接收到HTTP GET请求后生成一个PDF文件。
在核心部分,servlet的doGet方法做了如下的工作:
1.创建一个包含PDF文档字节的ByteArrayOutputStream对象;
2.在reponse对象上设置HTTP响应头内容;
3.得到servlet输出流;
4.把文档字节写到servlet的输出流中;
5.刷新servlet输出流;
generatePDFDocumentBytes方法
generatePDFDocumentBytes方法负责创建PDF文档。在这个方法中三个最重要的对象是Document对象,ByteArrayOutputStream对象和PdfWriter对象。PdfWriter使用ByteArrayOutputStream关联Document。

Document doc = new Document();
ByteArrayOutputStream baosPDF = new ByteArrayOutputStream();
PdfWriter docWriter = null;
docWriter = PdfWriter.getInstance(doc, baosPDF);
// ...
用add方法把内容添加到Document中。
doc.add(new Paragraph(
"This document was created by a class named: "
this.getClass().getName()));

doc.add(new Paragraph(
"This document was created on "
new java.util.Date()));

当你添加完内容后,要关闭Document和PdfWriter对象。
doc.close();
docWriter.close();
当关闭文档后,ByteArrayOutputStream对象返回到调用者。
return baosPDF;
ByteArrayOutputStream包含了PDF文档的所有字节。
HTTP响应头
在这个应用中,我们仅仅关注四个HTTP 响应头:Content-type,Content-disposition,Content-length,和Cache-control。如果你从没有使用过HTTP头,请参考HTTP 1.1规范。
研究在PDFServlet中的doGet方法,你会注意到要在任何数据写到servlet输出流之前设置HTTP响应头内容,这是很重要的,也是细微的一点。
让我们更详细地说明一下每个响应头的含义。
Content-type
在servlet中,HttpServletResponse有一个表明响应所包含内容类型的参数。对PDF文件而言,内容类型是application/pdf。如果servlet没有设置类型,web浏览器很难决定如何处理这个文件。
PDFServlet用下边的代码设置内容类型:
resp.setContentType("application/pdf");
Content-disposition
Content-disposition头提供给浏览器确定HTTP响应内容的信息。当浏览器读到这些头信息后,它能确定:

HTTP响应包含一个文件;

包含在响应中的文件名;

该文件是显示在浏览器主窗口中还是要用外部的应用查看;
RFC 2183中有对Content-disposition头完整的解释。
通过合适地设置Content-disposition的值,servlet能指示浏览器是“内嵌”显示文件还是把它当作附件处理。
例1.内嵌显示一个文件
Content-disposition: inline; filename=foobar.pdf
例2.往response里附加一个文件

Content-disposition: attachment; filename=foobar.pdf
下边的伪码说明了如何设置头信息:
public void doGet(HttpServletRequest req, HttpServletResponse resp)
{
// ...
resp.setHeader(
"Content-disposition",
"inline; filename=foobar.pdf" );
// ...
}
Cache-Control
根据你应用的特性不同,你可以让浏览器缓存或者不缓存你正在生成的PDF文件。服务器端应用可以有很多种HTTP 头来控制内容缓存。下边是一些例子:

Cache-Control: no-cache

Cache-Control: no-store

Cache-Control: must-revalidate

Cache-Control: max-age=30

Pragma: no-cache

Expires: 0
关于Cache-Control头的全面解释见HTTP 1.1规范。
PDFServlet把Cache-Control设置为max-age=30。这个头信息告诉浏览器缓存这个文件的最长时间为30秒。
Content-length
Content-length头必须设置成PDF文件中字节的数值。如果Content-length没有设置正确,浏览器可能不能正确地显示该文件。下边是例子代码:

ByteArrayOutputStream baos = getByteArrayOutputStream();
resp.setContentLength(baos.size());
把PDF文档送到Web浏览器
PDFServlet通过把字节流写到servlet的输出流的方式把PDF文档送到客户端。它通过调用HttpServletResponse对象的getOutputStream方法来获得输出流。getOutputStream方法返回一个javax.servlet.ServletOutputStream类型的对象。
ServletOutputStream sos;
sos = resp.getOutputStream();
baos.writeTo(sos);
sos.flush();
在把所有的数据写到流之后,调用flush()方法把所有的字节发送到客户端。
打包和部署
为了在Tomcat中运行PDFServlet,你需要把应用打包在WAR文件中。iText JAR文件(itext-0.99.jar)必须放在WAR文件的lib目录下边。如果你忘了把iText JAR文件打包进去,servlet会报一个java.lang.NoClassDefFoundError的错误并停止运行。
运行应用
在WAR文件部署之后,你已经准备好了测试servlet了。Jakarta Tomcat在8080端口上监听请求。
在浏览器中请求http://hostname:8080/pdfservlet/createpdf。servlet将会执行并返回浏览器一个PDF文档。

4.iText之外的方案

iText提供了许多产生PDF文档的底层API。然而,它不是对任何应用都有效。
在我的日常工作中,我结合Microsoft Word和Adobe Acrobat使用iText。首先,我们的团队使用Microsoft Word设计了一个出货表单。之后,我们用Acrobat把Word文档转换成PDF文档。然后,我们使用iText的模板的功能,我们把PDF文件装入到我们的应用中。从这里,把数据填入表格和输出最终的PDF文档是相当容易的。
对基于报表的Web应用,像JasperReports这样的工具,它提供了比iText更高层次的抽象。

5.总结

当你的应用需要动态地创建PDF文档的时,iText类库是一个不错的方案。你可以通过增强和扩展本文中的代码来体验iText的能力。很快,由于提供了完善的PDF文档,你将会给你的同事和客户留下深刻的印象。

6.其他资源

http://www.lowagie.com/iText/
www.jpedal.org
www.pdfbox.org
xml.apache.org/fop
HTTP 1.1 protocol specification
RFC 2183
dmoz.org/Computers/Data_Formats/Document/Publishing/PDF
www.planetpdf.com
www.pdfzone.com

Web网页、HTML 、 XML、SVG等转换为 PDF 文件,速度快质量高,C#、C++、Python、Node、Java、PHP等实现 HTML(html)文档转pdf文档,web端网页转pdf, XML、SVG等转换为 pdf 文件,速度快、质量高,实现方式简单,快速上手实现,支持多变成语言的使用包含(C#、C++、Python、Node、Java、PHP等); 阅读详情

相关推荐

Java Web开发基础教程(PDF版)

本文还有配套的精品资源,点击获取 简介:Java Web开发是使用Java语言进行服务器端Web应用开发的编程分支。本PDF教程为初学者提供全面基础起点,包含Servlet和JSP核心,MVC设计模式,JDBC数据库连接,EJB企业级应用,JPA简化数据库操作,Spring框架,Struts和Hibernate框架,Tomcat和Jetty服务器,前端技术HTML/CSS/...

weixin_42298254的博客 2263

Java Web应用动态生成PDF文件的问题整理

Java Web应用在给浏览器返回动态生成的PDF文件时,要确保发送的HTTP header消息中正确设置了相应参数,否则浏览器可能无法获取到或者获取到错误的PDF文件。整理了下这些参数的设置方法,还有遇到的一些问题,记录下来避免以后再走弯路。

问题,总是可以解决滴 5219

JavaScript性能优化:全链路性能优化策略

JavaScript性能优化是提升Web应用质量的核心要素,直接影响用户体验与业务成果。研究表明,页面加载延迟1秒可能导致转化率下降7%。高效的JavaScript执行能减少主线程阻塞,避免动画卡顿或操作延迟,尤其在移动端低性能设备上更为关键。优化内存管理与减少冗余计算可降低浏览器资源消耗,防止因内存泄漏导致的崩溃,提升应用稳定性。在竞争激烈的互联网环境中,性能优势已成为产品差异化的关键因素,直接影响用户留存与商业价值。因此,性能优化应作为开发全周期的核心实践,而非事后补救措施。

weixin_49707375的博客 1270

在Web应用中动态创建PDF文件

在Web应用中动态创建PDF文件 gagaghost 翻译  (参与分:104,专家分:230)   发表:2004-9-15 下午6:33   版本:1.0   阅读:885次 在Web应用中动态创建PDF文件原文:Sean C. Sullivan    翻译:gagaghost  在一个最近的后勤项目中,客户要求我们建一个能让用户能从...

weixin_34146805的博客 260

2024广东省职业技能大赛云计算——集群部署GitLab

题目是这样的:在Kubernetes集群中新建命名空间gitlab-ci,将GitLab部署到该命名空间下,Deployment和Service名称均为gitlab,以NodePort方式将80端口对外暴露为30880,设置GitLab服务root用户的密码为admin@123,将项目包demo-2048.tar.gz导入到GitLab中并命名为demo-2048。GitLab是一个功能强大且灵活的 DevOps 平台,为开发团队和企业提供了从代码管理到持续集成、交付和部署的一整套解决方案。

kuuuugua的博客 4395

RTKLIB PPP与RTK_POST精密定位实战:从实时到事后处理的完整流程解析

本文详细解析了如何使用RTKLIB进行精密单点定位(PPP)的完整流程,涵盖从实时处理到事后处理(RTK_POST)的关键步骤。文章深入探讨了数据准备、软件配置、核心参数设置(如电离层、对流层、潮汐改正)以及常见问题排查,旨在帮助用户掌握高精度GNSS定位技术,实现从入门到精通的实战应用。

weixin_29047919的博客 279

关于 com.lowagie.text 报错的问题

首先项目中没有加入com.lowagie.text的依赖(非maven项目看lib目录有没有itext.jar包),需要自己添加相应jar包或依赖, 到maven repositury下载lowagie相关的jar包是需要注意版本信息, 第一次下载的5.5.13版本的,jar包提示是com.itextpdf..xxxx,和项目需要的com.lowagie.text不对,重新搜索lowagie之后发现还有其他版本 重新选择下载次数最多的2.1.7的包导入后显示的是com.lowagie.text..

qq_26582185的博客 5945

MATLAB与STK互联23:卫星对象操作(14)—仿真分析案例1,建立8个地面站,分析对卫星的可见性

学习到这里,我们有必要做个仿真分析案例,把之前我们学习的零散知识点串起来,看一下在真实的分析中怎么应用。 分析要求:建立8个地面站,分析每个地面站对某个轨道高度500km、倾角60°圆轨道的卫星,1天内的可见次数、可见弧长以及可见弧段间隔列表。 基本约束:地面站仰角8°~90°,作用距离<2000km,太阳矢量与地面站到卫星视线夹角不小于15°,可见弧段应大于30s。地面站站址可随机生成,但要求在南北纬50°范围内。 下面上代码: uiap = actxserver(‘STK11.application’)

ltylty001的博客 7491

PDF生成工具类(copy 代码直接可用)

import java.awt.Color; import java.io.BufferedOutputStream; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.OutputStream; import java.io.StringWriter; ...

hxwjilin的博客 1974

利用NURBS曲线进行点云曲面拟合算法

点云拟合曲面算法是将点云数据拟合成一个二次或高次曲面模型的算法。这种算法主要用于三维模型重建、计算机视觉、机器人感知、医学图像处理等领域。最小二乘法(Least Squares Method):通过最小化点到曲面距离的平方和来拟合曲面模型。三角剖分算法(Triangulation-Based Method):将点云构建成三角网格,再拟合成曲面模型。隐式曲面算法(Implicit Surface Method):通过定义一个隐式函数来表示曲面,然后用点云数据来估计隐式函数的系数。

weixin_44770969的博客 1万+

大模型之Spring AI实战系列(二十六):Spring Boot + DeepSeek 实战指南:构建AI聊天应用

在人工智能技术飞速发展的今天,大型语言模型已经成为了推动技术创新的重要力量。DeepSeek作为国内领先的大型语言模型提供商,其推出的DeepSeek系列模型在多个领域都展现出了卓越的性能。本文将详细介绍如何使用Spring Boot框架集成DeepSeek API,构建一个简单的AI聊天应用。我们将实现两个核心功能:普通文本生成和流式文本生成。

寻道AI,探索AI无限可能! 2264

总结之使用lowagie.text添加PDF水印

引入依赖 <!-- pdf水印 --> <dependency> <groupId>com.lowagie.text</groupId> <artifactId>com.springsource.com.lowagie.text</artifactId> <version>${com.lowagie.text.version}</version> </dependency

IManiy的博客 4102

基于深度学习YOLOv8的商品识别系统(深度学习 + UI界面 + 训练数据集 + Python代码)

如果使用自定义数据集,可以通过图像标注工具如LabelImg来标注每个商品的类别和边界框,并保存为YOLO格式的文本文件。bash复制编辑/dataset/images/train/val/labels/train/val这样,我们就准备好了数据集,可以开始训练YOLOv8模型。本文介绍了如何使用YOLOv8构建一个商品识别系统,包括从数据准备到模型训练,再到UI界面的开发。通过深度学习技术,尤其是YOLOv8的高效目标检测能力,我们能够快速实现商品识别并集成到实际应用中。

YOLO 302

java jsp动态生成pdf_在Web应用中动态创建PDF文件

在Web应用中动态创建PDF文件原文:SeanC.Sullivan翻译:gagaghost在一个最近的后勤项目中,客户要求我们建一个能让用户能从一个遗留系统查询出货信息的Web站点,有三个主要的需求:1.出货信息必须以PDF文档的格式返回;2.PDF文件必须能通过浏览器下载;3.PDF文件必须能用AdobeAcrobatReader阅读;尽管我们的团队有很多J2EEWeb应用的开...

weixin_39525300的博客 299

[QMT量化交易小白入门]-七十三、主力资金动向:板块与个股资金流数据API(量化python代码解析)

本专栏主要是介绍QMT的基础用法,常见函数,写策略的方法,也会分享一些量化交易的思路,大概会写100篇左右。QMT的相关资料较少,在使用过程中不断的摸索,遇到了一些问题,记录下来和大家一起沟通,共同进步。

木头大左的博客 1115

复分析 阿尔福斯(Ahlfors) 第三版答案 英文

答案分为十章,有部分习题没有答案,全英文复分析阿尔福斯(Ahlfors) 第三版答案

如何在WEB应用中动态创建PDF文件

如何在WEB应用中动态创建PDF文件时间: 2006-04-22 12:55:33 | [ [>>] 作者:itzealot 发文时间:2006.04.18 来源:赛迪博客  在一个最近的后勤项目中,客户要求我们建一个能让用户能从一个遗留系统查询出货信息的Web站点,有三个主要的需求:  1.出货信息必须以PD

hcx_2008的专栏 999

老版QQ原生表情gif动态

这是老版的QQ表情,不过全是动态的的,Windows照片查看器是不会动的,可以右击用浏览器打开查看,再说一遍是老版的,只是分享给宁愿用老版也要动态的人。

Python Web 开发中 Excel 转 PDF 文件

Python web java pdf

chenhaiy的博客 729

jre9下载 jdk9

(Java SE Runtime Environment 9.0) 9.0u175 官方最新版 【x86|x64】

精雕软件(JDpaint) 5.5 绿色版

精雕软件(JDpaint) 5.5 绿色版精雕软件(JDpaint) 5.5 绿色版精雕软件(JDpaint) 5.5 绿色版

《Java高手真经_编程基础卷:Java核心编程技术》(JAVA开发专家)扫描版[PDF]

编辑推荐 本书详细讲解Java语言基础开发中的各种技术,主要内容包括如下。   ·Java开发入门:JDK、JVM、Eclipse、Linux。   ·Java语法基础:类、抽象类、接口、内部类、匿名类、异常、编码规范。   ·Java核心编程:流、多线程、实体类、集合类、正则表达式、XML、属性文件。   ·Java网络编程:Applet、Sockt/TCP/UDP、NIO、RMI

闹腾的外行 1930

java集成pdf.js实现pdf文件在线预览

最近项目需要实现在线预览pdf文件功能,找来找去,发现有个pdf.js的类库挺好用,直接用js实现在线预览。 pdf.js是开源项目,github的地址: https://github.com/mozilla/pdf.js 根据教程指引,有以下几个步骤: - clone源码到本地,如果是linux的话很方便,windows的话要另外下载git工具; git地址:https://git-fo

wang704987562的博客 3万+

【java】web在线打开PDF文件

项目中用java实现,当用户点击那个pdf链接时,不弹出下载提示框,而是以网页的形式打开这个pdf。1.前端有一个&lt;a&gt;标签,当点击事件发生之后要把文件所在的路径传到后台2.后台代码如下    @RequestMapping("showPhoto.do")    public String getpic(String path, HttpServletRequest request,...

qq_37359047的博客 6070

《python编程基础及应用》,python编程基础及应用pdf

1.range和xrange都是在循环中使用,输出结果一样。2.range返回的是一个list对象,而xrange返回的是一个生成器对象(xrange object)。3.xrange则不会直接生成一个list,而是每次调用返回其中的一个值,内存空间使用极少,因而性能非常好。注意:Python 3.x已经去掉xrange,全部用range代替。

2301_81900494的博客 995
上一篇: Java学习从入门到精通 1工具篇-Java基础-Java-编程开发
下一篇: Java学习从入门到精通 3过程篇-Java基础-Java-编程开发
java169
博客等级 码龄18年 27粉丝 2568原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值