OCR text & AI summary — API contract (web → backend)

This document describes the HTTP endpoints the RedactStripe web app (apps/web) expects for OCR extracted text and AI document summary. Implement these on your API gateway or service behind VITE_API_URL.

Client: all calls use apiRequest() (apps/web/src/api/client.js):

Source files (frontend):


AI summary

Used by the AI Summary sidebar: load the latest saved summary when the panel opens; regenerate on button click.

MethodPathDescription
GET/ai-summary/latestReturn the latest stored summary for the document.
POST/ai-summary/generateCreate or regenerate a summary (sync or async—see notes).

GET /ai-summary/latest

Query parameters

NameTypeDescription
doc_idstringDocument identifier (same as navigation/state docId).
user_idstringAuthenticated user id (numeric or string per your auth model).

Response (frontend parsing)

The UI reads summary text from either:

Empty or missing summary → sidebar shows “No summary available yet.”

Errors: Any non-2xx sets the sidebar error state from error / message in the JSON body.

POST /ai-summary/generate

JSON body

{
  "doc_id": "<document id>",
  "user_id": "<user id>"
}

Response

Same as GET: prefer summary or data.summary with the final (or initial) summary text.

Note: The current hook does not poll; it assumes the POST returns when work is done (or returns a stub you extend later). If generation is async, extend the hook or add GET /ai-summary/status and polling in a follow-up.


OCR text

Used by the OCR Text sidebar: fetch stored per-page text; optionally start an OCR job and poll until complete, then fetch text again.

MethodPathDescription
GET/ocr/textReturn stored OCR output for the document (typically per-page).
POST/ocr/statusStart or trigger OCR processing for the document (may be long-running).
POST/ocr/latest-statusReturn current job status for polling.

Optional (not called by the web client today, listed in code comments): GET /ocr/health — health check for the OCR service.

GET /ocr/text

Query parameters

NameTypeDescription
doc_idstringDocument identifier.
user_idstringUser identifier.

Response (frontend parsing)

The hook merges pages[].text with double newlines for a single text fallback in the UI.

404: Treated as “no OCR stored yet” (empty pages/text, not thrown as a user-facing error).

POST /ocr/status

JSON body

{
  "doc_id": "<document id>",
  "user_id": "<user id>"
}

Purpose: Kick off OCR. The frontend comment warns that this request may run a long time; consider returning 202 + job_id and short timeouts on the client, or move work async and use status polling only.

POST /ocr/latest-status

JSON body

Same as /ocr/status.

Purpose: Poll while OCR runs. The client calls this every 5 seconds, up to 240 attempts (~20 minutes), until status is terminal.

Status field (flexible)

The hook reads status from the JSON object (or nested data) using the first present field:

Completed-like values: completed, complete, success, finished, succeeded, done

Failed-like values: failed, error, cancelled, canceled, failure

On success, the client then calls GET /ocr/text again to load the stored text.


Flow summary

AI summary

  1. Open sidebar → GET /ai-summary/latest?doc_id=&user_id=
  2. User clicks Generate → POST /ai-summary/generate with body { doc_id, user_id }

OCR

  1. Open sidebar (optional load-only) → GET /ocr/text?doc_id=&user_id=
  2. User runs OCR → POST /ocr/status → loop POST /ocr/latest-status until complete/failed/timeout → GET /ocr/text

Changelog