API Documentation
Fill PDF form fields programmatically. Send a template URL and your data — get back a filled PDF in seconds.
Quick Start
Three steps to your first filled PDF.
- Get your API key from your dashboard.
- Host a fillable PDF somewhere publicly accessible (Dropbox, Google Drive, S3, etc.).
- Make a POST request with your template URL and data.
curl -X POST https://www.pdfortless.com/api/pdf/fill \ -H "Authorization: Bearer YOUR_API_KEY" \ -H "Content-Type: application/json" \ -d '{ "template_url": "https://your-site.com/onboarding-form.pdf", "data": { "applicant_name": "Emily Clark", "rent_amount": "1500", "move_in_date": "2026-09-01" } }' \ --output filled-form.pdf
import requests response = requests.post( "https://www.pdfortless.com/api/pdf/fill", headers={"Authorization": "Bearer YOUR_API_KEY"}, json={ "template_url": "https://your-site.com/onboarding-form.pdf", "data": { "applicant_name": "Emily Clark", "rent_amount": "1500", "move_in_date": "2026-09-01" } } ) with open("filled-form.pdf", "wb") as f: f.write(response.content)
const fs = require('fs'); const response = await fetch('https://www.pdfortless.com/api/pdf/fill', { method: 'POST', headers: { 'Authorization': 'Bearer YOUR_API_KEY', 'Content-Type': 'application/json' }, body: JSON.stringify({ template_url: 'https://your-site.com/onboarding-form.pdf', data: { applicant_name: 'Emily Clark', rent_amount: '1500', move_in_date: '2026-09-01' } }) }); const buffer = await response.arrayBuffer(); fs.writeFileSync('filled-form.pdf', Buffer.from(buffer));
$ch = curl_init('https://www.pdfortless.com/api/pdf/fill'); curl_setopt_array($ch, [ CURLOPT_POST => true, CURLOPT_RETURNTRANSFER => true, CURLOPT_HTTPHEADER => [ 'Authorization: Bearer YOUR_API_KEY', 'Content-Type: application/json' ], CURLOPT_POSTFIELDS => json_encode([ 'template_url' => 'https://your-site.com/onboarding-form.pdf', 'data' => [ 'applicant_name' => 'Emily Clark', 'rent_amount' => '1500', 'move_in_date' => '2026-09-01' ] ]) ]); file_put_contents('filled-form.pdf', curl_exec($ch));
Authentication
All API requests require your API key passed as a Bearer token in the Authorization header.
Authorization: Bearer YOUR_API_KEY
Never expose your API key in client-side code or public repositories. Treat it like a password. Regenerate it from your dashboard if it's ever compromised.
Base URL
https://www.pdfortless.com/api
Fill PDF
Fills a PDF template with your data and returns the completed PDF as a binary file.
Request body
| Parameter | Type | Required | Description |
|---|---|---|---|
| template_url | string | required | Public URL of the PDF template to fill. |
| data | object | required | Key-value pairs where each key matches a PDF field name. |
| flatten | boolean | optional | If true, flattens form fields making them non-editable. Default: true. |
Response
Returns the filled PDF as a binary application/pdf file. Save the response body directly to a .pdf file.
Response headers
| Header | Description |
|---|---|
| X-Fields-Filled | Number of fields that were successfully filled. |
| X-Processing-Time-Ms | Time taken to process the PDF in milliseconds. |
| X-File-Size-Kb | Size of the returned PDF in kilobytes. |
Use the Get Fields endpoint to discover exact field names in your PDF before filling.
Get Fields
Inspects a PDF template and returns all fillable field names. Use this to discover field names before calling Fill PDF.
Request body
| Parameter | Type | Required | Description |
|---|---|---|---|
| template_url | string | required | Public URL of the PDF to inspect. |
Response
{
"fieldCount": 6,
"fields": [
{ "name": "applicant_name", "type": "TextField" },
{ "name": "rent_amount", "type": "TextField" },
{ "name": "move_in_date", "type": "TextField" },
{ "name": "pets_allowed", "type": "CheckBox" },
{ "name": "start_date", "type": "Dropdown" },
{ "name": "unit_number", "type": "TextField" }
]
}
Zapier Integration
Automate PDF generation from Google Sheets, Airtable, or any app in Zapier — no code needed.
- Create a new Zap with your data source as the trigger (e.g. Google Sheets "New Row").
- Add a "Webhooks by Zapier" action — search for "Webhooks" and choose Custom Request.
- Configure the request:
- Method:
POST - URL:
https://www.pdfortless.com/api/pdf/fill - Headers:
Authorization: Bearer YOUR_API_KEY - Data: Raw (JSON)
- Method:
- Set the JSON body using Zapier's field mapping to insert values from your trigger data.
- Add a file storage step (Google Drive, Dropbox, etc.) to save the returned PDF.
// Example Zapier JSON body { "template_url": "https://your-site.com/form.pdf", "data": { "applicant_name": "{{Name}}", "start_date": "{{Start Date}}", "move_in_date": "{{MoveIn}}" } }
The API returns a binary PDF file. In Zapier, set Response Type to File to pass it to a storage action.
Make.com Integration
Use Make's HTTP module to call the API and route filled PDFs into any workflow.
- Add an HTTP module — search for "HTTP" and choose Make a Request.
- Set the URL to
https://www.pdfortless.com/api/pdf/fill - Set Method to
POST - Add a header:
Authorization: Bearer YOUR_API_KEY - Set Body Type to Raw, Content Type to
application/json, then paste your JSON payload. - Set Response Type to File — Make will treat the response as a file you can pass to Google Drive, Dropbox, or email.
Make.com's data mapping lets you pull values directly from any previous module — spreadsheets, forms, CRMs, and more.
Error Codes
| Status | Code | Meaning |
|---|---|---|
| 400 | Bad Request | Missing required fields or invalid PDF URL. |
| 401 | Unauthorized | Missing or invalid API key. |
| 402 | Payment Required | Free trial exhausted — add a payment method. |
| 403 | Forbidden | Account is inactive or subscription lapsed. |
| 429 | Too Many Requests | Rate limit exceeded. Slow down requests. |
| 500 | Server Error | Something went wrong on our end. Try again. |
Error response format
{
"error": "Could not download PDF template. Please check the URL."
}
Rate Limits
To ensure fair usage, API requests are rate limited per API key.
If you need higher limits for batch processing, contact us.
Pricing
PDeffortless uses simple pay-per-use pricing with no monthly commitment.