{
  "openapi": "3.0.1",
  "info": {
    "title": "Bulk OCR: Image & Scanned PDF to Text from CSV or Google Sheet",
    "description": "OCR every image and scanned PDF linked in an Apify dataset, CSV, Excel or Google Sheet, keeping your columns. Inputs: datasetId or fileUrl or fileUrls, urlField, languages. Adds text, confidence and page counts. Tesseract inside the run, no outside service. Charged per page. Agent-ready: x402, MCP.",
    "version": "0.1",
    "x-build-id": "o5kUzF6v7ezTQRX7Y"
  },
  "servers": [
    {
      "url": "https://api.apify.com/v2"
    }
  ],
  "paths": {
    "/acts/nerolabs~bulk-ocr-image-pdf-to-text/run-sync-get-dataset-items": {
      "post": {
        "operationId": "run-sync-get-dataset-items-nerolabs-bulk-ocr-image-pdf-to-text",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor, waits for its completion, and returns Actor's dataset items in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK"
          }
        }
      }
    },
    "/acts/nerolabs~bulk-ocr-image-pdf-to-text/runs": {
      "post": {
        "operationId": "runs-sync-nerolabs-bulk-ocr-image-pdf-to-text",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor and returns information about the initiated run in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/runsResponseSchema"
                }
              }
            }
          }
        }
      }
    },
    "/acts/nerolabs~bulk-ocr-image-pdf-to-text/run-sync": {
      "post": {
        "operationId": "run-sync-nerolabs-bulk-ocr-image-pdf-to-text",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor, waits for completion, and returns the OUTPUT from Key-value store in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK"
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "inputSchema": {
        "type": "object",
        "properties": {
          "datasetId": {
            "title": "Dataset",
            "type": "string",
            "description": "An Apify dataset holding one row per image or PDF, for example the output of a scraper that collected photos, receipts or document links. Every original column is kept and the recognised text, confidence and page counts are added alongside. Use the picker rather than typing an ID."
          },
          "fileUrl": {
            "title": "File or Google Sheet URL",
            "type": "string",
            "description": "A public link to a CSV, TSV, Excel, JSON or JSON Lines file holding one row per image or PDF. A normal Google Sheets link works: share it as 'Anyone with the link can view'. Used when no dataset is given."
          },
          "fileFormat": {
            "title": "File format",
            "enum": [
              "auto",
              "csv",
              "tsv",
              "json",
              "jsonl",
              "xlsx"
            ],
            "type": "string",
            "description": "Leave on 'Detect automatically' unless the link has no file extension and the server reports the wrong content type.",
            "default": "auto"
          },
          "sheetName": {
            "title": "Excel sheet name",
            "type": "string",
            "description": "Which sheet to read from an Excel workbook. Defaults to the first sheet."
          },
          "fileUrls": {
            "title": "Image or PDF URLs",
            "type": "array",
            "description": "A plain list of image (PNG, JPEG, WebP, GIF, BMP, TIFF) or PDF links, for a quick one-off run with no spreadsheet. Use the dataset, file or Google Sheet inputs above to keep your own columns alongside the results.",
            "items": {
              "type": "string"
            }
          },
          "data": {
            "title": "Rows",
            "type": "array",
            "description": "Rows as inline JSON, an alternative to a dataset or file. Each object needs a field holding the image or PDF link."
          },
          "urlField": {
            "title": "File URL field",
            "type": "string",
            "description": "The column holding the image or PDF link. Left empty it is detected automatically, preferring a column whose values end in .jpg, .png or .pdf over one merely named 'url'."
          },
          "languages": {
            "title": "Languages",
            "type": "array",
            "description": "Tesseract language codes, one per line, for example eng, deu, fra, spa, por, ita, nld, pol, rus, jpn, chi_sim, chi_tra, ara, hin, kor. Several codes read mixed documents. English is built in; any other language is downloaded once at the start of the run (5 to 15 MB each). Picking the right language is the single biggest factor in accuracy.",
            "items": {
              "type": "string"
            }
          },
          "usePdfTextLayer": {
            "title": "Copy a PDF's own text layer when it has one",
            "type": "boolean",
            "description": "A born-digital PDF page already contains its text. When this is on, such pages are copied exactly and charged at the low text-layer rate instead of being rendered and recognised. Turn it off to force OCR on every page, for example when a PDF's text layer is known to be garbage.",
            "default": true
          },
          "dpi": {
            "title": "PDF render resolution",
            "minimum": 100,
            "maximum": 400,
            "type": "integer",
            "description": "Resolution used to render PDF pages before recognition. 200 suits most scans; 300 helps small print and takes about twice as long; 150 is faster for large clean type. Images are used at their own resolution, enlarged when small and capped at 4000 pixels on the longest side.",
            "default": 200
          },
          "pageSegmentation": {
            "title": "Page layout",
            "enum": [
              "auto",
              "sparse",
              "single_block",
              "single_column",
              "single_line"
            ],
            "type": "string",
            "description": "How the engine should look for text. 'Automatic' handles documents, receipts and letters. 'Sparse' finds scattered text on screenshots, slides and product photos. 'Single block' suits a cropped paragraph, 'single column' a narrow receipt, 'single line' a cropped field.",
            "default": "auto"
          },
          "maxPagesPerFile": {
            "title": "Max pages per file",
            "minimum": 1,
            "maximum": 500,
            "type": "integer",
            "description": "Pages read from each PDF before stopping. This is also your cost ceiling per file: a 300-page scan cannot run up a bill you did not expect. Images always count as one page.",
            "default": 20
          },
          "minWordConfidence": {
            "title": "Minimum word confidence",
            "minimum": 0,
            "maximum": 100,
            "type": "integer",
            "description": "Drop words the engine is less sure about than this, from 0 to 100. Leave at 0 to keep everything and judge by the reported confidence instead. Raising it cuts noise out of poor scans at the cost of real words.",
            "default": 0
          },
          "includePageText": {
            "title": "Include per-page text",
            "type": "boolean",
            "description": "Add a 'pages' array with each page's text, method (OCR or copied text layer), confidence and word count, on top of the combined text. Useful for citing a page number, and it makes rows larger.",
            "default": false
          },
          "keep": {
            "title": "Which rows to keep",
            "enum": [
              "all",
              "with_text",
              "no_text",
              "problems"
            ],
            "type": "string",
            "description": "Filtering happens after the file has been fetched and read, so it does not make a run cheaper. 'Problems only' is the quick way to find broken links and unsupported files in a large list.",
            "default": "all"
          },
          "keepOriginalFields": {
            "title": "Keep my original columns",
            "type": "boolean",
            "description": "Keep every column from the input row next to the recognised text, so results line up with your own data. Turn off for text and counts only.",
            "default": true
          },
          "concurrency": {
            "title": "Files at a time",
            "minimum": 1,
            "maximum": 4,
            "type": "integer",
            "description": "How many files to recognise in parallel. Each slot runs its own OCR engine, so the default of 2 fits the default 2 GB of memory; raise memory before raising this.",
            "default": 2
          },
          "requestTimeoutSecs": {
            "title": "Download timeout",
            "minimum": 5,
            "maximum": 300,
            "type": "integer",
            "description": "How long to wait for one file before giving up on it. A timed-out file is never charged.",
            "default": 60
          },
          "maxFileMb": {
            "title": "Largest file",
            "minimum": 1,
            "maximum": 100,
            "type": "integer",
            "description": "Files bigger than this are skipped and not charged, rather than spending the run's memory on one enormous scan.",
            "default": 25
          },
          "maxItems": {
            "title": "Maximum files",
            "minimum": 1,
            "maximum": 50000,
            "type": "integer",
            "description": "A hard ceiling on how many rows are read from the input, as a safety net on a large dataset."
          },
          "exportFormats": {
            "title": "Export files",
            "type": "array",
            "description": "Also write the results as a real downloadable CSV or Excel file, linked from the run's output. Per-page text is JSON-encoded into a single cell so it fits a spreadsheet.",
            "items": {
              "type": "string",
              "enum": [
                "csv",
                "xlsx"
              ],
              "enumTitles": [
                "CSV",
                "Excel (xlsx)"
              ]
            },
            "default": []
          },
          "outputDatasetName": {
            "title": "Append to named dataset",
            "type": "string",
            "description": "Also append every kept row to a named dataset that persists across runs, building one growing text archive. Not charged again."
          },
          "webhookUrl": {
            "title": "Webhook URL",
            "type": "string",
            "description": "POST the run summary to this URL when the run finishes, for Slack, Zapier, Make, n8n or your own API. Charged only on a confirmed 2xx response."
          }
        }
      },
      "runsResponseSchema": {
        "type": "object",
        "properties": {
          "data": {
            "type": "object",
            "properties": {
              "id": {
                "type": "string"
              },
              "actId": {
                "type": "string"
              },
              "userId": {
                "type": "string"
              },
              "startedAt": {
                "type": "string",
                "format": "date-time",
                "example": "2025-01-08T00:00:00.000Z"
              },
              "finishedAt": {
                "type": "string",
                "format": "date-time",
                "example": "2025-01-08T00:00:00.000Z"
              },
              "status": {
                "type": "string",
                "example": "READY"
              },
              "meta": {
                "type": "object",
                "properties": {
                  "origin": {
                    "type": "string",
                    "example": "API"
                  },
                  "userAgent": {
                    "type": "string"
                  }
                }
              },
              "stats": {
                "type": "object",
                "properties": {
                  "inputBodyLen": {
                    "type": "integer",
                    "example": 2000
                  },
                  "rebootCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "restartCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "resurrectCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "computeUnits": {
                    "type": "integer",
                    "example": 0
                  }
                }
              },
              "options": {
                "type": "object",
                "properties": {
                  "build": {
                    "type": "string",
                    "example": "latest"
                  },
                  "timeoutSecs": {
                    "type": "integer",
                    "example": 300
                  },
                  "memoryMbytes": {
                    "type": "integer",
                    "example": 1024
                  },
                  "diskMbytes": {
                    "type": "integer",
                    "example": 2048
                  }
                }
              },
              "buildId": {
                "type": "string"
              },
              "defaultKeyValueStoreId": {
                "type": "string"
              },
              "defaultDatasetId": {
                "type": "string"
              },
              "defaultRequestQueueId": {
                "type": "string"
              },
              "buildNumber": {
                "type": "string",
                "example": "1.0.0"
              },
              "containerUrl": {
                "type": "string"
              },
              "usage": {
                "type": "object",
                "properties": {
                  "ACTOR_COMPUTE_UNITS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_WRITES": {
                    "type": "integer",
                    "example": 1
                  },
                  "KEY_VALUE_STORE_LISTS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_INTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_EXTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_SERPS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              },
              "usageTotalUsd": {
                "type": "number",
                "example": 0.00005
              },
              "usageUsd": {
                "type": "object",
                "properties": {
                  "ACTOR_COMPUTE_UNITS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_WRITES": {
                    "type": "number",
                    "example": 0.00005
                  },
                  "KEY_VALUE_STORE_LISTS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_INTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_EXTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_SERPS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}