URL to PDF
Point this endpoint at any public URL and get back the page as a PDF — not a screenshot stitched together, but a real document with selectable text, working page breaks, and the layout the site actually renders. It exists for the moment you need proof of what a page looked like, or a printable copy of content you do not control.
Run it online
Run this on our servers with your account. Free tools run in your browser; this one bills your KIT balance per the price above.
Why you archive a page instead of its HTML
Sometimes the source is not yours: a competitor's pricing page, a government notice, a partner's terms, a listing you need to keep evidence of before it changes. Saving raw HTML is fragile — external stylesheets rot, scripts stop running, and six months later the file renders as a wall of unstyled text. A PDF freezes the page as it was rendered at fetch time: fonts embedded, layout locked, dated. This endpoint is built for that exact need, where you care about the destination page as the source of truth, not a template you author yourself.
What actually happens when you call it
You POST the target URL to /pdf/from-url, optionally with page size, margins, and a wait condition if the page needs a moment to finish loading. The call returns a task_id right away because fetching and rendering a live site is not instant — DNS, redirects, images, and fonts all take real time. Once the page has fully rendered, we convert it to a PDF and notify you on your webhook, or leave it for pickup at a signed link valid for 24 hours.
A quieter history than it looks
Turning a rendered page into paper-sized output is older than the modern web — browsers have shipped a 'print' function since the 1990s — but doing it headlessly, on demand, over an API, is a newer convenience built on the same rendering engines that power everyday browsing. What used to require opening a browser, waiting, and clicking File then Print now happens as one asynchronous call, which is what makes it usable inside software instead of only inside a human's workflow.
Where it sits in a pipeline
Because each request is independent and reports back over a webhook, you can queue a URL the moment it matters — a new invoice appears in a customer portal, a regulatory page updates, a job listing goes live — and capture it without a person ever opening a browser. Retries happen automatically up to three times if a page is slow or briefly unreachable, and only a page that never loads returns an error. Nothing is charged for a request that fails.
Pricing, access and data handling
The price is $0.040 per request plus $0.001 per page of the resulting PDF, so a single-page snapshot costs about four cents and a long article a few cents more. Calling the endpoint requires prepaid balance — without it you get a 402, which is intentional and keeps the rendering queue fast for everyone with access. The fetched page and the PDF it produces are kept only for the retention window, then deleted, and are never used to train anything.
What you can do with it
Legal and compliance evidence
Capture a competitor's advertised claims, a vendor's published terms, or a government notice exactly as it appeared on a given date, before the page can be edited or taken down.
Reading-later and offline archives
Convert long-form articles or documentation pages into PDFs for a knowledge base, so teammates without internet access, or without an account on the source site, can still read the material.
Automated monitoring snapshots
Fetch a pricing page, a status page, or a public dashboard on a schedule and store each PDF as a dated record, so you can prove what a page showed at any point in time.
Client deliverables from hosted content
Turn a client-facing report or dashboard that only exists as a web page into a PDF you can email or file, without asking anyone to install anything.
FAQ
How do I convert a URL to PDF with an API?
POST the URL to /pdf/from-url and you receive a task_id right away. The finished PDF arrives on your webhook, or you fetch it from a signed link once rendering finishes.
Is there a free tier or free trial for the URL to PDF API?
There's no free tier — free tiers get abused and slow everyone down. Access runs on a prepaid ForHosting KIT balance: top up from $10.00 (it never expires) and each request is charged at its published price, so a call with no balance returns HTTP 402. No subscription, no tokens, no invented credits, and a failed task is never charged.
How much does it cost to convert a web page to PDF?
Pricing is $0.040 per request plus $0.001 per page in the resulting document, so a typical single-page snapshot costs about $0.041.
Does it capture pages that load content dynamically?
Yes — the page is fully rendered, including scripts and styles, before conversion, so content that appears after the initial load is included in the PDF.
Can I convert password-protected or private pages?
The endpoint fetches public URLs; pages behind a login wall that the request cannot reach will not render correctly, so it is best suited to publicly accessible content.
Can I process a large batch of URLs at once?
Yes. Each URL is its own independent task with its own task_id, so you can queue thousands of pages and let each completion webhook trigger the next step, with no polling required.
What happens if the target page fails to load?
The task is retried automatically up to three times, and only then returns a clear error. You are never charged for a request that ultimately fails.
How long is the result available and is my data retained?
The signed link stays valid for 24 hours. After the retention window, the fetched page and the generated PDF are deleted and never used to train anything.
For developers — API access
Everything on this page is available programmatically. This section is for teams who want to wire it into their own systems; everyone else can just use the tool above.
API endpoint
Prefer to automate it? One authenticated POST creates the task; the result comes back by webhook or a signed link. The same capability also runs here on the web, and soon from our app, email and Telegram.
Call it from your stack
curl -X POST https://api.kit.forhosting.com/pdf/from-url \
-H "Authorization: Bearer $KIT_KEY" \
-H "Content-Type: application/json" \
-d '{"pdf":"https://ejemplo.com/documento.pdf"}'const res = await fetch("https://api.kit.forhosting.com/pdf/from-url", {
method: "POST",
headers: {
"Authorization": `Bearer ${process.env.KIT_KEY}`,
"Content-Type": "application/json"
},
body: JSON.stringify({
"pdf": "https://ejemplo.com/documento.pdf"
})
});
const { task_id } = await res.json();import os, requests
res = requests.post(
"https://api.kit.forhosting.com/pdf/from-url",
headers={"Authorization": f"Bearer {os.environ['KIT_KEY']}"},
json={
"pdf": "https://ejemplo.com/documento.pdf"
},
)
task_id = res.json()["task_id"]<?php
$res = file_get_contents("https://api.kit.forhosting.com/pdf/from-url", false, stream_context_create([
"http" => [
"method" => "POST",
"header" => "Authorization: Bearer " . getenv("KIT_KEY") . "\r\nContent-Type: application/json",
"content" => '{"pdf":"https://ejemplo.com/documento.pdf"}',
],
]));
$task = json_decode($res, true);body := bytes.NewBufferString(`{"pdf":"https://ejemplo.com/documento.pdf"}`)
req, _ := http.NewRequest("POST", "https://api.kit.forhosting.com/pdf/from-url", body)
req.Header.Set("Authorization", "Bearer "+os.Getenv("KIT_KEY"))
req.Header.Set("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)Example request
{
"pdf": "https://ejemplo.com/documento.pdf"
}Example response
{
"task_id": "tsk_a1b2c3d4e5f6a1b2c3d4e5f6",
"type": "pdf.from_url",
"status": "queued",
"_links": {
"result": "/tasks/tsk_…/result"
}
}The API is asynchronous: the call returns a task_id immediately and the result arrives by webhook. Polling is capped at 1 req/s per task.
Pricing
Published price — no tokens, no invented credits. A failed task is never charged.
Limits
max_mb | 25 |
max_pages | 200 |
Errors
| HTTP | Code | Meaning |
|---|---|---|
401 | unauthorized | Missing or invalid API key. |
402 | insufficient_balance | Your balance doesn't cover the task price. |
404 | unknown_type | That task type doesn't exist. |
429 | rate_limited | Too many requests. Use the webhook instead of polling. |
413 | input_too_large | The file exceeds the size limit. |
422 | task_failed | The task failed after 3 retries. You are never charged for it. |