使用iTextSharp将PDF文件合并到输出流

时间:2016-11-01 23:23:22

标签: c# pdf itext

我试图以流式方式合并PDF文件(可能是1000个),这样我就不必将所有文档加载到内存中或创建一个加载到内存中的怪物输出PDF。

对于我的函数,我只是传递一个目录名,其中包含要合并的所有PDF以及要写入的输出Stream

private void MergePDFDocuments( string batchFilesFolder, Stream outputStream )
{
    using ( var batchDocument = new iTextSharp.text.Document() )
    using ( var writer = iTextSharp.text.pdf.PdfWriter.GetInstance( batchDocument, outputStream ) )
    {
        batchDocument.Open();

        var cb = writer.DirectContent;

        foreach ( var file in new DirectoryInfo( batchFilesFolder ).GetFiles( "*.pdf" ) )
        {
            // we create a reader for the document
            using ( var reader = new iTextSharp.text.pdf.PdfReader( file.FullName ) )
            {
                int i = 0;
                while ( i < reader.NumberOfPages )
                {
                    i++;
                    batchDocument.SetPageSize( reader.GetPageSizeWithRotation( 1 ) );
                    batchDocument.NewPage();

                    var page = writer.GetImportedPage( reader, i );
                    var rotation = reader.GetPageRotation( i );

                    if ( rotation == 90 || rotation == 270 )
                    {
                        cb.AddTemplate( page, 0, -1f, 1f, 0, 0, reader.GetPageSizeWithRotation( i ).Height );
                    }
                    else
                    {
                        cb.AddTemplate( page, 1f, 0, 0, 1f, 0, 0 );
                    }
                }
            }
        }
    }
}

但是,当我运行此代码时,我得到一个&#39; System.ObjectDisposedException异常:无法访问已关闭的文件。&#39;例外。这是调用堆栈。

   at System.IO.__Error.FileNotOpen()
   at System.IO.FileStream.get_Position()
   at iTextSharp.text.io.RAFRandomAccessSource.Get(Int64 position, Byte[] bytes, Int32 off, Int32 len)
   at iTextSharp.text.io.IndependentRandomAccessSource.Get(Int64 position, Byte[] bytes, Int32 off, Int32 len)
   at iTextSharp.text.pdf.RandomAccessFileOrArray.Read(Byte[] b, Int32 off, Int32 len)
   at iTextSharp.text.pdf.RandomAccessFileOrArray.ReadFully(Byte[] b, Int32 off, Int32 len)
   at iTextSharp.text.pdf.RandomAccessFileOrArray.ReadFully(Byte[] b)
   at iTextSharp.text.pdf.PdfReader.GetStreamBytesRaw(PRStream stream, RandomAccessFileOrArray file)
   at iTextSharp.text.pdf.PdfReader.GetStreamBytesRaw(PRStream stream)
   at iTextSharp.text.pdf.PRStream.ToPdf(PdfWriter writer, Stream os)
   at iTextSharp.text.pdf.PdfIndirectObject.WriteTo(Stream os)
   at iTextSharp.text.pdf.PdfWriter.PdfBody.Write(PdfIndirectObject indirect, Int32 refNumber, Int32 generation)
   at iTextSharp.text.pdf.PdfWriter.PdfBody.Add(PdfObject objecta, Int32 refNumber, Int32 generation, Boolean inObjStm)
   at iTextSharp.text.pdf.PdfWriter.AddToBody(PdfObject objecta, PdfIndirectReference refa)
   at iTextSharp.text.pdf.PdfReaderInstance.WriteAllPages()
   at iTextSharp.text.pdf.PdfWriter.AddSharedObjectsToBody()
   at iTextSharp.text.pdf.PdfWriter.Close()
   at iTextSharp.text.pdf.PdfDocument.Close()
   at iTextSharp.text.pdf.PdfWriter.Close()
   at iTextSharp.text.DocWriter.Dispose()
   at BTR.Evolution.Legacy.Jobs.BatchDocGen.MergePDFDocuments(String batchFilesFolder, Stream outputStream) in C:\BTR\Source\Evolution\BTR.Evolution\Legacy.Jobs\BatchDocGen.cs:line 598

1 个答案:

答案 0 :(得分:0)

我打赌你的参数'outputStream'已关闭。你打算两次调用这个方法吗?当您的变量“writer”被释放时,它将关闭基础流。