List PDF form fields
A PDF can look like a simple page while carrying a structured form beneath the visible design.
Run — free
Runs in your browser. Free, unlimited — your data never leaves this page.
This capability reads that form structure and returns a clean inventory of every field, including its complete name, recognized field type, and current value. It handles the common AcroForm controls used for applications, questionnaires, approvals, and intake documents. Processing is deterministic and local to the parser: there are no network requests, model guesses, or random results. If the supplied document is not a PDF, is malformed, or contains no form fields, the request returns a clear input error instead of an empty result that could be mistaken for success.
Inspect the real structure behind a PDF form
Interactive PDF forms store controls separately from the words and lines painted on each page. A field may have an internal name such as customer.address.postcode even when the page only shows the label “Postal code.” This capability follows the document catalog to its AcroForm dictionary, walks the field tree, applies inherited properties, and returns terminal fields in document order. Each result contains the full field name, a normalized type, and the value currently stored in the PDF. Text boxes, checkboxes, radio groups, dropdowns, option lists, push buttons, and signature fields are distinguished using the field type and flags defined by the document. Hierarchical names are joined with dots so similarly named controls in different sections remain unambiguous. This makes the output useful as a machine-readable schema inventory, not merely a scrape of visible page text. When a checkbox has no active value it is reported as false, and an unsigned signature field is identified without pretending that a signature exists.
Provide the document and interpret the response
Send the PDF in the pdf parameter as plain base64 or as a base64 application/pdf data URL. The parser first validates the encoding and PDF header, then reads the indirect objects needed to locate the catalog and form field tree. The response includes fields, an array of records, and count, the number of returned fields. Field types use practical names such as TextField, CheckBox, RadioGroup, Dropdown, OptionList, PushButton, and Signature. Current values preserve strings and arrays where the PDF stores them, while checkbox state is returned as a boolean. Empty text-like controls use an empty string, making them easy to distinguish from absent fields. Do not treat the display label printed beside a control as its field name; only the internal form definition determines the returned name. The capability deliberately errors when no fields exist. That behavior helps automation detect a flattened PDF, a scanned paper form, or the wrong attachment instead of silently continuing with an empty field map. The maximum accepted encoded document size is bounded to keep parsing predictable.
Use the inventory safely in document workflows
A field inventory is a useful first step before filling, validating, migrating, or auditing PDF forms. For example, an onboarding system can compare the returned names against the keys produced by its application database before attempting to populate a template. A quality-control job can verify that a revised form still exposes the required fields and that control types have not changed unexpectedly. An archive migration can record which values were embedded in each interactive document before flattening it for long-term storage. Because the algorithm does not call external services or infer values from page appearance, repeated requests with identical bytes return identical JSON. That predictability is important for tests and audit trails. However, this is an AcroForm structure reader, not optical character recognition: a scan of a paper form has pixels but no interactive fields and therefore produces the no-fields error. It also does not modify, flatten, sign, decrypt, or repair documents. Encrypted files and PDFs whose relevant form objects cannot be read should be prepared with an appropriate PDF tool before submission.
What you can do with it
Map a form before filling it
Discover the exact internal names and control types a filling workflow must target before sending customer data.
Detect template regressions
Compare the returned inventory with an approved contract when a designer publishes a new version of a PDF form.
Audit stored responses
Extract the current values from interactive application or approval documents for structured review and migration.
FAQ
What does a request cost?
The API price is $0.002 per request.
Which PDF field types are recognized?
The output distinguishes text fields, checkboxes, radio groups, dropdowns, option lists, push buttons, and signature fields.
What happens when the PDF contains no form?
The request returns an invalid-input error stating that the PDF has no form fields.
Can this read a scanned paper form?
No. Scanned pages need OCR; this capability reads interactive AcroForm structures embedded in a PDF.
Does it change or fill the document?
No. It only reports field names, types, and current values and never modifies the supplied PDF.
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, by email and from Telegram — and soon from our app too.
Call it from your stack
curl -X POST https://api.kit.forhosting.com/pdf/list-form-fields \
-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/list-form-fields", {
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/list-form-fields",
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/list-form-fields", 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/list-form-fields", 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.list_form_fields",
"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. |