itextsharp没有关闭文件

问题描述 投票:1回答:5

我有一些代码用于itextsharp合并2个pdf文件。在某处找到它。合并工作正常,但似乎源文件在完成后仍保持使用状态。我想要做的是删除我已合并的第一个文件,该文件通过fileupload上传,并仅保留合并文件。这肯定是进行合并的代码导致文件保持打开状态。我试图删除服务器上的文件,它告诉我IIShelper打开的东西。通过几个小时的工作,我缩小到这个东西。为什么要保留文件?

    public static void MergeFiles(string destinationFile, string[] sourceFiles)
    {

        int f = 0;
        // we create a reader for a certain document
        PdfReader reader = new PdfReader(sourceFiles[f]);
        // we retrieve the total number of pages
        int n = reader.NumberOfPages;
        // step 1: creation of a document-object
        Document document = new Document(reader.GetPageSizeWithRotation(1));
        // step 2: we create a writer that listens to the document
        PdfWriter writer = PdfWriter.GetInstance(document, new FileStream(destinationFile, FileMode.Create));
        // step 3: we open the document
        document.Open();
        PdfContentByte cb = writer.DirectContent;
        PdfImportedPage page;
        int rotation;
        if(reader.IsEncrypted() == false)
        {
            // step 4: we add content
            while (f < sourceFiles.Length)
            {
                int i = 0;
                while (i < n)
                {
                    i++;
                    document.SetPageSize(reader.GetPageSizeWithRotation(i));
                    document.NewPage();
                    page = writer.GetImportedPage(reader, i);
                    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);
                    }
                }
                f++;
                if (f < sourceFiles.Length)
                {
                    reader = new PdfReader(sourceFiles[f]);
                    // we retrieve the total number of pages
                    n = reader.NumberOfPages;
                }

            }
        }
        else
        {
            //is encrypted
        }
        // step 5: we close the document
        document.Close();
        reader.Close();
        reader.Dispose();


    }

提前致谢

asp.net itextsharp
5个回答
3
投票

你最后只关闭一个reader,但每个文件打开一个阅读器。因此,只有最后一个reader将被关闭。

你需要先关闭旧读者

    reader = new PdfReader(sourceFiles[f]);

1
投票

好的,这就是我最终的结果。

    public static void MergeFiles(string destinationFile, string[] sourceFiles)
    {

        int f = 0;
        // we create a reader for a certain document
        //PdfReader reader = new PdfReader(sourceFiles[f]);
        PdfReader reader = new PdfReader(new RandomAccessFileOrArray(sourceFiles[f], true), null);
        if (reader.IsEncrypted() == false)
        {
            // we retrieve the total number of pages
            int n = reader.NumberOfPages;
            // step 1: creation of a document-object
            Document document = new Document(reader.GetPageSizeWithRotation(1));
            // step 2: we create a writer that listens to the document
            using(var destinationFileStream = new FileStream(destinationFile, FileMode.Create))
            {
                PdfWriter writer = PdfWriter.GetInstance(document, destinationFileStream);
                // step 3: we open the document
                document.Open();
                PdfContentByte cb = writer.DirectContent;
                PdfImportedPage page;
                int rotation;

                    // step 4: we add content
                    while (f < sourceFiles.Length)
                    {
                        int i = 0;
                        while (i < n)
                        {
                            i++;
                            document.SetPageSize(reader.GetPageSizeWithRotation(i));
                            document.NewPage();
                            page = writer.GetImportedPage(reader, i);
                            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);
                            }
                        }
                        f++;
                        if (f < sourceFiles.Length)
                        {

                            reader = new PdfReader(sourceFiles[f]);
                            // we retrieve the total number of pages
                            n = reader.NumberOfPages;
                        }

                    }
                    //close everything
                    document.Close();
                    reader.Close();
                    destinationFileStream.Close();
            }

        }
        else
        {
            //is encrypted
            reader.Close();
        }

    }

我尝试了关闭阅读器等的所有可能组合,但似乎无论什么itext保持源文件打开。

诀窍是将PdfReader reader = new PdfReader(sourceFiles [f])更改为PdfReader reader = new PdfReader(new RandomAccessFileOrArray(sourceFiles [f],true),null)。

RandomAccessFileOrArray产生了不同。

我绝不是一个itextsharp专家。有人可以向我解释为什么在这种情况下,这对于释放文件的itext有如此大的影响?


1
投票

这就是我所做的:我创建了一个列表,列出了我合并的所有文件读者,以便跟踪它们,然后我最后将它们全部关闭。

List<PdfReader> readers = new List<PdfReader>();
        try
        {
            int f = 0;

            //PdfReader reader = new PdfReader(sSrcFile[f]);

            readers.Add(new PdfReader(sSrcFile[f]));

            int n = readers[f].NumberOfPages;
            //Response.Write("There are " + n + " pages in the original file.\n");
            Document document = new Document(PageSize.A4);

            PdfWriter writer = PdfWriter.GetInstance(document, new FileStream(destinationFile, FileMode.Create));

            document.Open();
            PdfContentByte cb = writer.DirectContent;
            PdfImportedPage page;

            int rotation;
            while (f < sSrcFile.Length)
            {
                int i = 0;
                while (i < n)
                {
                    i++;

                    document.SetPageSize(PageSize.A4);
                    document.NewPage();
                    page = writer.GetImportedPage(readers[f], i);

                    rotation = readers[f].GetPageRotation(i);
                    if (rotation == 90 || rotation == 270)
                    {
                        cb.AddTemplate(page, 0, -1f, 1f, 0, 0, readers[f].GetPageSizeWithRotation(i).Height);
                    }
                    else
                    {
                        cb.AddTemplate(page, 1f, 0, 0, 1f, 0, 0);
                    }
                    //Response.Write("\n Processed page " + i + "\n");
                }

                f++;
                if (f < sSrcFile.Length)
                {
                    readers.Add(new PdfReader(sSrcFile[f]));
                    n = readers[f].NumberOfPages;
                    //Response.Write("ff : There are " + n + " pages in the original file.\n");
                }
            }

            //Response.Write(returnLocation);
            document.Close();

            for (var i = 0; i < readers.Count; i++)
            {
                readers[i].Close();
            }

            return returnLocation;
        }
        catch (Exception e)
        {
            Response.Write("The error message is: " + e.Message);
            return e.Message;
        }

1
投票

我在VB.net中遇到了同样的问题。您需要关闭每个阅读器,pdfDoc和编写器。

Imports iTextSharp.text.pdf
Imports iTextSharp.text

Public Sub MergePDF_File(ByVal fileArray As String(), ByVal outPutPDF As String)

    If fileArray Is Nothing OrElse fileArray.Length = 0 Then
        Throw New ApplicationException("No file list")
    End If
    If String.IsNullOrEmpty(outPutPDF) Then
        Throw New ApplicationException("Must specify output file")
    End If

    Dim pdfDoc As iTextSharp.text.Document = Nothing
    Dim writer As iTextSharp.text.pdf.PdfCopy = Nothing

    For i = 0 To fileArray.Length - 1
        Using reader As New iTextSharp.text.pdf.PdfReader(fileArray(i))

            If i = 0 Then
                pdfDoc = New iTextSharp.text.Document(reader.GetPageSizeWithRotation(1))
                writer = New iTextSharp.text.pdf.PdfCopy(pdfDoc, _
                                      New FileStream(outPutPDF, _
                                      FileMode.OpenOrCreate, _
                                      FileAccess.Write))
                pdfDoc.Open()
            End If

            Dim pageCount As Integer = reader.NumberOfPages
            For pg = 1 To pageCount
                pdfDoc.SetPageSize(reader.GetPageSizeWithRotation(pg))
                pdfDoc.NewPage()
                Dim page As iTextSharp.text.pdf.PdfImportedPage = Nothing
                page = writer.GetImportedPage(reader, pg)
                writer.AddPage(page)
            Next

            reader.Close()
        End Using
    Next

    pdfDoc.Close()
    writer.Close()

End Sub

0
投票

我注意到的一件事是你没有关闭你正在构建的FileStream对象。由于FileStream类实现了IDisposable,我强烈建议您将代码包装在using块中,以便适当地清理资源。

    using(var destinationFileStream = new FileStream(destinationFile, FileMode.Create))
    {
        PdfWriter writer = PdfWriter.GetInstance(document, destinationFileStream));
        // step 3: we open the document
        document.Open();
        PdfContentByte cb = writer.DirectContent;
        PdfImportedPage page;
        int rotation;
        if(reader.IsEncrypted() == false)
        {
            // step 4: we add content
            while (f < sourceFiles.Length)
            {
                int i = 0;
                while (i < n)
                {
                    i++;
                    document.SetPageSize(reader.GetPageSizeWithRotation(i));
                document.NewPage();
                page = writer.GetImportedPage(reader, i);
                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);
                }
            }
            f++;
            if (f < sourceFiles.Length)
            {
                reader = new PdfReader(sourceFiles[f]);
                // we retrieve the total number of pages
                n = reader.NumberOfPages;
            }

        }
    }
    else
    {
        //is encrypted
    }
 }
© www.soinside.com 2019 - 2024. All rights reserved.