# Extract text from PDF (`akash9078/pdf-text-extractor`) Actor

Efficiently extract text content from PDF files, ideal for data processing, content analysis, and automation workflows. Supports various PDF structures and outputs clean, readable text.

- **URL**: https://apify.com/akash9078/pdf-text-extractor.md
- **Developed by:** [Akash Kumar Naik](https://apify.com/akash9078) (community)
- **Categories:** Developer tools, Automation, Other
- **Features:** Limited permissions
- **Stats:** 127 total users, 3 monthly users, 100.0% runs succeeded, 1 bookmarks
- **User rating**: No ratings yet

## Pricing

from $0.00005 / actor start

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

## PDF Text Extractor — Extract Text from Any PDF File

Extract text from PDF files with OCR support for scanned documents and image-based PDFs. Supports direct URLs and cloud storage links.

### 🎯 What It Does

- **Extract text** from any PDF — digitally created or scanned
- **Cloud storage support** — Google Drive, Dropbox, and OneDrive share links
- **OCR fallback** — automatically runs Tesseract OCR on pages with no embedded text
- **Multi-language OCR** — 100+ languages supported
- **Mistral AI OCR fallback** — when both pdf.js-extract and Tesseract fail, optionally use Mistral OCR for state-of-the-art document understanding (tables, equations, complex layouts)
- **Page limiting** — optionally cap extraction to a specific number of pages
- **Structured output** — extracted text plus metadata (page count, source type, file size, timestamp)

### 📥 Input

```json
{
  "pdfUrl": "https://drive.google.com/file/d/FILE_ID/view?usp=sharing",
  "maxPages": 0,
  "ocrFallback": true,
  "ocrLanguage": "eng",
  "mistralApiKey": "your-mistral-api-key"
}
```

| Field | Type | Default | Description |
|-------|------|---------|-------------|
| `pdfUrl` | string | — | PDF URL or cloud storage share link (Google Drive, Dropbox, OneDrive) |
| `maxPages` | integer | `0` | Max pages to extract. `0` = all pages |
| `ocrFallback` | boolean | `true` | Run Tesseract OCR on pages with <50 chars of embedded text |
| `ocrLanguage` | string | `eng` | Tesseract language code (e.g. `fra`, `deu`, `chi_sim`) |
| `mistralApiKey` | string | — | Optional Mistral AI API key. When provided, if both pdf.js-extract and Tesseract fail to produce meaningful text, the PDF is sent to Mistral OCR for premium document understanding |

### 📤 Output

```json
{
  "originalPdfUrl": "https://drive.google.com/file/d/FILE_ID/view",
  "processedPdfUrl": "https://drive.google.com/uc?export=download&id=FILE_ID",
  "extractedText": "Full text content extracted from the PDF...",
  "pageCount": 12,
  "extractedPages": 12,
  "fileSizeBytes": 1048576,
  "sourceType": "google-drive",
  "ocrApplied": true,
  "mistralFallbackApplied": false,
  "timestamp": "2026-06-05T07:00:00.000Z",
  "success": true
}
```

### 🔍 How It Works

1. **Downloads** the PDF via HTTP with retry logic (3 attempts, exponential backoff)
2. **Extracts embedded text** using `pdf.js-extract` (fast for digital PDFs) — **Stage 1**
3. **Tesseract OCR fallback** (when enabled): pages with <50 chars are rendered to PNG at 300 DPI via `pdftoppm`, then processed with Tesseract OCR — **Stage 2**
4. **Mistral OCR premium fallback** (when `mistralApiKey` is set): if Stages 1 and 2 produce fewer than 200 characters total, the PDF URL is sent to Mistral AI's OCR API for state-of-the-art document understanding — **Stage 3**
5. **Returns** structured JSON with extracted text and metadata

### 💰 Pricing

Pay-per-event — charged only on successful extractions.

| Event | Price | Trigger |
|-------|-------|---------|
| `pdf-processed` | **$0.005** | Per successfully processed PDF |
| `page-extracted` | **$0.0005** | Per page (only when `extractedPages > 1`) |

### 🚀 Use Cases

- **Document processing** — invoices, contracts, reports, scanned paper copies
- **Research** — academic papers, white papers, archival PDFs
- **Data pipelines** — feed PDF content into NLP or search systems
- **Content management** — index PDF archives for full-text search
- **Automation** — process PDFs at scale via Apify API, Zapier, or Make

### ⚡ Tips

- **Scanned PDFs**: `ocrFallback: true` is enabled by default — works out of the box
- **Large PDFs**: set `maxPages` to limit processing time and cost
- **Non-English docs**: set `ocrLanguage` to the matching Tesseract language code
- **Failed extractions**: not charged — error details returned in `errorMessage` field

# Actor input Schema

## `pdfUrl` (type: `string`):

URL of the PDF file to extract. Can be: (1) Direct download URL, (2) Google Drive share link, (3) Dropbox share link, (4) OneDrive share link

## `maxPages` (type: `integer`):

Maximum number of pages to extract. Set to 0 or leave empty to extract all pages. Useful for large PDFs to limit processing time and memory usage.

## `ocrFallback` (type: `boolean`):

When enabled, any page that contains fewer than 50 characters of embedded text is rendered to an image and processed with Tesseract OCR. Use this for scanned PDFs or image-based PDFs that have no text layer. Increases processing time and memory usage.

## `ocrLanguage` (type: `string`):

Tesseract language code used for OCR. Only applies when ocrFallback is true. Common codes: eng (English), fra (French), deu (German), spa (Spanish), chi_sim (Chinese Simplified), jpn (Japanese), ara (Arabic). See https://tesseract-ocr.github.io/tessdoc/Data-Files-in-different-versions.html for the full list.

## `mistralApiKey` (type: `string`):

Optional Mistral AI API key for premium OCR fallback. When provided, if both pdf.js-extract and Tesseract OCR fail to produce meaningful text, the PDF URL is sent to Mistral OCR for state-of-the-art document understanding (tables, equations, complex layouts). Get your key at https://console.mistral.ai/api-keys/

## Actor input object example

```json
{
  "pdfUrl": "https://drive.google.com/file/d/1mt0Tt0YQumH5AOX3bapn4XjxCrtKY4Ns/view?usp=drive_link",
  "maxPages": 0,
  "ocrFallback": true,
  "ocrLanguage": "eng"
}
```

# Actor output Schema

## `datasetUrl` (type: `string`):

Complete extraction results including extractedText, pageCount, fileSizeBytes, sourceType, ocrApplied, and other metadata fields. Access via Apify API or download in your preferred format.

## `textPreview` (type: `string`):

Quick preview of the extracted text (limited to the first dataset item). Use this to verify extraction quality before downloading the full dataset.

## `outputSchema` (type: `string`):

Structured output schema defining all available fields: originalPdfUrl, processedPdfUrl, extractedText, pageCount, extractedPages, fileSizeBytes, sourceType, ocrApplied, timestamp, success, errorMessage (on failure).

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "pdfUrl": "https://drive.google.com/file/d/1mt0Tt0YQumH5AOX3bapn4XjxCrtKY4Ns/view?usp=drive_link",
    "maxPages": 0,
    "ocrLanguage": "eng"
};

// Run the Actor and wait for it to finish
const run = await client.actor("akash9078/pdf-text-extractor").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = {
    "pdfUrl": "https://drive.google.com/file/d/1mt0Tt0YQumH5AOX3bapn4XjxCrtKY4Ns/view?usp=drive_link",
    "maxPages": 0,
    "ocrLanguage": "eng",
}

# Run the Actor and wait for it to finish
run = client.actor("akash9078/pdf-text-extractor").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "pdfUrl": "https://drive.google.com/file/d/1mt0Tt0YQumH5AOX3bapn4XjxCrtKY4Ns/view?usp=drive_link",
  "maxPages": 0,
  "ocrLanguage": "eng"
}' |
apify call akash9078/pdf-text-extractor --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,akash9078/pdf-text-extractor"
        }
    }
}
```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/hh3tHDVKQe0v3uhHX/builds/B5u9l0bDsrsAOnCst/openapi.json
