Loading...
Loading...
OpenOCR automatically handles PDFs — no extra configuration needed. Send a PDF the same way you send an image, and the API takes care of the rest.
When you send a PDF to the /v1/ocr endpoint, the router automatically detects it and handles conversion:
---).Use the same /v1/ocr endpoint. PDFs can be sent as base64 or via URL, just like images.
How a PDF is recognized. For an engine with native_pdf true the provider reads the PDF itself. For every other engine, pdf means the router rasterizes the PDF first. It recognizes a PDF only when the input is base64 with mime_type application/pdf (or data starting with the %PDF magic), or a URL whose path ends in .pdf (query string ignored). An extensionless PDF URL such as /download/123 is not detected and is sent to the engine as an image: download it and send base64, or use a .pdf URL.
Set page_count to process more than one page. Without it, only page 1 of a multi-page PDF is processed (the default is 1, not all pages). Pass the number of pages you want, up to the limit of the engine you chose (each engine has its own maximum; see max_pages_per_request in GET /v1/engines).
# PDF via base64
curl -X POST https://api.open-ocr.com/v1/ocr \
-H "Content-Type: application/json" \
-H "Authorization: Bearer sk-ocr-your-api-key" \
-H "Idempotency-Key: $(uuidgen)" \
-d '{
"engine": "mistral-mistral-ocr-4-1",
"page_count": 10,
"input": {
"type": "base64",
"data_base64": "<your-pdf-base64>",
"mime_type": "application/pdf"
}
}'
# PDF via URL
curl -X POST https://api.open-ocr.com/v1/ocr \
-H "Content-Type: application/json" \
-H "Authorization: Bearer sk-ocr-your-api-key" \
-H "Idempotency-Key: $(uuidgen)" \
-d '{
"engine": "openocr-ocrmypdf",
"page_count": 10,
"input": {
"type": "url",
"url": "https://example.com/document.pdf"
}
}'import base64
import uuid
import requests
# Read a local PDF
with open("document.pdf", "rb") as f:
pdf_b64 = base64.b64encode(f.read()).decode()
response = requests.post(
"https://api.open-ocr.com/v1/ocr",
headers={
"Authorization": "Bearer sk-ocr-your-api-key",
"Idempotency-Key": str(uuid.uuid4()) # new UUID per logical request
},
json={
"engine": "mistral-mistral-ocr-4-1",
"page_count": 10, # default is 1: set this to process more pages
"input": {
"type": "base64",
"data_base64": pdf_b64,
"mime_type": "application/pdf"
}
}
)
response.raise_for_status() # an error envelope has no "status" field
result = response.json()
if result["status"] != "succeeded":
raise RuntimeError(f"OCR ended as {result['status']}: {result.get('provider_error')}")
print(result["extracted_text"])For multi-page PDFs, the extracted text from each page is separated by --- (three dashes on their own line). You can split on this delimiter to get per-page text:
JSON responses report pages (processed and billed) and pages_total. With output_format text or markdown, the same information arrives in the X-OCR-Pages, X-OCR-Pages-Total and X-OCR-Warnings headers (warnings joined with " | "; the header is absent when nothing was skipped).
# result is the parsed JSON body of a successful response
result = {"extracted_text": "Page one text\n---\nPage two text"}
pages = result["extracted_text"].split("\n---\n")
for i, page_text in enumerate(pages):
print(f"Page {i + 1}: {len(page_text)} chars")| Engine | PDF Handling | Notes |
|---|---|---|
| openocr-ocrmypdf | Native | Processes PDFs directly. Best for scanned documents. |
| local-tesseract | Auto-converted | PDF pages converted to 200 DPI images automatically. |
| local-easyocr | Auto-converted | PDF pages converted to 200 DPI images automatically. |
| local-doctr | Auto-converted | PDF pages converted to 200 DPI images automatically. |
| openocr-rapidocr | Auto-converted | PDF pages converted to 200 DPI images automatically. |