ItextSharp Error on trying to parse html for pdf conversion

c#, html-agility-pack, html-parsing, itext, xmlworker

Solution

`HTMLWorker' has been deprecated in favor of XMLWorker. Here is a working example tested with a snippet of HTML like you used above:

StringReader html = new StringReader(@"
<div style='font-size: 18pt; font-weight: bold;'>
Mouser Electronics <br />Authorized Distributor</div><br /> <br />
<div style='font-size: 14pt;'>Click to View Pricing, Inventory, Delivery & Lifecycle Information:
</div>
<br />
<div>
<table>
<tr><td></td><td>
<a href='http://www.mouser.com/access/?pn=78211-009' 
style='color: Blue; font-size: 10pt; text-decoration: underline;'>78211-009</a></td></tr>
</table></div>    
");      
using (Document document = new Document()) {
  PdfWriter writer = PdfWriter.GetInstance(document, STREAM);
  document.Open();
  XMLWorkerHelper.GetInstance().ParseXHtml(
    writer, document, html
  );
}

When using `XMLWorker` you need to use well-formed HTML - it's an XML parser, after all. The sample `HTML` from your question above doesn't have closing `<a>` or `<br>` tags. A `HTML` parser like HtmlAgilityPack will fix those problems, and turn this:

<div><img src='a.gif'><br><hr></div>

into this:

<div><img src='a.gif' /><br /><hr /></div>

with only a few lines of code:

var hDocument = new HtmlDocument()
{
    OptionWriteEmptyNodes = true,
    OptionAutoCloseOnEnd = true
};
hDocument.LoadHtml("<div><img src='a.gif'><br><hr></div>");
var closedTags  = hDocument.DocumentNode.WriteTo();

`XMLWorker` is available as a nuget package, or as a separate download at sourceforge.

See here for more advanced usage of `XMLWorker`.

Problem

I was using the ItextSharp module to convert the below listed html in to a pdf page. ``` <div style="font-size: 18pt; font-weight: bold;"> mma<br>mmar</div><br> <br> <div style="font-size: 14pt;">Click to View Pricing </div> <br> <div> <table> <tr><td> <a href="http://www.mma.com/fci" style="color: Blue; font-size: 10pt; text-decoration: underline;"> FCI</a>:</td> <td><a href="http://www.mma.com/access/?pn=78211-014" style="color: Blue; font-size: 10pt; text-decoration: underline;"> 78211-014</a></td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-009" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-009</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-006" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-006</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-007" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-007</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-003" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-003</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-005" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-005</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-008" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-008</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-004" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-004</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-012" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-012</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-007LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-007LF</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-015LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-015LF</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-003LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-003LF</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-009LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-009LF</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-005LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-005LF</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-010LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-010LF</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-006LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-006LF</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-014LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-014LF</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-004LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-004LF</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-012LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-012LF</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-008LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-008LF</td></tr><tr><td></td> <td> <a href="http://www.mma.com/access/?pn=78211-011LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-011LF</td></tr><tr><td></td> <td><a href="http://www.mma.com/access/?pn=78211-013LF" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-013LF</td></tr><tr><td></td> <td><a href="http://www.mma.com/access/?pn=78211-010" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-010</td></tr><tr><td></td> <td><a href="http://www.mma.com/access/?pn=78211-015" style="color: Blue; font-size: 10pt; text-decoration: underline;">78211-015</td></tr><tr><td> <a href="http://www.mma.com/souriau" style="color: Blue; font-size: 10pt; text-decoration: underline;"> Souriau</a>:</td> <td><a href="http://www.mma.com/access/?pn=24JR124-3" style="color: Blue; font-size: 10pt; text-decoration: underline;"> 24JR124-3</a></td></tr></table></div> ``` C# code to generate the html above : ``` var html = new StringBuilder(@"<div style=""font-size: 18pt; font-weight: bold;"">Authorized Distributor</div><br> <br><div style=""font-size: 14pt;"">Click to View Pricing, Inventory, Delivery & Lifecycle Information:</div><br>"); List<MfrBrandView> mfrBrands = MfrBrandView.Load(fileId); var uniquesuppliers = mfrBrands.GroupBy(t => new {t.Manufacturer,t.SupplierVirtualDirectory}).Select(g => g.First()); html.Append("<div><table>"); foreach (var uniquesupplier in uniquesuppliers) { var mfrPartNums = mfrBrands.Where(t => t.ManufacturerId == uniquesupplier.ManufacturerId).Select( t => t.ManufacturerPartNumber).ToList(); html.AppendFormat(@"<tr><td> <a href=""http://www.mma.com/{0}"" style=""color: Blue; font-size: 10pt; text-decoration: underline;""> {1}</a>:</td> <td><a href=""http://www.mma.com/access/?pn={2}"" style=""color: Blue; font-size: 10pt; text-decoration: underline;""> {2}</a></td></tr>", uniquesupplier.SupplierVirtualDirectory, uniquesupplier.MouserizationLabel, mfrPartNums[0]); for (int i = 1; i < mfrPartNums.Count(); i++) { html.AppendFormat( @"<tr><td></td> <td><a href=""http://www.mma.com/access/?pn={0}"" style=""color: Blue; font-size: 10pt; text-decoration: underline;"">{0}</td></tr>", mfrPartNums[i]); } } html.Append("</table></div>"); return html.ToString(); ``` Code to generate the page after html is formed: ``` PdfWriter writer = null; PdfDocument doc = null; //PdfReader reader = new PdfReader(content); // reader.Info["Title"] try { doc = new PdfDocument(); doc.SetPageSize(PageSize.LETTER); writer = PdfWriter.GetInstance(doc, content); writer.CloseStream = false; doc.Open(); doc.NewPage(); foreach (IElement element in iTextSharp.text.html.simpleparser.HTMLWorker.ParseToList(new StringReader(html), null)) { doc.Add(element); } } ``` below is where i get an exception saying "Unable to cast object of type 'iTextSharp.text.html.simpleparser.CellWrapper' to type 'iTextSharp.text.Paragraph'." `iTextSharp.text.html.simpleparser.HTMLWorker.ParseToList(new StringReader(html), null)` Is there something wrong with the html I'm trying to parse? Is there a better way of doing this? Thanks much in advance for your help. It's very much appreciated.

Original source

Related problems