Watermark a PDF
Send a PDF and a line of text, and every page comes back stamped — diagonally, semi-transparent, sitting above the content but never obscuring it. The PDF watermark API exists for one job: marking documents at scale so nobody has to open Acrobat and repeat the same manual step across a hundred files.
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.
The problem it quietly solves
Legal teams, publishers, HR departments and design studios hit the same wall: a document leaves your control the moment you send it, and there is no way to say DRAFT, CONFIDENTIAL, or a recipient's name on the page without a tedious manual pass. Doing it by hand is fine for one file and unbearable for a batch. This endpoint takes the repetitive part — open, stamp every page, flatten, save — and turns it into a single API call that runs the same whether the PDF has two pages or two hundred.
How the call behaves
You POST your text and the source document to /pdf/watermark-text and immediately receive a task_id. It runs asynchronously on our global edge, so your request never blocks on a large file. When the stamp is done, the finished PDF is delivered to your signed webhook, or you fetch it from a signed link valid for 24 hours. You control the wording and where it sits, while the engine handles page geometry so the text lands consistently on portrait, landscape and mixed-size pages.
Why text watermarks, specifically
PDF has carried the notion of an overlay for decades, and a text watermark is its most honest version: real text rendered into the page, not a fragile note a viewer might hide. Unlike an image stamp, a line of text stays crisp at any zoom and weighs almost nothing. That is exactly what you want for status marking — a COPY or an INTERNAL USE ONLY that survives printing, screenshots and forwarding, and reads clearly instead of hiding in metadata nobody checks.
Built to sit inside a pipeline
Because it is asynchronous and priced per page, this fits naturally at the end of a document workflow — right after a contract is generated, an invoice rendered, or a report exported. Point the webhook at your storage handler and stamped files arrive without polling. A failed task is never charged: the system retries three times with backoff, and if it still cannot process the file you get a clear error instead of a silent bill. That makes it safe to wire into a flow and forget.
Access and pricing, plainly
The rate is published: $0.002 per request, billed by the page, with no tokens and no invented credits. There is no free tier — access needs prepaid balance, and a call without it returns a clean 402 rather than a degraded result. That is deliberate: staying paid-only keeps the service fast and free of the abuse that plagues open endpoints. Your documents are deleted after the retention window and never used to train anything.
What you can do with it
Stamp every contract draft before it circulates
A law firm generates redlined agreements from a template and pipes each one through the endpoint to stamp DRAFT — NOT FOR EXECUTION on every page, so no version leaves the office looking final by accident.
Personalize confidential reports per recipient
A research provider watermarks each downloaded PDF with the subscriber's email and CONFIDENTIAL, creating a per-page trail that discourages redistribution of paid analysis.
Mark invoices and statements as copies
An accounting platform stamps DUPLICATE across reissued invoices automatically, so a reprinted document is never mistaken for the original when a client requests another copy.
Flag pre-release documentation
A publisher runs review PDFs through the API to overlay UNCORRECTED PROOF on every page before sending galleys to critics, keeping unfinished text visibly distinct from the shipped edition.
FAQ
How do I add a text watermark to a PDF with an API?
POST your PDF and the text you want to the /pdf/watermark-text endpoint. You get back a task_id, and the stamped file arrives at your webhook or a signed link once the pdf watermark api finishes processing every page.
Is the PDF watermark API free?
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.
Does it stamp every page or just the first one?
Every page. The text is applied across the whole document, and pages are billed individually, so a ten-page file is stamped and priced as ten pages.
Can I put a diagonal watermark like DRAFT or CONFIDENTIAL?
Yes — that is exactly what this is built for. Send any short line of text such as DRAFT, CONFIDENTIAL, or COPY, and it is rendered across each page as a semi-transparent overlay above the existing content.
How do I watermark PDFs in bulk?
Call the endpoint once per document; because it is asynchronous, you can fire many requests in parallel and let the webhooks report back as each file finishes. There is no queue to babysit and no polling required.
Will the watermark reduce the quality of my PDF?
No. Text is rendered as vector text into the page, so it stays sharp at any zoom and adds almost nothing to the file size. The original content underneath is untouched.
What happens if a file fails to process?
The task retries three times with backoff. If it still cannot be completed you receive a clear error and are not charged — failed tasks are never billed.
How long can I download the finished file?
A signed link is valid for 24 hours, and a signed webhook delivery is recommended for automation. After the retention window your documents 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/watermark-text \
-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/watermark-text", {
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/watermark-text",
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/watermark-text", 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/watermark-text", 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.watermark_text",
"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. |