【问题标题】:Merge PDF using iText and save as stream on client side使用 iText 合并 PDF 并在客户端另存为流
【发布时间】:2015-10-29 16:48:34
【问题描述】:

我尝试使用我在这里找到的代码 http://web.archive.org/web/20111012184438/http://alex.buayacorp.com/merge-pdf-files-with-itext-and-net.html 将 2 个或多个 PDF 文件合并为一个。

我想实现输出作为流返回并保存在客户端。我试图修改代码但没有成功。该代码尝试将输出保存在服务器上,然后导致未经授权的访问异常。 谁有正确的线索?


private void MergePDFs()
{
    DataSourceSelectArguments args = new DataSourceSelectArguments();
    DataView view = (DataView)SqlDataSource1.Select(args);

    DataTable table = view.ToTable();
    List<PdfReader> readerList = new List<PdfReader>();

    foreach (DataRow myRow in table.Rows)
    {
        PdfReader pdfReader = new PdfReader(Convert.ToString(myRow[0]));
        readerList.Add(pdfReader);
    }

    Document document = new Document();
    PdfCopy copy = new PdfCopy(document, Response.OutputStream);
    document.Open();

    foreach (PdfReader reader in readerList)
    {
        for (int i = 1; i <= reader.NumberOfPages; i++)
        {
            copy.AddPage(copy.GetImportedPage(reader, i));
        }
    }

    document.Close();
    Response.AppendHeader("content-disposition", "inline; filename=OutPut.pdf");
    Response.ContentType = "application/pdf";
}

【问题讨论】:

  • 我尝试修改代码 - 您是否尝试将 FileStream 替换为响应流(或 MemoryStream,您最终将其内容复制到响应中流)?` 有人问,您找到的代码是一个示例,说明 not 通常如何合并 PDF。使用与PdfCopy 配合使用的代码。
  • 我尝试了响应流和内存流,但作为一个新手我没有成功。它让我对你所说的代码感到困惑,而不是用于合并 PDF。似乎正是为了这个目的!?
  • 似乎正是为了这个目的!? - 是的,但它是以错误的方式完成的。详情请查看this answer

标签: c# .net pdf itextsharp


【解决方案1】:

您似乎正在使用 OutputStream 将 PDF 字节作为文件写入服务器磁盘。这通常是您在 Web 应用程序中不想要的。在 Web 应用程序中,您希望将字节写入 Response 对象,如iTextSharp generated PDF: How to send the pdf to the client and add a prompt? 的答案中所述

常识会告诉您,最好将字节直接写入ResponseOutputStream,但经验告诉我们,并非所有浏览器都能正确处理这些字节。最好先将 PDF 写入MemoryStream(如Create PDF in memory instead of physical file 中所述)。一旦你在内存中有字节,那么你可以将字节刷新到Response对象设置正确的HTTP标头(尤其是ContentLength对于某些人来说很重要浏览器)。

很明显,您不能在未经用户同意的情况下将字节写入客户端,例如因为

  1. 这会带来安全隐患。浏览器不应允许服务器将任何内容写入最终用户的磁盘。
  2. 您不知道最终用户的文件系统的组织结构(并非每台计算机都有C: 驱动器)。

如果您希望最终用户保存 PDF,您应该使用以下 HTTP 标头:

Response.AddHeader("Content-Disposition", "attachment; filename=yourfile.pdf");

想了解更多信息吗?阅读How To Write Binary Files to the Browser Using ASP.NET and Visual C# .NET

额外的建议:请帮我一个忙,不要使用糟糕的 iTextSharp 示例。合并 PDF 使用 PdfCopy 完成,NOT 使用 PdfWriter。下载免费电子书The Best iText Questions on StackOverflow,您将节省大量时间 (1.) 寻找答案和 (2.) 避免错误答案。

【讨论】:

  • 感觉就像在 Excel 上提问,盖茨先生在回答自己!你在这里很活跃——太好了!我花了一段时间才理解这些例子。没有太深入,我发现在示例中您使用的参考文献比我使用的参考文献更令人困惑 - 但我想这只是由于我缺乏知识。最后我成功地让它工作了。代码贴在上面。我现在面临的问题是在合并大约 300 个 PDF 时出现“System.OutOfMemoryException”错误。我读到我可以写入 FileStream 以减少内存影响,但在语法上遇到了问题
  • 您应该确保在执行操作时释放一些内存。例如:我从来没有看到你在任何地方做reader.Close()
猜你喜欢
  • 2015-12-23
  • 1970-01-01
  • 1970-01-01
  • 2019-03-28
  • 2012-04-23
  • 1970-01-01
  • 2015-08-17
  • 2015-12-02
相关资源
最近更新 更多