Skip to footer content
MIGRATION GUIDES

How to Migrate from wkhtmltopdf to IronPDF in C#

wkhtmltopdf has been a widely-used tool for converting HTML documents to PDF using Qt WebKit. Despite its popularity among developers for its command-line capabilities and free licensing, the project now presents critical security risks that can no longer be ignored. The library was officially abandoned in 2016-2017, and a CRITICAL severity vulnerability (CVE-2022-35583) remains permanently unpatched.

This guide provides a complete migration path from wkhtmltopdf to IronPDF, with step-by-step instructions, code comparisons, and practical examples for professional .NET developers who need to eliminate this security risk from their applications.

Critical Security Warning: CVE-2022-35583

wkhtmltopdf contains a critical security vulnerability that will never be fixed:

IssueSeverityStatus
CVE-2022-35583CRITICAL (9.8/10)UNPATCHED
SSRF VulnerabilityInfrastructure takeover riskUNPATCHED
Last Update2016-2017ABANDONED
WebKit Version2015 (Qt WebKit)OBSOLETE
CSS Grid SupportNoneBroken
Flexbox SupportPartialBroken
ES6+ JavaScriptNoneBroken

How the SSRF Attack Works

The Server-Side Request Forgery vulnerability allows attackers to access internal services, steal credentials, scan your internal network, and exfiltrate sensitive data through crafted HTML:


<iframe src="http://169.254.169.254/latest/meta-data/iam/security-credentials/"></iframe>
<img src="http://internal-database:5432/admin"/>

<iframe src="http://169.254.169.254/latest/meta-data/iam/security-credentials/"></iframe>
<img src="http://internal-database:5432/admin"/>
HTML

When wkhtmltopdf renders this HTML, it fetches these URLs from your server's network context, bypassing firewalls and security controls.

Affected Wrapper Libraries

All .NET wrappers for wkhtmltopdf inherit these vulnerabilities:

Wrapper LibraryStatusSecurity Risk
DinkToPdfAbandoned⚠️ CRITICAL
RotativaAbandoned⚠️ CRITICAL
TuesPechkinAbandoned⚠️ CRITICAL
WkHtmlToPdf-DotNetAbandoned⚠️ CRITICAL
NReco.PdfGeneratorUses wkhtmltopdf⚠️ CRITICAL

If you use any of these libraries, you are vulnerable to CVE-2022-35583.

IronPDF vs wkhtmltopdf: Feature Comparison

Understanding the architectural differences helps technical decision-makers evaluate the migration investment:

FeaturewkhtmltopdfIronPDF
LicensingLGPLv3 (Free)Commercial
Rendering EngineQt WebKit (2015)Current Chromium Engine
Security VulnerabilitiesCVE-2022-35583, major unpatched issuesNo known CVEs
Active MaintenanceAbandoned, no meaningful updates since 2017Actively maintained with regular releases
Support for Modern Web StandardsLimited (Broken flexbox, no CSS Grid)Supported
Integration and SupportLimited to community forumsExtensive documentation and dedicated support
CSS Grid❌ Not supported✅ Supported
Flexbox⚠️ Broken✅ Supported
ES6+ JavaScript❌ Not supported✅ Supported
Async/Await❌ Not supported✅ Supported
PDF Manipulation❌ Not supported✅ Supported
Digital Signatures❌ Not supported✅ Supported
PDF/A Compliance❌ Not supported✅ Supported

Quick Start: wkhtmltopdf to IronPDF Migration

The migration can begin immediately with these foundational steps.

Step 1: Remove wkhtmltopdf Packages and Binaries

Remove all wkhtmltopdf wrapper packages:

# Remove wkhtmltopdf wrapper (whichever you're using)
dotnet remove package WkHtmlToPdf-DotNet
dotnet remove package DinkToPdf
dotnet remove package TuesPechkin
dotnet remove package Rotativa
dotnet remove package Rotativa.AspNetCore
dotnet remove package NReco.PdfGenerator

# Remove wkhtmltopdf binary from your deployment
# Delete wkhtmltopdf.exe, wkhtmltox.dll, etc.
# Remove wkhtmltopdf wrapper (whichever you're using)
dotnet remove package WkHtmlToPdf-DotNet
dotnet remove package DinkToPdf
dotnet remove package TuesPechkin
dotnet remove package Rotativa
dotnet remove package Rotativa.AspNetCore
dotnet remove package NReco.PdfGenerator

# Remove wkhtmltopdf binary from your deployment
# Delete wkhtmltopdf.exe, wkhtmltox.dll, etc.
SHELL

Step 2: Install IronPDF

# Add IronPDF (secure, modern alternative)
dotnet add package IronPdf
# Add IronPDF (secure, modern alternative)
dotnet add package IronPdf
SHELL

Step 3: Update Namespaces

Replace wkhtmltopdf namespaces with the IronPdf namespace:

// Before (wkhtmltopdf)
using WkHtmlToPdfDotNet;
using WkHtmlToPdfDotNet.Contracts;

// After (IronPDF)
using IronPdf;
// Before (wkhtmltopdf)
using WkHtmlToPdfDotNet;
using WkHtmlToPdfDotNet.Contracts;

// After (IronPDF)
using IronPdf;
IRON VB CONVERTER ERROR developers@ironsoftware.com
$vbLabelText   $csharpLabel

Step 4: Initialize License

Add license initialization at application startup:

IronPdf.License.LicenseKey = "YOUR-LICENSE-KEY";
IronPdf.License.LicenseKey = "YOUR-LICENSE-KEY";
IronPdf.License.LicenseKey = "YOUR-LICENSE-KEY"
$vbLabelText   $csharpLabel

Code Migration Examples

Converting HTML to PDF

The most fundamental operation reveals the complexity difference between these .NET PDF approaches.

wkhtmltopdf Approach:

// NuGet: Install-Package WkHtmlToPdf-DotNet
using WkHtmlToPdfDotNet;
using WkHtmlToPdfDotNet.Contracts;
using System.IO;

class Program
{
    static void Main()
    {
        var converter = new SynchronizedConverter(new PdfTools());
        var doc = new HtmlToPdfDocument()
        {
            GlobalSettings = {
                ColorMode = ColorMode.Color,
                Orientation = Orientation.Portrait,
                PaperSize = PaperKind.A4
            },
            Objects = {
                new ObjectSettings()
                {
                    HtmlContent = "<h1>Hello World</h1><p>This is a PDF from HTML.</p>"
                }
            }
        };
        byte[] pdf = converter.Convert(doc);
        File.WriteAllBytes("output.pdf", pdf);
    }
}
// NuGet: Install-Package WkHtmlToPdf-DotNet
using WkHtmlToPdfDotNet;
using WkHtmlToPdfDotNet.Contracts;
using System.IO;

class Program
{
    static void Main()
    {
        var converter = new SynchronizedConverter(new PdfTools());
        var doc = new HtmlToPdfDocument()
        {
            GlobalSettings = {
                ColorMode = ColorMode.Color,
                Orientation = Orientation.Portrait,
                PaperSize = PaperKind.A4
            },
            Objects = {
                new ObjectSettings()
                {
                    HtmlContent = "<h1>Hello World</h1><p>This is a PDF from HTML.</p>"
                }
            }
        };
        byte[] pdf = converter.Convert(doc);
        File.WriteAllBytes("output.pdf", pdf);
    }
}
' NuGet: Install-Package WkHtmlToPdf-DotNet
Imports WkHtmlToPdfDotNet
Imports WkHtmlToPdfDotNet.Contracts
Imports System.IO

Class Program
    Shared Sub Main()
        Dim converter = New SynchronizedConverter(New PdfTools())
        Dim doc = New HtmlToPdfDocument() With {
            .GlobalSettings = New GlobalSettings() With {
                .ColorMode = ColorMode.Color,
                .Orientation = Orientation.Portrait,
                .PaperSize = PaperKind.A4
            },
            .Objects = {
                New ObjectSettings() With {
                    .HtmlContent = "<h1>Hello World</h1><p>This is a PDF from HTML.</p>"
                }
            }
        }
        Dim pdf As Byte() = converter.Convert(doc)
        File.WriteAllBytes("output.pdf", pdf)
    End Sub
End Class
$vbLabelText   $csharpLabel

IronPDF Approach:

// NuGet: Install-Package IronPdf
using IronPdf;
using System;

class Program
{
    static void Main()
    {
        var renderer = new ChromePdfRenderer();
        var pdf = renderer.RenderHtmlAsPdf("<h1>Hello World</h1><p>This is a PDF from HTML.</p>");
        pdf.SaveAs("output.pdf");
    }
}
// NuGet: Install-Package IronPdf
using IronPdf;
using System;

class Program
{
    static void Main()
    {
        var renderer = new ChromePdfRenderer();
        var pdf = renderer.RenderHtmlAsPdf("<h1>Hello World</h1><p>This is a PDF from HTML.</p>");
        pdf.SaveAs("output.pdf");
    }
}
IRON VB CONVERTER ERROR developers@ironsoftware.com
$vbLabelText   $csharpLabel

wkhtmltopdf requires creating a SynchronizedConverter with PdfTools, constructing an HtmlToPdfDocument with GlobalSettings and Objects, setting properties like ColorMode, Orientation, and PaperSize, calling converter.Convert() to get raw bytes, and manually writing to a file with File.WriteAllBytes().

IronPDF eliminates this ceremony entirely—create a ChromePdfRenderer, call RenderHtmlAsPdf(), and use the built-in SaveAs() method.

For advanced HTML-to-PDF scenarios, see the HTML to PDF conversion guide.

Converting URLs to PDF

URL-to-PDF conversion shows similar complexity patterns.

wkhtmltopdf Approach:

// NuGet: Install-Package WkHtmlToPdf-DotNet
using WkHtmlToPdfDotNet;
using WkHtmlToPdfDotNet.Contracts;
using System.IO;

class Program
{
    static void Main()
    {
        var converter = new SynchronizedConverter(new PdfTools());
        var doc = new HtmlToPdfDocument()
        {
            GlobalSettings = {
                ColorMode = ColorMode.Color,
                Orientation = Orientation.Portrait,
                PaperSize = PaperKind.A4
            },
            Objects = {
                new ObjectSettings()
                {
                    Page = "https://www.example.com"
                }
            }
        };
        byte[] pdf = converter.Convert(doc);
        File.WriteAllBytes("webpage.pdf", pdf);
    }
}
// NuGet: Install-Package WkHtmlToPdf-DotNet
using WkHtmlToPdfDotNet;
using WkHtmlToPdfDotNet.Contracts;
using System.IO;

class Program
{
    static void Main()
    {
        var converter = new SynchronizedConverter(new PdfTools());
        var doc = new HtmlToPdfDocument()
        {
            GlobalSettings = {
                ColorMode = ColorMode.Color,
                Orientation = Orientation.Portrait,
                PaperSize = PaperKind.A4
            },
            Objects = {
                new ObjectSettings()
                {
                    Page = "https://www.example.com"
                }
            }
        };
        byte[] pdf = converter.Convert(doc);
        File.WriteAllBytes("webpage.pdf", pdf);
    }
}
' NuGet: Install-Package WkHtmlToPdf-DotNet
Imports WkHtmlToPdfDotNet
Imports WkHtmlToPdfDotNet.Contracts
Imports System.IO

Module Program
    Sub Main()
        Dim converter As New SynchronizedConverter(New PdfTools())
        Dim doc As New HtmlToPdfDocument() With {
            .GlobalSettings = New GlobalSettings() With {
                .ColorMode = ColorMode.Color,
                .Orientation = Orientation.Portrait,
                .PaperSize = PaperKind.A4
            },
            .Objects = {
                New ObjectSettings() With {
                    .Page = "https://www.example.com"
                }
            }
        }
        Dim pdf As Byte() = converter.Convert(doc)
        File.WriteAllBytes("webpage.pdf", pdf)
    End Sub
End Module
$vbLabelText   $csharpLabel

IronPDF Approach:

// NuGet: Install-Package IronPdf
using IronPdf;
using System;

class Program
{
    static void Main()
    {
        var renderer = new ChromePdfRenderer();
        var pdf = renderer.RenderUrlAsPdf("https://www.example.com");
        pdf.SaveAs("webpage.pdf");
    }
}
// NuGet: Install-Package IronPdf
using IronPdf;
using System;

class Program
{
    static void Main()
    {
        var renderer = new ChromePdfRenderer();
        var pdf = renderer.RenderUrlAsPdf("https://www.example.com");
        pdf.SaveAs("webpage.pdf");
    }
}
IRON VB CONVERTER ERROR developers@ironsoftware.com
$vbLabelText   $csharpLabel

wkhtmltopdf uses the Page property in ObjectSettings to specify a URL, requiring the same document construction pattern. IronPDF provides a dedicated RenderUrlAsPdf() method that clearly expresses intent.

Explore the URL to PDF documentation for authentication and custom header options.

Custom Settings: HTML Files with Page Configuration

Configuring orientation, margins, and paper size requires different approaches.

wkhtmltopdf Approach:

// NuGet: Install-Package WkHtmlToPdf-DotNet
using WkHtmlToPdfDotNet;
using WkHtmlToPdfDotNet.Contracts;
using System.IO;

class Program
{
    static void Main()
    {
        var converter = new SynchronizedConverter(new PdfTools());
        var doc = new HtmlToPdfDocument()
        {
            GlobalSettings = {
                ColorMode = ColorMode.Color,
                Orientation = Orientation.Landscape,
                PaperSize = PaperKind.A4,
                Margins = new MarginSettings() { Top = 10, Bottom = 10, Left = 10, Right = 10 }
            },
            Objects = {
                new ObjectSettings()
                {
                    Page = "input.html",
                    WebSettings = { DefaultEncoding = "utf-8" }
                }
            }
        };
        byte[] pdf = converter.Convert(doc);
        File.WriteAllBytes("custom-output.pdf", pdf);
    }
}
// NuGet: Install-Package WkHtmlToPdf-DotNet
using WkHtmlToPdfDotNet;
using WkHtmlToPdfDotNet.Contracts;
using System.IO;

class Program
{
    static void Main()
    {
        var converter = new SynchronizedConverter(new PdfTools());
        var doc = new HtmlToPdfDocument()
        {
            GlobalSettings = {
                ColorMode = ColorMode.Color,
                Orientation = Orientation.Landscape,
                PaperSize = PaperKind.A4,
                Margins = new MarginSettings() { Top = 10, Bottom = 10, Left = 10, Right = 10 }
            },
            Objects = {
                new ObjectSettings()
                {
                    Page = "input.html",
                    WebSettings = { DefaultEncoding = "utf-8" }
                }
            }
        };
        byte[] pdf = converter.Convert(doc);
        File.WriteAllBytes("custom-output.pdf", pdf);
    }
}
' NuGet: Install-Package WkHtmlToPdf-DotNet
Imports WkHtmlToPdfDotNet
Imports WkHtmlToPdfDotNet.Contracts
Imports System.IO

Class Program
    Shared Sub Main()
        Dim converter As New SynchronizedConverter(New PdfTools())
        Dim doc As New HtmlToPdfDocument() With {
            .GlobalSettings = New GlobalSettings() With {
                .ColorMode = ColorMode.Color,
                .Orientation = Orientation.Landscape,
                .PaperSize = PaperKind.A4,
                .Margins = New MarginSettings() With {.Top = 10, .Bottom = 10, .Left = 10, .Right = 10}
            },
            .Objects = {
                New ObjectSettings() With {
                    .Page = "input.html",
                    .WebSettings = New WebSettings() With {.DefaultEncoding = "utf-8"}
                }
            }
        }
        Dim pdf As Byte() = converter.Convert(doc)
        File.WriteAllBytes("custom-output.pdf", pdf)
    End Sub
End Class
$vbLabelText   $csharpLabel

IronPDF Approach:

// NuGet: Install-Package IronPdf
using IronPdf;
using IronPdf.Rendering;
using System;

class Program
{
    static void Main()
    {
        var renderer = new ChromePdfRenderer();
        renderer.RenderingOptions.PaperOrientation = PdfPaperOrientation.Landscape;
        renderer.RenderingOptions.MarginTop = 10;
        renderer.RenderingOptions.MarginBottom = 10;
        renderer.RenderingOptions.MarginLeft = 10;
        renderer.RenderingOptions.MarginRight = 10;
        renderer.RenderingOptions.PaperSize = PdfPaperSize.A4;

        var pdf = renderer.RenderHtmlFileAsPdf("input.html");
        pdf.SaveAs("custom-output.pdf");
    }
}
// NuGet: Install-Package IronPdf
using IronPdf;
using IronPdf.Rendering;
using System;

class Program
{
    static void Main()
    {
        var renderer = new ChromePdfRenderer();
        renderer.RenderingOptions.PaperOrientation = PdfPaperOrientation.Landscape;
        renderer.RenderingOptions.MarginTop = 10;
        renderer.RenderingOptions.MarginBottom = 10;
        renderer.RenderingOptions.MarginLeft = 10;
        renderer.RenderingOptions.MarginRight = 10;
        renderer.RenderingOptions.PaperSize = PdfPaperSize.A4;

        var pdf = renderer.RenderHtmlFileAsPdf("input.html");
        pdf.SaveAs("custom-output.pdf");
    }
}
IRON VB CONVERTER ERROR developers@ironsoftware.com
$vbLabelText   $csharpLabel

wkhtmltopdf nests settings inside GlobalSettings and Objects, with MarginSettings as a separate object. IronPDF provides direct RenderingOptions properties with clear names like PaperOrientation, MarginTop, and PaperSize.

wkhtmltopdf API to IronPDF Mapping Reference

This mapping accelerates migration by showing direct API equivalents:

CLI to IronPDF Mapping

wkhtmltopdf CLI OptionIronPDF Equivalent
wkhtmltopdf input.html output.pdfrenderer.RenderHtmlFileAsPdf()
wkhtmltopdf URL output.pdfrenderer.RenderUrlAsPdf()
--page-size A4RenderingOptions.PaperSize = PdfPaperSize.A4
--page-size LetterRenderingOptions.PaperSize = PdfPaperSize.Letter
--orientation LandscapeRenderingOptions.PaperOrientation = Landscape
--margin-top 10mmRenderingOptions.MarginTop = 10
--margin-bottom 10mmRenderingOptions.MarginBottom = 10
--margin-left 10mmRenderingOptions.MarginLeft = 10
--margin-right 10mmRenderingOptions.MarginRight = 10
--header-html header.htmlRenderingOptions.HtmlHeader
--footer-center "[page]"{page} placeholder
--footer-center "[toPage]"{total-pages} placeholder
--enable-javascriptEnabled by default
--javascript-delay 500RenderingOptions.WaitFor.RenderDelay = 500
--dpi 300RenderingOptions.Dpi = 300
--grayscaleRenderingOptions.GrayScale = true

C# Wrapper API Mapping

wkhtmltopdf WrapperIronPDF
SynchronizedConverterChromePdfRenderer
HtmlToPdfDocumentRenderingOptions
GlobalSettings.Outpdf.SaveAs()
GlobalSettings.PaperSizeRenderingOptions.PaperSize
GlobalSettings.OrientationRenderingOptions.PaperOrientation
GlobalSettings.MarginsRenderingOptions.Margin*
ObjectSettings.PageRenderHtmlFileAsPdf()
ObjectSettings.HtmlContentRenderHtmlAsPdf()
converter.Convert(doc)renderer.RenderHtmlAsPdf()

Placeholder Syntax Migration

wkhtmltopdf PlaceholderIronPDF Placeholder
[page]{page}
[toPage]{total-pages}
[date]{date}
[time]{time}
[title]{html-title}
[url]{url}

Common Migration Issues and Solutions

wkhtmltopdf: Uses square bracket syntax like [page] and [toPage].

Solution: Update to IronPDF's curly brace placeholders:

// Before (wkhtmltopdf)
FooterSettings = { Left = "Page [page] of [toPage]" }

// After (IronPDF)
renderer.RenderingOptions.HtmlFooter = new HtmlHeaderFooter
{
    HtmlFragment = "<div style='text-align:left;'>Page {page} of {total-pages}</div>",
    MaxHeight = 25
};
// Before (wkhtmltopdf)
FooterSettings = { Left = "Page [page] of [toPage]" }

// After (IronPDF)
renderer.RenderingOptions.HtmlFooter = new HtmlHeaderFooter
{
    HtmlFragment = "<div style='text-align:left;'>Page {page} of {total-pages}</div>",
    MaxHeight = 25
};
IRON VB CONVERTER ERROR developers@ironsoftware.com
$vbLabelText   $csharpLabel

Issue 2: JavaScript Delay Configuration

wkhtmltopdf: Uses JavascriptDelay property with limited reliability.

Solution: IronPDF provides multiple options:

renderer.RenderingOptions.EnableJavaScript = true;

// Option 1: Fixed delay
renderer.RenderingOptions.WaitFor.RenderDelay(500);

// Option 2: Wait for specific element (more reliable)
renderer.RenderingOptions.WaitFor.HtmlElementById("content-loaded");

// Option 3: Wait for JavaScript condition
renderer.RenderingOptions.WaitFor.JavaScript("window.renderComplete === true");
renderer.RenderingOptions.EnableJavaScript = true;

// Option 1: Fixed delay
renderer.RenderingOptions.WaitFor.RenderDelay(500);

// Option 2: Wait for specific element (more reliable)
renderer.RenderingOptions.WaitFor.HtmlElementById("content-loaded");

// Option 3: Wait for JavaScript condition
renderer.RenderingOptions.WaitFor.JavaScript("window.renderComplete === true");
renderer.RenderingOptions.EnableJavaScript = True

' Option 1: Fixed delay
renderer.RenderingOptions.WaitFor.RenderDelay(500)

' Option 2: Wait for specific element (more reliable)
renderer.RenderingOptions.WaitFor.HtmlElementById("content-loaded")

' Option 3: Wait for JavaScript condition
renderer.RenderingOptions.WaitFor.JavaScript("window.renderComplete === true")
$vbLabelText   $csharpLabel

Issue 3: Modern CSS Not Rendering

Symptom: CSS Grid and Flexbox layouts render incorrectly in wkhtmltopdf.

Solution: IronPDF's Chromium engine handles modern CSS correctly:

// This CSS now works with IronPDF
var html = @"
<style>
    .grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 10px; }
    .flex { display: flex; justify-content: space-between; align-items: center; }
</style>
<div class='grid'>
    <div>Column 1</div>
    <div>Column 2</div>
    <div>Column 3</div>
</div>";

var pdf = renderer.RenderHtmlAsPdf(html);
// This CSS now works with IronPDF
var html = @"
<style>
    .grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 10px; }
    .flex { display: flex; justify-content: space-between; align-items: center; }
</style>
<div class='grid'>
    <div>Column 1</div>
    <div>Column 2</div>
    <div>Column 3</div>
</div>";

var pdf = renderer.RenderHtmlAsPdf(html);
IRON VB CONVERTER ERROR developers@ironsoftware.com
$vbLabelText   $csharpLabel

Issue 4: Synchronous vs Asynchronous Rendering

wkhtmltopdf: Wrappers are synchronous and block threads.

Solution: IronPDF supports async rendering:

public async Task<byte[]> GeneratePdfAsync(string html)
{
    var renderer = new ChromePdfRenderer();
    var pdf = await renderer.RenderHtmlAsPdfAsync(html);
    return pdf.BinaryData;
}
public async Task<byte[]> GeneratePdfAsync(string html)
{
    var renderer = new ChromePdfRenderer();
    var pdf = await renderer.RenderHtmlAsPdfAsync(html);
    return pdf.BinaryData;
}
IRON VB CONVERTER ERROR developers@ironsoftware.com
$vbLabelText   $csharpLabel

wkhtmltopdf Migration Checklist

Pre-Migration Tasks

Audit your codebase to identify all wkhtmltopdf usage:

# Find all wkhtmltopdf references
grep -r "WkHtmlToPdfDotNet\|DinkToPdf\|TuesPechkin\|Rotativa" --include="*.cs" .
grep -r "wkhtmltopdf" --include="*.yml" --include="*.yaml" --include="Dockerfile" .
# Find all wkhtmltopdf references
grep -r "WkHtmlToPdfDotNet\|DinkToPdf\|TuesPechkin\|Rotativa" --include="*.cs" .
grep -r "wkhtmltopdf" --include="*.yml" --include="*.yaml" --include="Dockerfile" .
SHELL

Locate and document wkhtmltopdf binary files for removal. Document current settings (paper size, margins, headers/footers).

Code Update Tasks

  1. Remove all wkhtmltopdf wrapper NuGet packages
  2. Remove wkhtmltopdf binaries (wkhtmltopdf.exe, wkhtmltox.dll)
  3. Install IronPdf NuGet package
  4. Update namespace imports from WkHtmlToPdfDotNet to IronPdf
  5. Replace SynchronizedConverter with ChromePdfRenderer
  6. Convert HtmlToPdfDocument patterns to direct rendering methods
  7. Update GlobalSettings configurations to RenderingOptions
  8. Convert margin configurations from MarginSettings to individual properties
  9. Update placeholder syntax ([page]{page}, [toPage]{total-pages})
  10. Add IronPDF license initialization at startup

Post-Migration Testing

After migration, verify these aspects:

  • Visual comparison of PDF output (should improve with modern CSS support)
  • Verify modern CSS rendering (CSS Grid and Flexbox now work)
  • Test JavaScript-heavy pages
  • Security scan to confirm no wkhtmltopdf binaries remain
  • Load test for performance comparison

Security Verification

# Scan for any remaining wkhtmltopdf artifacts
find /var/www/ -name "*wkhtmlto*" 2>/dev/null
find /usr/local/bin/ -name "*wkhtmlto*" 2>/dev/null
docker images | grep wkhtmltopdf

# Check if any process is still using it
ps aux | grep wkhtmltopdf
# Scan for any remaining wkhtmltopdf artifacts
find /var/www/ -name "*wkhtmlto*" 2>/dev/null
find /usr/local/bin/ -name "*wkhtmlto*" 2>/dev/null
docker images | grep wkhtmltopdf

# Check if any process is still using it
ps aux | grep wkhtmltopdf
SHELL

Key Benefits of Migrating to IronPDF

Moving from wkhtmltopdf to IronPDF provides several critical advantages:

Security: CVE-2022-35583 and all wkhtmltopdf vulnerabilities are eliminated. IronPDF has no known CVEs and receives regular security updates.

Modern Rendering Engine: IronPDF uses the current Chromium engine, ensuring full CSS3, CSS Grid, Flexbox, and ES6+ JavaScript support. Modern frameworks render correctly.

Simplified API: Direct rendering methods replace document construction patterns. Built-in SaveAs() methods eliminate manual byte handling.

Extended Capabilities: PDF manipulation, digital signatures, PDF/A compliance, watermarks, and merge/split operations are built-in features that wkhtmltopdf couldn't provide.

Active Development: As .NET 10 and C# 14 adoption increases through 2026, IronPDF's regular updates ensure compatibility with current and future .NET versions.

Async Support: Prevent thread blocking in high-load web applications with native async/await support.

Curtis Chau
Technical Writer

Curtis Chau holds a Bachelor’s degree in Computer Science (Carleton University) and specializes in front-end development with expertise in Node.js, TypeScript, JavaScript, and React. Passionate about crafting intuitive and aesthetically pleasing user interfaces, Curtis enjoys working with modern frameworks and creating well-structured, visually appealing manuals.

...

Read More