# Google Lens OCR API — Image to Text (`khadinakbar/google-lens-ocr-api`) Actor

Extract text from public image URLs using the same Google Lens OCR engine Chromium uses. Returns full text, detected language, and line/word bounding boxes. Cookieless HTTP, no Google login, MCP-ready. Not visual search.

- **URL**: https://apify.com/khadinakbar/google-lens-ocr-api.md
- **Developed by:** [Khadin Akbar](https://apify.com/khadinakbar) (community)
- **Categories:** AI, Developer tools, MCP servers
- **Stats:** 1 total users, 0 monthly users, 0.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $5.00 / 1,000 image ocrs

This Actor is paid per event and usage. You are charged both the fixed price for specific events and for Apify platform usage.

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

## Google Lens OCR API — Image to Text

Turn public image URLs into source-linked OCR dataset rows for automation engineers, RAG builders, and AI agents. Each result returns `fullText`, detected `language`, optional line/word boxes, and collection time from cookieless Google Lens OCR on Apify with Pay per event pricing and MCP-ready inputs.

Best paired with reverse visual search when you need lookalikes — use [Google Lens Visual Search](https://apify.com/khadinakbar/google-lens-visual-search) for matches, then this Actor when the next step is text extraction.

### Best fit for this Actor

- You need text from screenshots, signs, receipts, product labels, or scanned page images that are publicly reachable over HTTP(S).
- You want batch URL OCR with predictable Pay per event billing and a stable `OUTPUT.outcome` for agents.
- You need line-level geometry from Lens, with optional word-level layout hints for indexing or cropping.
- For reverse image search and product lookalikes, start with Google Lens Visual Search, then pass selected image URLs here for OCR.

### Support workflow: screenshot URL to searchable text

A support lead collects public screenshot URLs from a ticket thread. They run this Actor with `outputDetail: "text_only"`. Each dataset row returns `fullText` and `language`. They push `fullText` into a search index and keep `imageUrl` plus `scrapedAt` as provenance. When one URL is missing in a mixed batch, the Actor finishes `PARTIAL` and successful rows stay billed once each.

### Quick start input

```json
{
  "imageUrls": ["https://tesseract.projectnaptha.com/img/eng_bw.png"],
  "outputDetail": "full",
  "languageHint": "en",
  "regionHint": "US",
  "maxConcurrency": 2
}
```

### Input reference

| Field | Type | What it controls |
|---|---|---|
| `imageUrls` | array | Public HTTP(S) image URLs (JPEG/PNG/WebP/GIF/BMP/TIFF). Max 50. Private, localhost, and credentialed URLs are rejected. |
| `outputDetail` | enum | `full` (default), `lines`, `words`, or `text_only`. |
| `languageHint` | string | ISO language nudge for Lens locale (default `en`). |
| `regionHint` | string | Two-letter region nudge (default `US`). |
| `maxConcurrency` | integer | Parallel images, 1–5 (default 2). |

### What data you receive

One dataset item is one OCR'd image.

| Field | Description | Example |
| --- | --- | --- |
| `imageUrl` | Source public image URL | `https://example.com/sign.png` |
| `fullText` | Recognized text in reading order | `OPEN DAILY` |
| `language` | Detected language when Lens returns one | `en` |
| `lines` / `words` | Geometry when `outputDetail` requests it | line boxes from Lens |
| `wordCount` / `lineCount` | Size metrics | `12` / `2` |
| `processedInSeconds` | Per-image wall time | `1.8` |
| `scrapedAt` | Collection time | ISO timestamp |

```json
{
  "imageUrl": "https://tesseract.projectnaptha.com/img/eng_bw.png",
  "fullText": "Mild Splendour of the various-vested Night!\nMother of wildly-working visions! hail!",
  "language": "en",
  "wordCount": 12,
  "lineCount": 2,
  "outputDetail": "full",
  "lines": [
    {
      "text": "Mild Splendour of the various-vested Night!",
      "boundingBox": { "centerX": 0.44, "centerY": 0.10, "width": 0.85, "height": 0.11 }
    }
  ],
  "processedInSeconds": 1.8,
  "scrapedAt": "2030-01-01T00:00:00.000Z"
}
```

Download the dataset as JSON, CSV, Excel, or HTML from the Apify Console Output tab.

### Pricing

This Actor uses Pay per event plus Apify platform usage. The live Pricing tab is the current source of truth for billing details.

- `apify-actor-start`: $0.00005
- `image-ocr`: $0.005 per successfully OCR'd persisted image

Invalid input and total upstream failures leave `image-ocr` uncharged. Partial batches charge only the rows that persisted.

### API example

```bash
curl "https://api.apify.com/v2/acts/khadinakbar~google-lens-ocr-api/runs?token=$APIFY_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "imageUrls": ["https://tesseract.projectnaptha.com/img/eng_bw.png"],
    "outputDetail": "text_only"
  }'
```

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

const client = new ApifyClient({ token: process.env.APIFY_TOKEN });
const run = await client.actor('khadinakbar/google-lens-ocr-api').call({
  imageUrls: ['https://tesseract.projectnaptha.com/img/eng_bw.png'],
  outputDetail: 'text_only',
});
const { items } = await client.dataset(run.defaultDatasetId).listItems();
console.log(items.map((row) => row.fullText));
```

### Agent / MCP prompt card

> OCR these public image URLs with `khadinakbar/google-lens-ocr-api` (`outputDetail: text_only`). Return `imageUrl`, `fullText`, and `language` for each row. Read `OUTPUT.outcome` and charge only succeeded OCR rows.

Provenance: each row includes `imageUrl` and `scrapedAt`. Cost: `$0.005` per OCR row plus start and platform usage. Scope: public image OCR — visual search and Cloud Vision BYOK stay on dedicated Actors.

### Best results

- Provide direct image URLs (`.png` / `.jpg` / `.webp`) rather than HTML gallery pages.
- Start with sharp, upright text; handwriting and heavy skew can reduce recall.
- Keep `maxConcurrency` at 1 when you need the most stable upstream path.
- Line boxes come from Lens. Word boxes in `full` / `words` modes are character-proportional layout hints marked `approximated: true`.

### Responsible use

Collect public images you are authorized to access and follow applicable laws and site terms. Google and Google Lens are trademarks of Google LLC. This independent Actor is not affiliated with, associated with, or endorsed by Google. Keep legal and medical ID OCR outside this workflow.

### Related Actors

- [Google Lens Visual Search](https://apify.com/khadinakbar/google-lens-visual-search) — reverse image matches before OCR
- [AI Content Detector](https://apify.com/khadinakbar/ai-content-detector) — classify pasted text after OCR
- [Broken Link Checker](https://apify.com/khadinakbar/broken-link-checker) — validate image URLs before OCR batches
- [Email Address Validator](https://apify.com/khadinakbar/email-address-validator) — validate emails extracted from OCR text

### Builder's note

I built this as a lean URL-batch OCR Actor after I found that folding OCR into the visual-search sibling muddied billing and MCP routing. My goal is one public image in, one text row out, with Lens line geometry and explicit approximation labels when word boxes are derived.

# Actor input Schema

## `imageUrls` (type: `array`):

One to fifty publicly reachable HTTP(S) image URLs to OCR, for example \["https://tesseract.projectnaptha.com/img/eng\_bw.png"]. Each URL is downloaded once and submitted to Google Lens OCR. Supported formats include JPEG, PNG, WebP, GIF, BMP, and TIFF. Do not use webpage URLs, data URIs, private network hosts, or local file paths.

## `outputDetail` (type: `string`):

How much geometry to keep in each dataset row. text\_only returns fullText and language only. lines adds line boxes. words adds every word box (largest payload). full (default) returns lines and words.

## `languageHint` (type: `string`):

Optional ISO 639-1 language hint for Lens locale context, for example en, de, ja, or zh. Defaults to en. Lens still auto-detects content language; this only nudges recognition.

## `regionHint` (type: `string`):

Optional two-letter country/region code for Lens locale context, for example US, GB, or DE. Defaults to US. Improves region-specific formats such as addresses and dates.

## `maxConcurrency` (type: `integer`):

How many images to OCR in parallel, from 1 to 5. Defaults to 2. Lower this for large images or when Google rate-limits.

## Actor input object example

```json
{
  "imageUrls": [
    "https://tesseract.projectnaptha.com/img/eng_bw.png"
  ],
  "outputDetail": "full",
  "languageHint": "en",
  "regionHint": "US",
  "maxConcurrency": 2
}
```

# Actor output Schema

## `results` (type: `string`):

Dataset items with imageUrl, fullText, language, and optional line/word geometry.

## `summary` (type: `string`):

Terminal OUTPUT record with outcome, itemsPushed, charges, and warnings.

## `runSummary` (type: `string`):

Machine-readable RUN\_SUMMARY mirroring OUTPUT for integrations.

# 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 = {
    "imageUrls": [
        "https://tesseract.projectnaptha.com/img/eng_bw.png"
    ],
    "outputDetail": "full",
    "languageHint": "en",
    "regionHint": "US",
    "maxConcurrency": 2
};

// Run the Actor and wait for it to finish
const run = await client.actor("khadinakbar/google-lens-ocr-api").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 = {
    "imageUrls": ["https://tesseract.projectnaptha.com/img/eng_bw.png"],
    "outputDetail": "full",
    "languageHint": "en",
    "regionHint": "US",
    "maxConcurrency": 2,
}

# Run the Actor and wait for it to finish
run = client.actor("khadinakbar/google-lens-ocr-api").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 '{
  "imageUrls": [
    "https://tesseract.projectnaptha.com/img/eng_bw.png"
  ],
  "outputDetail": "full",
  "languageHint": "en",
  "regionHint": "US",
  "maxConcurrency": 2
}' |
apify call khadinakbar/google-lens-ocr-api --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,khadinakbar/google-lens-ocr-api"
        }
    }
}
```

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/nP2CawB9K0b1ktLMW/builds/X0X4tV41ZS48Wgcga/openapi.json
