如何使用 C# 將圖像轉換為 PDF
為什麼從CraftMyPDF遷移到IronPDF?
像CraftMyPDF這樣的雲端PDF API引入了基本問題,使其不適合許多生產環境。
雲端PDF API的問題
-
您的資料離開您的系統:每個HTML模板和JSON資料負載都會傳輸到CraftMyPDF的伺服器。 對於發票、合同、醫療記錄或任何敏感的商業資料,這會造成HIPAA、GDPR和SOC2合規風險。
-
網路延遲:每個PDF生成都涉及一次網路往返及排隊和渲染時間(通常以秒計)。 IronPDF在本地以毫秒生成。
-
按PDF成本累積:基於信貸的定價會隨著數量累積—與一次性永久授權相比,高吞吐量工作負載會產生顯著的經常性成本。
-
印刷優化輸出:雲端API通常為印刷優化—減少背景並簡化顏色以節省"墨水"。結果從未看起來像螢幕上的HTML。
- 模板鎖定:CraftMyPDF需要其專有的拖放編輯器。 您不能自由使用標準HTML/CSS。
架構比較
| 方面 | CraftMyPDF | IronPDF |
|---|---|---|
| 資料位置 | 雲端(您的資料離開您的系統) | 本地(資料從不離開) |
| 延遲 | 網路往返+渲染(通常以秒計) | 毫秒 |
| 定價 | 基於信貸的訂閱 | 一次性永久授權 |
| 模板系統 | 專有的拖放 | 任意HTML/CSS/JavaScript |
| 輸出品質 | 印刷優化 | 像素完美螢幕渲染 |
| 離線工作 | 否(需要互聯網) | 是 |
| 合規性 | 資料離開組織 | SOC2/HIPAA友好 |
功能比較
| 功能 | CraftMyPDF | IronPDF |
|---|---|---|
| HTML轉PDF | 通過API模板 | ✅原生 |
| URL到PDF | 通過API | ✅原生 |
| 自訂模板 | 專有編輯器 | ✅任意HTML |
| CSS3支援 | 有限 | ✅全面 |
| JavaScript渲染 | 有限 | ✅全面 |
| 合併/分割PDF | 通過API | ✅原生 |
| 浮水印 | 通過API | ✅原生 |
| 離線工作 | ❌ | ✅ |
| 自主託管 | ❌ | ✅ |
遷移前準備
前提條件
確保您的環境符合以下要求:
- .NET Framework 4.6.2+ or .NET Core 3.1 / .NET 5-9
- Visual Studio 2019+或VS Code與C#擴展
- NuGet包管理器存取 -IronPDF許可證金鑰(免費試用可在 ironpdf.com 獲得)
審核CraftMyPDF使用情況
在您的解決方案目錄中執行這些命令以識別所有CraftMyPDF引用:
# Find all CraftMyPDF usages in your codebase
grep -r "CraftMyPdf\|craftmypdf\|api.craftmypdf.com" --include="*.cs" .
grep -r "X-API-KEY" --include="*.cs" .
# Find API key references
grep -r "your-api-key\|template-id\|template_id" --include="*.cs" .
# Find NuGet package references
grep -r "CraftMyPdf\|RestSharp" --include="*.csproj" .
# Find all CraftMyPDF usages in your codebase
grep -r "CraftMyPdf\|craftmypdf\|api.craftmypdf.com" --include="*.cs" .
grep -r "X-API-KEY" --include="*.cs" .
# Find API key references
grep -r "your-api-key\|template-id\|template_id" --include="*.cs" .
# Find NuGet package references
grep -r "CraftMyPdf\|RestSharp" --include="*.csproj" .
預期的中斷變更
| 更改 | CraftMyPDF | IronPDF | 影響 |
|---|---|---|---|
| 架構 | 雲端REST API | 本地 .NET 程式庫 | 移除HTTP呼叫 |
| 模板 | 專有編輯器 | 標準HTML | 將模板轉換為HTML |
| API金鑰 | 每次呼叫都需要 | 啟動時授權 | 移除API金鑰處理 |
| 異步模式 | 必須(HTTP) | 可選 | 如需則移除await |
| 錯誤處理 | HTTP狀態碼 | 異常 | 更改try/catch模式 |
| 資料綁定 | JSON模板 | 字串插值 | 簡化資料綁定 |
逐步遷移過程
步驟1:更新NuGet包
移除HTTP客戶端程式庫並安裝IronPDF:
# Remove RestSharp HTTP client
dotnet remove package RestSharp
# Install IronPDF
dotnet add package IronPdf
# Remove RestSharp HTTP client
dotnet remove package RestSharp
# Install IronPDF
dotnet add package IronPdf
步驟 2:更新命名空間引用
使用IronPDF替換HTTP客戶端命名空間:
// Remove these
using RestSharp;
using System.IO;
// Add this
using IronPdf;
// Remove these
using RestSharp;
using System.IO;
// Add this
using IronPdf;
Imports IronPdf
步驟3:配置授權(啟動時一次)
用單一授權配置替換每次請求的API金鑰標頭:
// Add at application startup (Program.cs or Global.asax)
// This replaces all X-API-KEY headers
IronPdf.License.LicenseKey = "YOUR-LICENSE-KEY";
// Add at application startup (Program.cs or Global.asax)
// This replaces all X-API-KEY headers
IronPdf.License.LicenseKey = "YOUR-LICENSE-KEY";
' Add at application startup (Program.vb or Global.asax)
' This replaces all X-API-KEY headers
IronPdf.License.LicenseKey = "YOUR-LICENSE-KEY"
完整 API 遷移參考
API端點映射
| CraftMyPDF | IronPDF |
|---|---|
POST /v1/create |
renderer.RenderHtmlAsPdf(html) |
X-API-KEY 標頭 |
License.LicenseKey = "..." |
template_id |
標準HTML字串 |
{%name%} 佔位符 |
$"{name}" C#插值 |
POST /v1/merge |
PdfDocument.Merge(pdfs) |
POST /v1/add-watermark |
pdf.ApplyWatermark(html) |
| Webhook回調 | 不需要 |
| 速率限制 | 不適用 |
配置映射
| CraftMyPDF 選項 | IronPDF等價 |
|---|---|
template_id |
HTML字串 |
data JSON |
C#插值 |
page_size: "A4" |
PaperSize = PdfPaperSize.A4 |
orientation: "landscape" |
PaperOrientation = Landscape |
margin_top: 20 |
MarginTop = 20 |
header |
HtmlHeader |
footer |
HtmlFooter |
程式碼遷移範例
HTML到PDF轉換
最常見的操作顯示了從雲端API到本地渲染的基本架構轉變。
CraftMyPDF 的實施:
// NuGet: Install-Package RestSharp
using System;
using RestSharp;
using System.IO;
class Program
{
static void Main()
{
var client = new RestClient("https://api.craftmypdf.com/v1/create");
var request = new RestRequest(Method.POST);
request.AddHeader("X-API-KEY", "your-api-key");
request.AddJsonBody(new
{
template_id = "your-template-id",
data = new
{
html = "<h1>Hello World</h1><p>This is a PDF from HTML</p>"
}
});
var response = client.Execute(request);
File.WriteAllBytes("output.pdf", response.RawBytes);
}
}
// NuGet: Install-Package RestSharp
using System;
using RestSharp;
using System.IO;
class Program
{
static void Main()
{
var client = new RestClient("https://api.craftmypdf.com/v1/create");
var request = new RestRequest(Method.POST);
request.AddHeader("X-API-KEY", "your-api-key");
request.AddJsonBody(new
{
template_id = "your-template-id",
data = new
{
html = "<h1>Hello World</h1><p>This is a PDF from HTML</p>"
}
});
var response = client.Execute(request);
File.WriteAllBytes("output.pdf", response.RawBytes);
}
}
Imports System
Imports RestSharp
Imports System.IO
Module Program
Sub Main()
Dim client As New RestClient("https://api.craftmypdf.com/v1/create")
Dim request As New RestRequest(Method.POST)
request.AddHeader("X-API-KEY", "your-api-key")
request.AddJsonBody(New With {
.template_id = "your-template-id",
.data = New With {
.html = "<h1>Hello World</h1><p>This is a PDF from HTML</p>"
}
})
Dim response = client.Execute(request)
File.WriteAllBytes("output.pdf", response.RawBytes)
End Sub
End Module
IronPDF實現:
// NuGet: Install-Package IronPdf
using System;
using IronPdf;
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 System;
using IronPdf;
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");
}
}
Imports System
Imports IronPdf
Class Program
Shared Sub Main()
Dim renderer = New ChromePdfRenderer()
Dim pdf = renderer.RenderHtmlAsPdf("<h1>Hello World</h1><p>This is a PDF from HTML</p>")
pdf.SaveAs("output.pdf")
End Sub
End Class
IronPDF消除了RestClient設置、API金鑰標頭、模板ID和HTTP響應處理——將15行雲端操作縮減到4行本地程式碼。 有關更多選項,請參閱HTML轉PDF文件。
URL 到 PDF 轉換
CraftMyPDF 的實施:
// NuGet: Install-Package RestSharp
using System;
using RestSharp;
using System.IO;
class Program
{
static void Main()
{
var client = new RestClient("https://api.craftmypdf.com/v1/create");
var request = new RestRequest(Method.POST);
request.AddHeader("X-API-KEY", "your-api-key");
request.AddJsonBody(new
{
template_id = "your-template-id",
data = new
{
url = "https://example.com"
},
export_type = "file" // "file" returns binary PDF; "json" returns a CDN URL
});
var response = client.Execute(request);
File.WriteAllBytes("webpage.pdf", response.RawBytes);
}
}
// NuGet: Install-Package RestSharp
using System;
using RestSharp;
using System.IO;
class Program
{
static void Main()
{
var client = new RestClient("https://api.craftmypdf.com/v1/create");
var request = new RestRequest(Method.POST);
request.AddHeader("X-API-KEY", "your-api-key");
request.AddJsonBody(new
{
template_id = "your-template-id",
data = new
{
url = "https://example.com"
},
export_type = "file" // "file" returns binary PDF; "json" returns a CDN URL
});
var response = client.Execute(request);
File.WriteAllBytes("webpage.pdf", response.RawBytes);
}
}
Imports System
Imports RestSharp
Imports System.IO
Module Program
Sub Main()
Dim client As New RestClient("https://api.craftmypdf.com/v1/create")
Dim request As New RestRequest(Method.POST)
request.AddHeader("X-API-KEY", "your-api-key")
request.AddJsonBody(New With {
.template_id = "your-template-id",
.data = New With {
.url = "https://example.com"
},
.export_type = "file" ' "file" returns binary PDF; "json" returns a CDN URL
})
Dim response = client.Execute(request)
File.WriteAllBytes("webpage.pdf", response.RawBytes)
End Sub
End Module
IronPDF實現:
// NuGet: Install-Package IronPdf
using System;
using IronPdf;
class Program
{
static void Main()
{
var renderer = new ChromePdfRenderer();
var pdf = renderer.RenderUrlAsPdf("https://example.com");
pdf.SaveAs("webpage.pdf");
}
}
// NuGet: Install-Package IronPdf
using System;
using IronPdf;
class Program
{
static void Main()
{
var renderer = new ChromePdfRenderer();
var pdf = renderer.RenderUrlAsPdf("https://example.com");
pdf.SaveAs("webpage.pdf");
}
}
Imports System
Imports IronPdf
Class Program
Shared Sub Main()
Dim renderer = New ChromePdfRenderer()
Dim pdf = renderer.RenderUrlAsPdf("https://example.com")
pdf.SaveAs("webpage.pdf")
End Sub
End Class
IronPDF的 RenderUrlAsPdf 方法捕捉完整網頁,包括JavaScript渲染的內容。 有關更多選項,請參閱URL轉PDF文件。
頭部和尾部
CraftMyPDF 的實施:
// NuGet: Install-Package RestSharp
using System;
using RestSharp;
using System.IO;
class Program
{
static void Main()
{
var client = new RestClient("https://api.craftmypdf.com/v1/create");
var request = new RestRequest(Method.POST);
request.AddHeader("X-API-KEY", "your-api-key");
request.AddJsonBody(new
{
template_id = "your-template-id",
data = new
{
html = "<h1>Document Content</h1>",
header = "<div>Page Header</div>",
footer = "<div>Page {page} of {total_pages}</div>"
}
});
var response = client.Execute(request);
File.WriteAllBytes("document.pdf", response.RawBytes);
}
}
// NuGet: Install-Package RestSharp
using System;
using RestSharp;
using System.IO;
class Program
{
static void Main()
{
var client = new RestClient("https://api.craftmypdf.com/v1/create");
var request = new RestRequest(Method.POST);
request.AddHeader("X-API-KEY", "your-api-key");
request.AddJsonBody(new
{
template_id = "your-template-id",
data = new
{
html = "<h1>Document Content</h1>",
header = "<div>Page Header</div>",
footer = "<div>Page {page} of {total_pages}</div>"
}
});
var response = client.Execute(request);
File.WriteAllBytes("document.pdf", response.RawBytes);
}
}
Imports System
Imports RestSharp
Imports System.IO
Module Program
Sub Main()
Dim client As New RestClient("https://api.craftmypdf.com/v1/create")
Dim request As New RestRequest(Method.POST)
request.AddHeader("X-API-KEY", "your-api-key")
request.AddJsonBody(New With {
.template_id = "your-template-id",
.data = New With {
.html = "<h1>Document Content</h1>",
.header = "<div>Page Header</div>",
.footer = "<div>Page {page} of {total_pages}</div>"
}
})
Dim response = client.Execute(request)
File.WriteAllBytes("document.pdf", response.RawBytes)
End Sub
End Module
IronPDF實現:
// NuGet: Install-Package IronPdf
using System;
using IronPdf;
using IronPdf.Rendering;
class Program
{
static void Main()
{
var renderer = new ChromePdfRenderer();
renderer.RenderingOptions.TextHeader = new TextHeaderFooter()
{
CenterText = "Page Header"
};
renderer.RenderingOptions.TextFooter = new TextHeaderFooter()
{
CenterText = "Page {page} of {total-pages}"
};
var pdf = renderer.RenderHtmlAsPdf("<h1>Document Content</h1>");
pdf.SaveAs("document.pdf");
}
}
// NuGet: Install-Package IronPdf
using System;
using IronPdf;
using IronPdf.Rendering;
class Program
{
static void Main()
{
var renderer = new ChromePdfRenderer();
renderer.RenderingOptions.TextHeader = new TextHeaderFooter()
{
CenterText = "Page Header"
};
renderer.RenderingOptions.TextFooter = new TextHeaderFooter()
{
CenterText = "Page {page} of {total-pages}"
};
var pdf = renderer.RenderHtmlAsPdf("<h1>Document Content</h1>");
pdf.SaveAs("document.pdf");
}
}
Imports System
Imports IronPdf
Imports IronPdf.Rendering
Module Program
Sub Main()
Dim renderer = New ChromePdfRenderer()
renderer.RenderingOptions.TextHeader = New TextHeaderFooter() With {
.CenterText = "Page Header"
}
renderer.RenderingOptions.TextFooter = New TextHeaderFooter() With {
.CenterText = "Page {page} of {total-pages}"
}
Dim pdf = renderer.RenderHtmlAsPdf("<h1>Document Content</h1>")
pdf.SaveAs("document.pdf")
End Sub
End Module
IronPDF支持像 {page} 和 {total-pages} 這樣的佔位符標記,用於動態頁碼。 欲了解更多選項,請參見 頁眉和頁腳文件。
模板變數轉換
CraftMyPDF使用的專有模板佔位符必須轉換為C#字串插值:
CraftMyPDF 範例:
// CraftMyPDF template variables
request.AddJsonBody(new
{
template_id = "invoice-template",
data = new
{
customer = "John Doe",
amount = "$1,000",
items = invoiceItems
}
});
// CraftMyPDF template variables
request.AddJsonBody(new
{
template_id = "invoice-template",
data = new
{
customer = "John Doe",
amount = "$1,000",
items = invoiceItems
}
});
IronPDF模式:
// C# string interpolation
var html = $@"
<html>
<body>
<h1>Invoice</h1>
<p>Customer: {customerName}</p>
<p>Amount: {amount}</p>
{GenerateItemsTable(invoiceItems)}
</body>
</html>";
var pdf = renderer.RenderHtmlAsPdf(html);
// C# string interpolation
var html = $@"
<html>
<body>
<h1>Invoice</h1>
<p>Customer: {customerName}</p>
<p>Amount: {amount}</p>
{GenerateItemsTable(invoiceItems)}
</body>
</html>";
var pdf = renderer.RenderHtmlAsPdf(html);
Dim html As String = $"
<html>
<body>
<h1>Invoice</h1>
<p>Customer: {customerName}</p>
<p>Amount: {amount}</p>
{GenerateItemsTable(invoiceItems)}
</body>
</html>"
Dim pdf = renderer.RenderHtmlAsPdf(html)
關鍵遷移注意事項
移除所有HTTP程式碼
最顯著的變化是消除網路依賴性。 IronPDF在本地運行—無需RestClient,無API呼叫,無響應處理:
// CraftMyPDF - HTTP required
var client = new RestClient("https://api.craftmypdf.com/v1/create");
var request = new RestRequest(Method.POST);
request.AddHeader("X-API-KEY", "your-api-key");
var response = await client.ExecuteAsync(request);
//IronPDF- no HTTP
var pdf = renderer.RenderHtmlAsPdf(html);
// CraftMyPDF - HTTP required
var client = new RestClient("https://api.craftmypdf.com/v1/create");
var request = new RestRequest(Method.POST);
request.AddHeader("X-API-KEY", "your-api-key");
var response = await client.ExecuteAsync(request);
//IronPDF- no HTTP
var pdf = renderer.RenderHtmlAsPdf(html);
Imports RestSharp
' CraftMyPDF - HTTP required
Dim client As New RestClient("https://api.craftmypdf.com/v1/create")
Dim request As New RestRequest(Method.POST)
request.AddHeader("X-API-KEY", "your-api-key")
Dim response = Await client.ExecuteAsync(request)
' IronPDF- no HTTP
Dim pdf = renderer.RenderHtmlAsPdf(html)
移除速率限制程式碼
CraftMyPDF施加API速率限制,需要重試邏輯。IronPDF無限制:
// CraftMyPDF - needed to avoid 429 errors
await Task.Delay(100);
if (response.StatusCode == TooManyRequests) { /* retry */ }
//IronPDF- no limits, just generate
var pdf = renderer.RenderHtmlAsPdf(html);
// Remove all rate limit code!
// CraftMyPDF - needed to avoid 429 errors
await Task.Delay(100);
if (response.StatusCode == TooManyRequests) { /* retry */ }
//IronPDF- no limits, just generate
var pdf = renderer.RenderHtmlAsPdf(html);
// Remove all rate limit code!
移除Webhook處理程式
CraftMyPDF使用異步webhook來完成PDF。IronPDF是同步的—PDF立即準備好:
// CraftMyPDF - webhook callback required
// POST with webhook_url, wait for callback
//IronPDF- PDF ready immediately
var pdf = renderer.RenderHtmlAsPdf(html);
pdf.SaveAs("output.pdf");
// No callback needed!
// CraftMyPDF - webhook callback required
// POST with webhook_url, wait for callback
//IronPDF- PDF ready immediately
var pdf = renderer.RenderHtmlAsPdf(html);
pdf.SaveAs("output.pdf");
// No callback needed!
' CraftMyPDF - webhook callback required
' POST with webhook_url, wait for callback
' IronPDF- PDF ready immediately
Dim pdf = renderer.RenderHtmlAsPdf(html)
pdf.SaveAs("output.pdf")
' No callback needed!
預設同步
如果只是為了HTTP呼叫,移除async/await模式:
// CraftMyPDF - async required
var response = await client.ExecuteAsync(request);
//IronPDF- sync by default (async available if needed)
var pdf = renderer.RenderHtmlAsPdf(html);
// CraftMyPDF - async required
var response = await client.ExecuteAsync(request);
//IronPDF- sync by default (async available if needed)
var pdf = renderer.RenderHtmlAsPdf(html);
' CraftMyPDF - async required
Dim response = Await client.ExecuteAsync(request)
' IronPDF- sync by default (async available if needed)
Dim pdf = renderer.RenderHtmlAsPdf(html)
後遷移檢查清單
完成程式碼遷移後,請驗證以下內容:
- 執行所有PDF生成測試
- 比較輸出質量(IronPDF的Chromium引擎渲染像素完美)
- 測量性能提升(毫秒 vs. 秒)
- 驗證所有模板正確轉換
- 測試無速率限制的批處理
- 在所有目標環境中測試
- 更新 CI/CD 管道
- 取消CraftMyPDF訂閱
- 從密碼/配置中移除API金鑰
其他資源
從CraftMyPDF遷移到IronPDF消除了雲端依賴性、網路延遲、按PDF成本和模板鎖定,並提供像素完美的Chromium渲染,可在離線環境中運行。從REST API呼叫轉換到本地方法調用,簡化了您的程式碼庫,並將敏感文件資料保存在您的基礎設施中。

