Converts HTML or Markdown into a PDF file using headless Chromium (PuppeteerSharp) and Markdig, with page layout, header/footer, and margin control.
[!NOTE] This package is a fork of Markdown2Pdf 2.x — see THIRD-PARTY-NOTICES.md for the upstream attribution. Several option types carried over from upstream are not wired into the current
PdfGeneratorpipeline — the feature pages below mark exactly which options affect the output today.
ConvertMarkdownFileAsync("notes.md") writes notes.pdf next to it — no template engine, no browser lifecycle, no temp-file bookkeeping in your code.ChromePath configured, the first conversion downloads a matching build through PuppeteerSharp, so a container needs no browser baked in.Reach for it to turn Markdown documentation, generated reports, or arbitrary HTML into a downloadable PDF.
Use a .NET 10 console project. Install the package, then replace Program.cs with the example.
dotnet new console -f net10.0 -n PdfDemo
cd PdfDemo
dotnet add package DKNet.Svc.PdfGenerators
echo "# Hello PDF" > notes.md
using DKNet.Svc.PdfGenerators;
using DKNet.Svc.PdfGenerators.Options;
using Microsoft.Extensions.DependencyInjection;
var services = new ServiceCollection();
services.AddPdfGenerator(new PdfGeneratorOptions
{
MarginOptions = new MarginOptions { Top = "2cm", Bottom = "2cm", Left = "1.5cm", Right = "1.5cm" }
});
await using var provider = services.BuildServiceProvider();
var generator = provider.GetRequiredService<IPdfGenerator>();
var path = await generator.ConvertMarkdownFileAsync("notes.md", "reports/monthly.pdf");
Console.WriteLine(path);
Run with dotnet run. AddPdfGenerator(options) registers a factory for a
singleton IPdfGenerator, so the PdfGenerator is built on first resolve; the call is idempotent, and the
options passed to the first call are the ones the instance keeps for the process lifetime. The first conversion in a fresh environment downloads a Chromium build via
PuppeteerSharp’s BrowserFetcher unless ChromePath points at an existing install — expect a one-time delay.
PdfGeneratorSetup.AddPdfGenerator registers one PdfGenerator as a singleton; it launches Chromium on first use
and relaunches it only if the process disconnects. Not pictured: ThemeService, TableOfContentsCreator and
ModuleService exist in the package but are never constructed by PdfGenerator, and there is no page or browser
pool — every conversion opens and closes its own Chromium page.
The conversion is short, and the diagram is mostly useful for what it does not contain — there is no theme,
module, table-of-contents, or metadata stage between Markdig and Chromium. PrintBackground is always true and
the page renders with the screen media type, so @media print CSS rules never apply.
SerializableOptions but never reach the rendered output.FileInfo, so the natural next step is IBlobService.SaveAsync with BinaryData.FromStream(File.OpenRead(path)).