Base URL
https://api.html2pdfconverter.comAuthentication
Use your API key on all requests. This key is available in you dashboard settings
x-api-key: <YOUR_API_KEY>Create Conversion Job
Method 1: JSON Body (Small files)
POST /convert
Content-Type: application/json
x-api-key: <YOUR_API_KEY>
{
"url": "https://example.com/page",
"options": {
"format": "A4",
"printBackground": true,
"timeoutMs": 60000
},
"webhookUrl": "https://yourapp.com/webhooks/pdf"
}Method 2: Multipart Upload (Large files)
curl -X POST "$BASE_URL/convert" \
-H "x-api-key: $API_KEY" \
-F "file=@document.html" \
-F "options={"format":"A4","printBackground":true}"File Size Limits by Plan:
- • Free: 5MB | Starter: 10MB | Pro: 25MB
- • Scale: 50MB | Enterprise: 100MB
Multipart uploads are streamed for optimal performance.
HTTP/1.1 202 Accepted
Content-Type: application/json
{
"jobId": "6a1c...f92",
"status": "pending"
}Poll /jobs/:job_id or supply webhookUrl to receive callbacks.
Check Job Status
GET /jobs/:job_id
x-api-key: <YOUR_API_KEY>HTTP/1.1 200 OK
Content-Type: application/json
{
"job_id": "6a1c...f92",
"status": "completed",
"downloadUrl": "https://s3...signed"
}HTTP/1.1 200 OK
Content-Type: application/json
{
"job_id": "6a1c...f92",
"status": "failed",
"errorMessage": "Rendering timeout"
}Webhooks (optional)
If you send webhookUrl, we'll POST a signed JSON payload when the job finishes.
X-PDF-Service-Signature: sha256=<hex>Get your webhook secret from the customer portal dashboard.
Success payload
{
"jobId": "<JOB_ID>",
"status": "completed",
"downloadUrl": "https://s3...signed",
"renderTimeMs": 1234.56
}Failure payload
{
"jobId": "<JOB_ID>",
"status": "failed",
"error": "Rendering timeout"
}Verification Example
const crypto = require('crypto');
function verifyWebhook(req, res) {
const signature = req.headers['x-pdf-service-signature'];
const secret = process.env.PDF_SERVICE_WEBHOOK_SECRET;
const expectedSignature = 'sha256=' + crypto
.createHmac('sha256', secret)
.update(JSON.stringify(req.body))
.digest('hex');
if (signature === expectedSignature) {
console.log('✅ Webhook verified:', req.body);
} else {
res.status(401).send('Invalid signature');
}
}Code Examples
Here are code examples in various languages for creating PDF conversion jobs:
const fetch = require('node-fetch');
async function convertPdfNodeJs(sourceType, sourceContent, apiKey, webhookUrl = null) {
const payload = {
sourceType: sourceType, // "url" or "html"
url: sourceType === "url" ? sourceContent : undefined,
html: sourceType === "html" ? sourceContent : undefined,
options: {
format: "A4",
printBackground: true,
timeoutMs: 60000 // Optional
},
webhookUrl: webhookUrl // Optional
};
try {
const response = await fetch('https://api.html2pdfconverter.com/convert', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'x-api-key': apiKey
},
body: JSON.stringify(payload)
});
if (!response.ok) {
const errorData = await response.json();
throw new Error(errorData.message || 'Failed to create conversion job');
}
const data = await response.json();
console.log('Job created:', data);
return data.jobId;
} catch (error) {
console.error('Error creating conversion job:', error);
throw error;
}
}
// Example usage:
// convertPdfNodeJs('url', 'https://example.com', 'YOUR_API_KEY', 'https://your-webhook-url.com');
// convertPdfNodeJs('html', '<h1>Hello World!</h1>', 'YOUR_API_KEY');
// For large files, use multipart upload:
async function convertPdfMultipart(filePath, apiKey) {
const FormData = require('form-data');
const fs = require('fs');
const fetch = require('node-fetch');
const form = new FormData();
form.append('file', fs.createReadStream(filePath));
form.append('options', JSON.stringify({ format: 'A4', printBackground: true }));
const response = await fetch('https://api.html2pdfconverter.com/convert', {
method: 'POST',
headers: {
'x-api-key': apiKey,
...form.getHeaders()
},
body: form
});
return await response.json();
}
<?php
function convertPdfPhp($sourceType, $sourceContent, $apiKey, $webhookUrl = null) {
$apiUrl = 'https://api.html2pdfconverter.com/convert';
$payload = [
'sourceType' => $sourceType,
'options' => [
'format' => 'A4',
'printBackground' => true,
'timeoutMs' => 60000 // Optional
]
];
if ($sourceType === 'url') {
$payload['url'] = $sourceContent;
} elseif ($sourceType === 'html') {
$payload['html'] = $sourceContent;
} else {
throw new Exception('Invalid sourceType. Must be "url" or "html".');
}
if ($webhookUrl) {
$payload['webhookUrl'] = $webhookUrl;
}
$ch = curl_init($apiUrl);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'POST');
curl_setopt($ch, CURLOPT_HTTPHEADER, [
'Content-Type: application/json',
'x-api-key: ' . $apiKey
]);
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($payload));
$response = curl_exec($ch);
$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);
if ($httpCode !== 202) {
$errorData = json_decode($response, true);
throw new Exception($errorData['message'] ?? 'Failed to create conversion job');
}
$data = json_decode($response, true);
echo 'Job created: ' . print_r($data, true) . "
";
return $data['jobId'];
}
// Example usage:
// try {
// convertPdfPhp('url', 'https://example.com', 'YOUR_API_KEY', 'https://your-webhook-url.com');
// convertPdfPhp('html', '<h1>Hello from PHP!</h1>', 'YOUR_API_KEY');
// } catch (Exception $e) {
// echo 'Error: ' . $e->getMessage() . "
";
// }import requests
import json
def convert_pdf_python(source_type, source_content, api_key, webhook_url=None):
api_url = "https://api.html2pdfconverter.com/convert"
payload = {
"sourceType": source_type,
"options": {
"format": "A4",
"printBackground": True,
"timeoutMs": 60000 # Optional
}
}
if source_type == "url":
payload["url"] = source_content
elif source_type == "html":
payload["html"] = source_content
else:
raise ValueError("Invalid sourceType. Must be 'url' or 'html'.")
if webhook_url:
payload["webhookUrl"] = webhook_url
headers = {
"Content-Type": "application/json",
"x-api-key": api_key
}
try:
response = requests.post(api_url, headers=headers, data=json.dumps(payload))
response.raise_for_status() # Raise an exception for HTTP errors (4xx or 5xx)
data = response.json()
print(f"Job created: {data}")
return data.get("jobId")
except requests.exceptions.HTTPError as http_err:
print(f"HTTP error occurred: {http_err}")
print(f"Response: {response.text}")
raise
except Exception as err:
print(f"Other error occurred: {err}")
raise
# Example usage:
# try:
# convert_pdf_python("url", "https://example.com", "YOUR_API_KEY", "https://your-webhook-url.com")
# convert_pdf_python("html", "<h1>Hello from Python!</h1>", "YOUR_API_KEY")
# except Exception as e:
# print(f"Error: {e}")// Go code example will be added later.import java.io.OutputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import java.nio.charset.StandardCharsets;
import java.util.HashMap;
import java.util.Map;
import com.google.gson.Gson; // You'll need to add Gson to your project dependencies
public class PdfConverter {
private static final String API_URL = "https://api.html2pdfconverter.com/convert";
private static final Gson gson = new Gson();
public static String convertPdfJava(String sourceType, String sourceContent, String apiKey, String webhookUrl) throws Exception {
Map<String, Object> payload = new HashMap<>();
payload.put("sourceType", sourceType);
if (sourceType.equals("url")) {
payload.put("url", sourceContent);
} else if (sourceType.equals("html")) {
payload.put("html", sourceContent);
} else {
throw new IllegalArgumentException("Invalid sourceType. Must be "url" or "html".");
}
Map<String, Object> options = new HashMap<>();
options.put("format", "A4");
options.put("printBackground", true);
options.put("timeoutMs", 60000); // Optional
payload.put("options", options);
if (webhookUrl != null && !webhookUrl.isEmpty()) {
payload.put("webhookUrl", webhookUrl);
}
String jsonPayload = gson.toJson(payload);
URL url = new URL(API_URL);
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
connection.setRequestMethod("POST");
connection.setRequestProperty("Content-Type", "application/json");
connection.setRequestProperty("x-api-key", apiKey);
connection.setDoOutput(true);
try (OutputStream os = connection.getOutputStream()) {
byte[] input = jsonPayload.getBytes(StandardCharsets.UTF_8);
os.write(input, 0, input.length);
}
int responseCode = connection.getResponseCode();
if (responseCode == HttpURLConnection.HTTP_ACCEPTED) {
String responseBody = new String(connection.getInputStream().readAllBytes(), StandardCharsets.UTF_8);
Map<String, String> responseMap = gson.fromJson(responseBody, Map.class);
System.out.println("Job created: " + responseMap);
return responseMap.get("jobId");
} else {
String errorBody = new String(connection.getErrorStream().readAllBytes(), StandardCharsets.UTF_8);
Map<String, String> errorMap = gson.fromJson(errorBody, Map.class);
throw new Exception("API Error (" + responseCode + "): " + errorMap.get("message"));
}
}
public static void main(String[] args) {
// Example usage:
// String apiKey = "YOUR_API_KEY";
// String webhook = "https://your-webhook-url.com";
// try {
// // URL conversion
// String jobIdUrl = convertPdfJava("url", "https://example.com", apiKey, webhook);
// System.out.println("URL Conversion Job ID: " + jobIdUrl);
// // HTML conversion
// String jobIdHtml = convertPdfJava("html", "<h1>Hello from Java!</h1>", apiKey, null);
// System.out.println("HTML Conversion Job ID: " + jobIdHtml);
// } catch (Exception $e) {
// e.printStackTrace();
// }}
require 'net/http'
require 'uri'
require 'json'
def convert_pdf_ruby(source_type, source_content, api_key, webhook_url = nil)
uri = URI.parse('https://api.html2pdfconverter.com/convert')
http = Net::HTTP.new(uri.host, uri.port)
http.use_ssl = true
request = Net::HTTP::Post.new(uri.request_uri, {
'Content-Type' => 'application/json',
'x-api-key' => api_key
})
payload = {
sourceType: source_type,
options: {
format: 'A4',
printBackground: true,
timeoutMs: 60000 # Optional
}
}
if source_type == 'url'
payload[:url] = source_content
elsif source_type == 'html'
payload[:html] = source_content
else
raise ArgumentError, 'Invalid sourceType. Must be "url" or "html".'
end
if webhook_url
payload[:webhookUrl] = webhook_url
end
request.body = payload.to_json
response = http.request(request)
unless response.code == '202'
error_data = JSON.parse(response.body)
raise "API Error (#{response.code}): #{error_data['message'] || 'Failed to create conversion job'}"
end
data = JSON.parse(response.body)
puts "Job created: #{data}"
data['jobId']
end
# Example usage:
# api_key = 'YOUR_API_KEY'
# webhook = 'https://your-webhook-url.com'
# begin
# # URL conversion
# job_id_url = convert_pdf_ruby('url', 'https://example.com', api_key, webhook)
# puts "URL Conversion Job ID: #{job_id_url}"
# # HTML conversion
# job_id_html = convert_pdf_ruby('html', '<h1>Hello from Ruby!</h1>', api_key)
# puts "HTML Conversion Job ID: #{job_id_html}"
# rescue StandardError => e
# puts "Error: #{e.message}"
# endcurl -X POST "https://api.html2pdfconverter.com/convert" -H "Content-Type: application/json" -H "x-api-key: YOUR_API_KEY" -d '{
"sourceType": "url",
"url": "https://example.com",
"options": {"format":"A4","printBackground":true}
}'Troubleshooting Timeouts
PDF conversion can sometimes time out, especially with complex content or slow-loading URLs. Here are some tips to avoid timeouts:
- Optimize HTML/CSS: Keep your HTML clean, minimize large CSS files, and avoid unnecessary JavaScript.
- Efficient Images: Use optimized image formats and sizes.
- Fast URLs: If converting from a URL, ensure the target page loads quickly. Heavy client-side rendering or slow server responses can lead to timeouts.
- Use Webhooks for long jobs: For jobs that might take longer than your plan's timeout, consider using the
webhookUrloption to get an asynchronous notification when the job is complete. This avoids client-side request timeouts. - Adjust
timeoutMs: You can specifyoptions.timeoutMsin your/convertrequest. However, there's a maximum timeout enforced per plan. Refer to your dashboard for plan-specific limits.
AI Integrations (MCP)
You can integrate HTML2PDF Converter directly into your favorite AI tools (like Claude Desktop, Cursor, or other MCP-compatible clients) using our official Model Context Protocol (MCP) server.
This allows your AI to natively generate PDFs and save them to your computer without you having to write any code.
Installation via npx
npx -y @html2pdfconverter/mcp-serverClaude Desktop Configuration
Add the following to your claude_desktop_config.json file:
{
"mcpServers": {
"html2pdf": {
"command": "npx",
"args": ["-y", "@html2pdfconverter/mcp-server"],
"env": {
"HTML2PDF_API_KEY": "YOUR_API_KEY_HERE"
}
}
}
}Note: Replace YOUR_API_KEY_HERE with a real API key generated from your dashboard.