WebP to PDF API
POST a WebP to /v2/convert/webp/to/pdf and get a one-page PDF with the decoded image on it, stood upright when its EXIF data says so. Transparency is kept as a soft mask, and the page takes the image's size at 96 pixels per inch, plus any margins, unless you name a PageSize.
- Endpoint
- POST /v2/
convert/ webp/ to/ pdf - Accepts
- webp
- Sample timing
- 7 ms median of 5 runsHow we measure
- Request size
- Up to 10 MB on the Free plan or 100 MB on paid plans, all files together
Request and response
Every sample below ran against the API before this page was published. Set PDFCONVERSIONAPI_KEY to your key and run it as is.
curl -sS -X POST \
https://api.pdfconversionapi.com/v2/convert/webp/to/pdf \
-H "Authorization: Bearer $PDFCONVERSIONAPI_KEY" \
-F File=@guest-badge.webp \
--form-string FileName=guest-pass-0381 \
-o response.json
# FileData is base64. Save the first file in converted/,
# or print the JSON error.
if jq -e '.Files' response.json > /dev/null; then
mkdir -p converted
name=$(jq -r '.Files[0].FileName' response.json)
jq -r '.Files[0].FileData' response.json \
| base64 --decode > "converted/$name"
else
cat response.json
fiimport base64
import os
import requests
key = os.environ["PDFCONVERSIONAPI_KEY"]
response = requests.post(
"https://api.pdfconversionapi.com/v2/convert/webp/to/pdf",
headers={"Authorization": f"Bearer {key}"},
files=[("File", open("guest-badge.webp", "rb"))],
data={
"FileName": "guest-pass-0381",
},
timeout=180,
)
result = response.json()
if not response.ok:
raise SystemExit(f"{result['Code']}: {result['Message']}")
os.makedirs("converted", exist_ok=True)
for file in result["Files"]:
path = os.path.join("converted", file["FileName"])
with open(path, "wb") as out:
out.write(base64.b64decode(file["FileData"]))
print(path, file["FileSize"], "bytes")
import { mkdir, readFile, writeFile } from "node:fs/promises";
import { join } from "node:path";
const form = new FormData();
const file = "guest-badge.webp";
form.append("File", new Blob([await readFile(file)]), file);
form.append("FileName", "guest-pass-0381");
const url = "https://api.pdfconversionapi.com/v2/convert/webp/to/pdf";
const key = process.env.PDFCONVERSIONAPI_KEY;
const response = await fetch(url, {
method: "POST",
headers: { Authorization: `Bearer ${key}` },
body: form,
});
const result = await response.json();
if (!response.ok) {
throw new Error(`${result.Code}: ${result.Message}`);
}
await mkdir("converted", { recursive: true });
for (const file of result.Files) {
const path = join("converted", file.FileName);
await writeFile(path, Buffer.from(file.FileData, "base64"));
console.log(path, file.FileSize, "bytes");
}
{
"ConversionCost": 1,
"ConversionTime": 0.007,
"Files": [
{
"FileName": "guest-pass-0381.pdf",
"FileExt": "pdf",
"FileSize": 53679,
"FileData": "JVBERi0xLjcKJYCAgIAKMSAw…"
}
]
}Response from our test run on 2026-11-03. ConversionTime shows the median of 5 runs. FileData is shortened here; the real response carries the whole file as base64.
The sample, converted
The same file the code sends. Download the input and the output and compare them yourself.

- Input
- guest-badge.webp (9.4 KB)
- Output
- guest-pass-0381.pdf (52 KB)
- Source
- A guest pass for a made-up trade show that we drew for this page, saved as a lossy WebP with a transparent background and a soft shadow. (CC0-1.0). How it was made
- Made by
- 2026-11-04, API build
9eeeb0640aba
Parameters
Send these as form fields next to the file. Names are case-insensitive. If you set one of the documented options below that we don't support yet, the request fails with a 400 that names it instead of returning a file made without it.
| Parameter | What it does |
|---|---|
PageSizeenum, default default | letter made a 612 × 792 pt page with the badge centered at its own size; default and auto give a 300 × 195 pt page for the 400 × 260 badge.Values: default, auto, a3, a4, a5, letter, legal |
PageOrientationenum, default default | landscape turns a named page sideways: A4 landscape is 841.89 × 595.28 pt. No effect without PageSize.Values: default, portrait, landscape |
Rotateinteger | Clockwise turn in whole degrees. 90 and -90 both stand the badge on a 195 × 300 pt page, facing opposite ways; 30 sized the page to 357.31 × 318.87 pt around the tilted badge, soft mask intact. Empty follows the WebP's EXIF orientation, and 0 overrides it.Values: -360 to 360 |
MarginHorizontalinteger, default 0 | Space in millimeters to the left and right. 12 made the default page 368.03 pt wide instead of 300. On Letter, 100 leaves 45.07 pt across, so the badge was scaled down to 45.07 × 29.3 pt.Values: 0 to 500 (mm) |
MarginVerticalinteger, default 0 | Space in millimeters above and below: 12 gave a 263.03 pt tall page with the badge 34.02 pt above the bottom edge. 110 on A5 leaves no height for the image and returns 400.Values: 0 to 500 (mm) |
FileNamestring | Name of the PDF. The sample sends guest-pass-0381 and receives guest-pass-0381.pdf. |
StoreFileboolean, default false | true keeps the PDF for 3 hours and returns a link in Files[].Url. |
Not supported yet
Setting one of these to anything but its default returns 400.
| Option | What to do instead |
|---|---|
ColorSpace | The image is stored as RGB with a gray soft mask; gray or CMYK pages can't be requested. TrueColors is taken as default and gives the same file. |
ColorProfile | Only default; a profile inside the WebP is not carried over. |
Pdfa | true returns 400. Use /v2/convert/pdf/to/pdfa on the result. |
What carries over, and what doesn't
Kept
- The decoded pixels: the PDF's RGB image and its soft mask together equal the decoded WebP exactly, alpha included.
- Soft transparency. The 11,188 partly transparent shadow and edge pixels (alpha 1 to 106) keep their alpha in a DeviceGray soft mask.
- The image size: 400 × 260 pixels on a 300 × 195 pt page.
- EXIF orientation: 300 × 200 WebPs tagged 6 and 8 were stood upright on 150 × 225 pt pages, tag 3 was turned half way and tag 2 mirrored.
- The soft mask on a turned page: with
Rotate=90,180or30the badge kept its 2,160-byte mask and the same 49,720-byte color stream.
Lost or not yet supported
- Small file size. The 9,596-byte lossy WebP became a 53,679-byte PDF, because the decoded pixels are stored losslessly (49,720 bytes of RGB plus 2,160 bytes of mask).
- Frames after the first: an animated WebP gives a one-page PDF.
- The WebP's ICC profile and its EXIF and XMP chunks. A WebP with a 588-byte sRGB profile gave a plain DeviceRGB image, and a WebP's own XMP text was absent from the PDF, whose only metadata is its own XMP packet.
- Text: the badge's words are part of the picture and can't be searched until you run OCR.
Limits
- One WebP per request; combine several images with
/v2/convert/images/to/pdf(up to 50). - Requests up to 10 MB on the Free plan or 100 MB on paid plans, all files and fields together.
- An image above 100,000,000 pixels returns 413.
ImageWidthand similar image options are not used here; scale with/v2/convert/webp/to/pngfirst.Rotatemust be a whole number from -360 to 360 and each margin 0 to 500 mm:Rotate=400andMarginVertical=600return 400.- Conversions run for at most 120 seconds before a 504.
Where teams use it
Printable passes, tickets and badges
Event passes, coupons and tickets can come as transparent WebP images. Wrap one in a PDF to print it or attach it to an e-mail, with the soft shadow intact, and add margins in millimeters for a blank border to cut along.
Web images in document workflows
Archives, e-signature tools and print queues may accept PDF but not WebP. A one-page PDF per image fits those systems without a lossy re-encode.
Questions
Why is the PDF bigger than the WebP?
The PDF holds the decoded image with lossless Flate compression rather than the original WebP data. For the badge that is 49,720 bytes of RGB and a 2,160-byte alpha mask, so 53,679 bytes in all, against 9,596 for the WebP.
What happens to the transparent background?
It stays transparent. The alpha channel becomes a soft mask, so viewers show the page color, usually white, through the clear areas, and the drop shadow fades as it did in the WebP.
How big is the page?
By default the page matches the image at 96 pixels per inch: 400 × 260 pixels gives 300 × 195 points. With PageSize=letter or a4 the image is centered at that size, never enlarged.
Is AlphaChannel needed to keep transparency?
No. Transparency is always kept for WebP. AlphaChannel is not an option for this route and is ignored: AlphaChannel=true gave the same 53,679-byte file.
Can I turn the badge or put a border around it?
Yes. Rotate turns it clockwise and the page is sized to the turned image, so Rotate=90 gives a 195 × 300 pt page. MarginHorizontal and MarginVertical add white space in millimeters; with a named PageSize, a badge that no longer fits between them is scaled down.
My WebP shows upright in a browser. Will the PDF match?
Yes, if the uprightness comes from an EXIF orientation tag: with Rotate empty the PDF applies it, so a sideways-stored 300 × 200 WebP tagged 6 gave a 150 × 225 pt portrait page. Our WebP to PNG, JPG and other image conversions turn the pixels by the tag too, but there Rotate=0 does not switch that off.
Convert your first WebP file in a minute.