PDF to Markdown & Text Extractor for LLM and RAG
Pricing
from $1.40 / 1,000 pdf converteds
PDF to Markdown & Text Extractor for LLM and RAG
Convert PDF URLs to clean Markdown or plain text for LLMs, AI agents and RAG. Headings, lists, paragraphs and simple tables, optional ready-to-embed chunks with page numbers. No start fee, $0.002 per PDF, scanned PDFs are not charged.
Pricing
from $1.40 / 1,000 pdf converteds
Rating
0.0
(0)
Developer
Data Gleaner
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
1
Monthly active users
3 days ago
Last modified
Categories
Share
Give it PDF links, get clean Markdown, plain text and ready-to-embed chunks back. Headings become # titles, wrapped lines become real paragraphs, bullet lists stay lists, simple tables become Markdown tables, and page headers, footers and page numbers are removed. Built for RAG ingestion, AI agents and LLM pipelines. No browser, no API key, no start fee.
Price: $0.002 per PDF ($2 per 1,000 documents), no start fee. PDFs that fail to download or have no text (scans) are returned with the reason and not charged. See Pricing below.
Why use this one
- Cheapest per document. One flat price per PDF, whether it has 2 pages or 200. No start fee and no per-page charge.
- Real Markdown, not a text dump. Heading levels are guessed from font size, bold and section numbers (
1,2.1,A.3); lines are re-flowed into paragraphs, words hyphenated at a line end are re-joined,-and•lists are kept, and tables with aligned columns are returned as Markdown tables. - RAG chunks included. Set
chunkSizeand each document also returns achunksarray: pieces cut at paragraph and sentence boundaries, with overlap, each with itspageStartandpageEndso an answer can cite the page. - Fast. Text extraction reads the file in-process, so a 100-page report converts in about two seconds.
- Safe on bad input. One broken link never stops the run: every URL returns one row, with an
errorthat says what happened. - Honest limit: no OCR yet. A scanned PDF is returned with
hasTextLayer: falseand is not charged.
Minimal input
{"urls": [{"url": "https://arxiv.org/pdf/1706.03762"}], "outputFormat": "markdown", "chunkSize": 1000}
Start it with no input and it converts one built-in sample PDF (the 15-page arXiv paper 1706.03762) and says so in the run's status message.
What does PDF to Markdown do?
For each link it downloads the file (up to 50 MB, redirects followed, a real PDF check on the first bytes), reads the text layer with every character's position and font, and rebuilds the document structure. Typical uses:
- RAG ingestion. Turn a folder of reports, papers or manuals into Markdown chunks with page numbers for a vector database.
- AI agents. Give an agent a tool that reads any PDF link into text it can quote and reason over.
- Research papers. Convert arXiv and journal PDFs to Markdown with section headings, ready to summarise or compare.
- Contracts and policies. Pull terms, clauses and numbered sections into text for review or clause extraction.
- Reports and filings. Annual reports, government and regulatory reports, white papers and earnings releases as searchable text.
- Knowledge bases and search. Index documentation PDFs by title, page and section.
Input
| Field | Type | What it does |
|---|---|---|
urls | list of links | The PDF files to convert. Leave empty for the built-in sample. |
outputFormat | choice | markdown (default), text or both. |
maxPagesPerPdf | number | Convert only the first N pages, default 200. pageCount still shows the full length. |
pageRange | text | Optional pages, 1-based: 1-5, 8, 10-12, 3- (page 3 to the end). |
chunkSize | number | 0 (default) returns no chunks. Set about 1000 characters (roughly 250 tokens) to also get chunks. |
chunkOverlap | number | Characters repeated between neighbouring chunks, default 100. |
includePageBreaks | true/false | Add a --- Page 3 --- line where each page starts. |
removeHeadersFooters | true/false | Drop running headers, footers and page numbers, default true. |
maxPdfs | number | Process at most this many of the URLs; also your cost cap. |
maxFileSizeMb | number | Skip larger files (default 50). |
maxConcurrency | number | PDFs downloaded in parallel, default 4. |
proxyConfiguration | object | Optional Apify Proxy for sites that refuse the download. Default is no proxy. |
{"urls": [{"url": "https://arxiv.org/pdf/1706.03762"},{"url": "https://nvlpubs.nist.gov/nistpubs/ai/NIST.AI.100-1.pdf"}],"outputFormat": "both","pageRange": "1-10","chunkSize": 1000,"chunkOverlap": 150,"includePageBreaks": true,"maxPdfs": 50}
Output
One dataset row per PDF.
| Field | Meaning |
|---|---|
url, finalUrl | The link you gave and where the file was finally downloaded from. |
fileName | From the server or the link. |
title | The PDF's title metadata, else the first heading. |
author | From the PDF metadata, if present. |
pageCount, pagesProcessed | Pages in the file and pages converted. |
wordCount, charCount | Size of the extracted text. |
hasTextLayer | false for scanned or image-only PDFs. |
markdown, text | The content, depending on outputFormat. |
chunks | When chunkSize > 0: {index, text, pageStart, pageEnd} objects. |
metadata | producer, creator, creationDate, modificationDate (ISO 8601). |
error | null on success, otherwise the reason (download refused, not a PDF, scanned, password-protected). |
scrapedAt, input | When it ran and the settings used. |
{"url": "https://arxiv.org/pdf/1706.03762","finalUrl": "https://arxiv.org/pdf/1706.03762","fileName": "1706.03762v7.pdf","title": "Attention Is All You Need","author": null,"pageCount": 15,"pagesProcessed": 15,"wordCount": 5995,"charCount": 38771,"hasTextLayer": true,"markdown": "# Attention Is All You Need\n\n## Abstract\n\nThe dominant sequence transduction models are based on complex recurrent or convolutional neural networks ...\n\n## 1 Introduction\n\n...","chunks": [{"index": 0, "text": "# Attention Is All You Need\n\nAshish Vaswani ...", "pageStart": 1, "pageEnd": 1},{"index": 1, "text": "...", "pageStart": 1, "pageEnd": 2}],"metadata": {"producer": "pdfTeX-1.40.25", "creator": "LaTeX with hyperref", "creationDate": "2024-04-10T21:11:43+00:00", "modificationDate": "2024-04-10T21:11:43+00:00"},"error": null,"scrapedAt": "2026-10-22T06:00:00+00:00","input": {"url": "https://arxiv.org/pdf/1706.03762", "outputFormat": "markdown", "pageRange": null, "maxPagesPerPdf": 200, "chunkSize": 1000, "includePageBreaks": false}}
Pricing
$0.002 per PDF converted ($2 per 1,000), no start fee, billed through the pay-per-event event pdf-document. Higher Apify plans get lower prices: $0.0017 on Silver and $0.0014 on Gold. This price applies from 22 October 2026. A PDF is billed once when its text is extracted, however many pages it has and whether or not you ask for chunks. Nothing is charged for a link that fails to download, is not a PDF, is password-protected or has no text layer.
Worked examples:
- 1 research paper (any length) = $0.002.
- 100 contracts or reports = $0.20.
- A 5,000-document knowledge base = $10.00, less if some are scans.
- 1,000 links where 80 are scanned or dead = 920 billed = $1.84.
Set maxPdfs and the run cannot cost more than that many times $0.002. If you also set a maximum charge on the run, it stops there too.
Limits
- No OCR yet. Scanned and image-only PDFs have no text to read; they are returned with
hasTextLayer: falseand an explanation, and are not charged. Text embedded in images inside a normal PDF is not read. - Password-protected PDFs are skipped (returned with an error, not charged).
- Layout is inferred. Headings, lists and tables are guessed from fonts and positions, so unusual designs, complex multi-row table headers, equations and figure labels can come out as plain lines of text. Multi-column pages follow the reading order stored in the PDF, which is correct for most papers and reports.
- Size. Files over
maxFileSizeMb(default 50 MB) are skipped. Very long documents are capped bymaxPagesPerPdf. - Some sites refuse automated downloads (HTTP 403). That row has the reason and is not charged; try
proxyConfigurationor another copy of the file.
Use it from n8n, Make, Zapier or an AI agent
Actor ID: datagleaner/pdf-to-markdown
Minimal input:
{"urls": [{"url": "https://arxiv.org/pdf/1706.03762"}], "chunkSize": 1000}
Each tool below runs this Actor with your own Apify API token.
-
n8n: add the Apify node (
@apify/n8n-nodes-apify). Choose Run an Actor and get dataset, set Actor todatagleaner/pdf-to-markdownand paste the input above. -
Make: use the Apify app's Run an Actor module, then Get Dataset Items. Watch Actor Runs can trigger a scenario when a run finishes.
-
Zapier: use the Apify action Run Actor, then Fetch dataset items. The trigger Finished Actor run starts a Zap when a run ends.
-
AI agents (MCP): connect to
https://mcp.apify.com/?tools=datagleaner/pdf-to-markdown. In Claude Code:claude mcp add --transport http apify "https://mcp.apify.com/?tools=datagleaner/pdf-to-markdown"Then run
/mcpto sign in to Apify in your browser. Other clients can sign in with OAuth or send the headerAuthorization: Bearer YOUR_APIFY_TOKEN. Then ask the agent in plain words, for example:Convert this PDF to Markdown and summarise section 3: https://arxiv.org/pdf/1706.03762
-
LangChain (Python):
# pip install langchain-apify, then set APIFY_TOKEN in your environmentimport jsonfrom langchain_apify import ApifyActorsTooltool = ApifyActorsTool("datagleaner/pdf-to-markdown")result = tool.invoke({"run_input": json.loads('{"urls": [{"url": "https://arxiv.org/pdf/1706.03762"}], "chunkSize": 1000}')})
- LlamaIndex (Python): run the Actor with the Apify client and load the rows as documents:
# pip install apify-client llama-indexfrom apify_client import ApifyClientfrom llama_index.core import Documentclient = ApifyClient("YOUR_APIFY_TOKEN")run = client.actor("datagleaner/pdf-to-markdown").call(run_input={"urls": [{"url": "https://arxiv.org/pdf/1706.03762"}]})docs = [Document(text=row["markdown"], metadata={"title": row["title"], "url": row["url"], "pages": row["pageCount"]})for row in client.dataset(run["defaultDatasetId"]).iterate_items() if row.get("markdown")]
FAQ
Do I need an API key or login? No, only an Apify account. The Actor downloads public PDF links; it cannot open files behind a login.
What if I start it with no links? It converts one built-in sample PDF (arXiv 1706.03762, 15 pages) so you can see the output, and says so in the run's status message.
How are chunks cut? At paragraph boundaries first, then sentence or word boundaries for very long paragraphs, to about chunkSize characters, with chunkOverlap characters repeated from the previous chunk. Each chunk carries the first and last PDF page it covers.
Why is a table not a table? Tables are detected when three or more consecutive lines have the same number of aligned columns. Merged cells, multi-line cells and tables drawn as images are returned as text.
What happens to a scanned PDF? It comes back as a row with hasTextLayer: false, the page count and an explanation in error, and it is not charged. OCR is planned.
Can I convert only some pages? Yes, pageRange (for example 1-5,9) and maxPagesPerPdf.
Responsible use
This Actor converts PDF files you point it to. Only submit documents you are allowed to download and process, and respect the terms of the sites that host them. If the documents contain personal data, the obligations for processing it are yours.