2012-09-03 12 views
5

Tôi gặp sự cố với HTMLWorker.Parse Từ iTextSharp trong chương trình Biểu mẫu Windows . Mỗi khi tôi thực thi mã và nó bắt đầu với HTMLWorker.Parse, nó cung cấp cho objectDisposedException. Ngoại lệ cho biết rằng nó không thể truy cập tệp đã đóng. Nhưng tôi đã kiểm tra nhiều lần và không thể tìm thấy tệp đã đóng. Đây là mã:Itextsharp HTMLWorker.Parse error

class HtmlToPdfConverter 
{ 
      private iTextSharp.text.Document doc = new iTextSharp.text.Document(); 

    public HtmlToPdfConverter() 
    { 
     this.doc.SetPageSize(PageSize.A4); 

    } 

    public string Run(string html, string pdfName) 
    { 
     try 
     { 
      using (doc) 
      { 
       StyleSheet styles = new StyleSheet(); 
       using (PdfWriter writer = PdfWriter.GetInstance(this.doc, new  FileStream(@"Z:\programs\" + pdfName + ".pdf", FileMode.Create))) 
       { 
        this.doc.Open(); 
        this.doc.OpenDocument(); 
        this.doc.NewPage(); 
        if (this.doc.IsOpen() == true) 
        { 
         StringReader reader = new StringReader(html); 
         //XMLWorkerHelper.GetInstance().ParseXHtml(writer, doc, reader); 
         this.doc.Add(new Paragraph(" ")); 
         HTMLWorker worker = new HTMLWorker(this.doc); 
         worker.Open(); 
         worker.StartDocument(); 
         worker.NewPage(); 
         worker.Parse(reader); 
         worker.SetStyleSheet(styles); 

         List<IElement> ie = iTextSharp.text.html.simpleparser.HTMLWorker.ParseToList(reader, null); 

         foreach (IElement element in ie) 
         { 
          this.doc.Add((IElement)element); 
         } 

         worker.EndDocument(); 
         worker.Close(); 
        } 
       } 
      } 
      return string.Empty; 
     } 
     catch (Exception ex) 
     { 
      return ex.Message; 
     } 

    } 
} 

Đây là ngoại lệ:

System.ObjectDisposedException was caught 
    Message=Cannot access a closed file. 
    Source=mscorlib 
    ObjectName="" 
    StackTrace: 
     at System.IO.__Error.FileNotOpen() 
     at System.IO.FileStream.Write(Byte[] array, Int32 offset, Int32 count) 
     at iTextSharp.text.pdf.OutputStreamCounter.Write(Byte[] buffer, Int32 offset, Int32 count) 
     at iTextSharp.text.pdf.PdfIndirectObject.WriteTo(Stream os) 
     at iTextSharp.text.pdf.PdfWriter.PdfBody.Add(PdfObject objecta, Int32 refNumber, Boolean inObjStm) 
     at iTextSharp.text.pdf.PdfWriter.PdfBody.Add(PdfObject objecta, Int32 refNumber) 
     at iTextSharp.text.pdf.PdfWriter.PdfBody.Add(PdfObject objecta, PdfIndirectReference refa) 
     at iTextSharp.text.pdf.PdfWriter.AddToBody(PdfObject objecta, PdfIndirectReference refa) 
     at iTextSharp.text.pdf.Type1Font.WriteFont(PdfWriter writer, PdfIndirectReference piref, Object[] parms) 
     at iTextSharp.text.pdf.FontDetails.WriteFont(PdfWriter writer) 
     at iTextSharp.text.pdf.PdfWriter.AddSharedObjectsToBody() 
     at iTextSharp.text.pdf.PdfWriter.Close() 
     at iTextSharp.text.DocWriter.Dispose() 
     at WebPageExtraction.HtmlToPdfConverter.Run(String html, String pdfName) 
    InnerException: 

Trả lời

5

Bạn đang cố gắng để gọi các phương pháp chặt chẽ sau khi nó đã được xử lý.

Bạn có một khối using được xử lý các đối tượng tự động, vì vậy chỉ cần loại bỏ những hai dòng:

doc.CloseDocument(); 
doc.Close(); 

Nếu bạn không tin tưởng các mã dispose nội bộ để đóng đúng tài liệu và muốn làm điều đó mình dù sao, làm điều đó bên trong khối using:

using (doc) 
{ 
    StyleSheet styles = new StyleSheet(); 
    using (PdfWriter writer = PdfWriter.GetInstance(this.doc, new  FileStream(@"Z:\programs\" + pdfName + ".pdf", FileMode.Create))) 
    { 
     //..... 
    } 
    doc.CloseDocument(); 
    doc.Close(); 
} 

Sửa: sau khi thử code của bạn cho bản thân mình, tôi nhận thấy một số vấn đề hơn và tìm thấy lý do thực sự cho lỗi bạn nhận được:

  • Bạn đang đóng và hủy đối tượng chung doc và không bao giờ tạo phiên bản mới.
  • Bạn không thải bỏ tất cả các đối tượng, điều này có thể dẫn đến rò rỉ bộ nhớ hoặc tệp bị khóa.
  • Lỗi bạn nhận được là do theo mặc định, PdfWriter đang đóng Luồng đang sử dụng và khi được xử lý, người viết đang cố gắng sử dụng luồng này. Vì vậy, để giải quyết vấn đề này, bạn phải tự mình đóng luồng và bảo người viết không làm điều đó.

Hoàn thành code cố định:

Document doc = new Document(); 
StyleSheet styles = new StyleSheet(); 
string filePath = @"Z:\programs\" + pdfName + ".pdf"; 
using (FileStream pdfStream = new FileStream(filePath, FileMode.Create)) 
{ 
    using (PdfWriter writer = PdfWriter.GetInstance(doc, pdfStream)) 
    { 
     writer.CloseStream = false; 
     doc.Open(); 
     doc.OpenDocument(); 
     doc.NewPage(); 
     if (doc.IsOpen() == true) 
     { 
      using (StringReader reader = new StringReader(html)) 
      { 
       //XMLWorkerHelper.GetInstance().ParseXHtml(writer, doc, reader); 
       doc.Add(new Paragraph(" ")); 
       using (HTMLWorker worker = new HTMLWorker(doc)) 
       { 
        worker.Open(); 
        worker.StartDocument(); 
        worker.NewPage(); 
        worker.Parse(reader); 
        worker.SetStyleSheet(styles); 
        List<IElement> ie = iTextSharp.text.html.simpleparser.HTMLWorker.ParseToList(reader, null); 
        foreach (IElement element in ie) 
        { 
         doc.Add((IElement)element); 
        } 
        worker.EndDocument(); 
        worker.Close(); 
       } 
      } 
     } 
     writer.Close(); 
    } 
} 

doc.CloseDocument(); 
doc.Close(); 
doc.Dispose(); 
+0

i thêm những doc.close và .closeDocument như thêm để xem xét nếu được đi làm. Tôi đã thử giải pháp của bạn, nhưng nó vẫn không hoạt động. Cảm ơn vì sự giúp đỡ. – Emon

+1

Có, tìm thấy lý do thực sự. Xem chỉnh sửa của tôi. Thay đổi quan trọng là thêm 'writer.CloseStream = false;' –

+0

Bây giờ nó đưa ra một ngoại lệ khác. nó là ngoại lệ. nó nói rằng nó không thể tìm thấy đường dẫn mạng. Phiên bản này cũng dừng lại ở worker.parse, bạn có biết có gì sai với phương thức đó trong iTextSharp không? Nó không đưa ra ngoại lệ khác nữa. Cảm ơn vì đã giúp tôi. – Emon