This is an automated email from the ASF dual-hosted git repository.
tballison pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/tika.git
The following commit(s) were added to refs/heads/main by this push:
new becce47a27 improve docs (#3201)
becce47a27 is described below
commit becce47a278204afd5420e223aa6c082b43f848c
Author: Tim Allison <[email protected]>
AuthorDate: Fri Sep 18 16:04:10 2026 -0400
improve docs (#3201)
---
.../pages/configuration/inference-recipes.adoc | 65 ++++++++++++++++++++++
.../pages/migration-to-4x/chunk-strategies.adoc | 10 +++-
.../src/main/java/org/apache/tika/cli/TikaCLI.java | 2 +-
3 files changed, 74 insertions(+), 3 deletions(-)
diff --git a/docs/modules/ROOT/pages/configuration/inference-recipes.adoc
b/docs/modules/ROOT/pages/configuration/inference-recipes.adoc
index f23f7a0e15..a578cb70a0 100644
--- a/docs/modules/ROOT/pages/configuration/inference-recipes.adoc
+++ b/docs/modules/ROOT/pages/configuration/inference-recipes.adoc
@@ -41,6 +41,34 @@ configured once and named as the recognizer; the PDF's
`AUTO` strategy is the de
}
----
+== Hosted OCR: jina-ocr-v1
+
+A hosted document-OCR model in place of Tesseract, through the OpenAI
chat-completions shape.
+It is a text recognizer like Tesseract: images and, under `AUTO`, the PDF
pages whose extracted
+text is poor. The key comes from the environment
+(xref:configuration/index.adoc#env[Secrets from the environment]).
+
+[source,json]
+----
+{
+ "engines": {
+ "jina-ocr": { "openai-vlm-parser": {
+ "baseUrl": "https://api.jina.ai",
+ "model": "jina-ocr-v1",
+ "apiKey": "${env:JINA_API_KEY}",
+ "prompt": "Transcribe the provided document image into a clean
Markdown format, preserving the natural reading order.",
+ "maxTokens": 8192 } }
+ },
+ "text-recognizers": [ { "engine": "jina-ocr" } ]
+}
+----
+
+The model returns markdown with tables as raw HTML, whatever the prompt says;
Tika parses both
+into XHTML, so a table is a `<table>` in every output format and a pipe table
in markdown. Body
+cells come back as `<th>` and are passed through as such. The load-time health
check reads the
+public `/v1/models`, so a wrong key passes startup and surfaces on the first
request as the
+document's parse exception (HTTP 401 in the message).
+
== Text vectors for every document
One embedding request per document tree, chunks of the container and its
attachments mixed,
@@ -130,6 +158,43 @@ every other document is embedded by its text. List
`["TEXT", "PAGES"]` on the PD
}
----
+== Text, pictures, audio and video in one index (Jina omni)
+
+One engine, `jina-embeddings-v5-omni-small`, embeds every input kind into one
1024-dimension
+space: the extracted text of every document, every picture, and audio and
video cut into
+segments. Four bindings share it. `mediaInput: "object"` is required for the
MEDIA bindings,
+`normalized` makes cosine scores comparable across the four fields, and `task`
selects the
+indexing adapter (a query uses `retrieval.query` with the same model).
+
+[source,json]
+----
+{
+ "engines": {
+ "jina": { "openai-embedding-engine": {
+ "baseUrl": "https://api.jina.ai",
+ "apiKey": "${env:JINA_API_KEY}",
+ "model": "jina-embeddings-v5-omni-small",
+ "mediaInput": "object",
+ "maxBatchSize": 8,
+ "requestParameters": { "task": "retrieval.passage", "dimensions":
1024, "normalized": true } } }
+ },
+ "inference": [
+ { "id": "text", "engine": "jina", "input": "TEXT", "tasks":
["embed"],
+ "chunker": { "markdown-chunker": { "maxChunkChars": 1500,
"overlapChars": 200 } } },
+ { "id": "pictures", "engine": "jina", "input": "IMAGES", "tasks":
["embed"] },
+ { "id": "jina-video", "engine": "jina", "input": "MEDIA", "modality":
"visual" },
+ { "id": "jina-audio", "engine": "jina", "input": "MEDIA", "modality":
"audio" }
+ ]
+}
+----
+
+Media needs ffmpeg on the `PATH`; the `-full` Docker image ships it, the
minimal one does not.
+The default grid, 25 s windows with 5 s overlap, stays under the 30 s cap Jina
puts on an audio
+item; a `media` block that raises `seconds` to 30 or more has every audio
segment refused. A
+segment's two vectors share a `correlator`, and the Elasticsearch and
OpenSearch emitters'
+`chunkStrategy: DOCUMENTS` merges them into one document per segment (see
+xref:migration-to-4x/chunk-strategies.adoc[Chunk strategies]).
+
== OCR off for PDFs only
The recognizer stays on for embedded and standalone images; the PDF parser
never renders.
diff --git a/docs/modules/ROOT/pages/migration-to-4x/chunk-strategies.adoc
b/docs/modules/ROOT/pages/migration-to-4x/chunk-strategies.adoc
index 82ab0f651a..84888fa275 100644
--- a/docs/modules/ROOT/pages/migration-to-4x/chunk-strategies.adoc
+++ b/docs/modules/ROOT/pages/migration-to-4x/chunk-strategies.adoc
@@ -185,7 +185,7 @@ decoded to a float array under `v.<producer>`:
----
{
"file_id": "s3://bucket/talk.mp4", "container_id": "s3://bucket/talk.mp4",
- "correlator": "t:25000-55000", "start_ms": 25000, "end_ms": 55000,
+ "correlator": "t:20000-45000", "start_ms": 20000, "end_ms": 45000,
"v": { "jina-video": [0.01, ...], "jina-audio": [0.02, ...] }
}
----
@@ -194,7 +194,13 @@ A hit is then a chunk, and Elasticsearch adds up scores
per document, so two `kn
(or an `rrf` retriever) over `v.jina-video` and `v.jina-audio` rank a segment
that matches
in both channels above one that matches in either: search one channel with one
clause, both
with two. That cannot be done with segments nested inside the file's document,
where each
-clause scores the file by its best child, possibly a different child per
clause. Mapping:
+clause scores the file by its best child, possibly a different child per
clause. The `rrf`
+retriever is a licensed Elasticsearch feature and answers 403 on a basic
license; a top-level
+`knn` array works on any license, but it adds the scores, so a segment with
two vector fields
+outranks a text chunk with one even when the text is the better match. Search
one channel at
+a time when that matters. Elasticsearch 9 leaves `dense_vector` values out of
`_source` by
+default, so a fetched document shows no `v`; read them back with `fields` or
check them with an
+`exists` query. Mapping:
[source,json]
----
diff --git a/tika-app/src/main/java/org/apache/tika/cli/TikaCLI.java
b/tika-app/src/main/java/org/apache/tika/cli/TikaCLI.java
index d4a50d196f..d1c3d823d2 100644
--- a/tika-app/src/main/java/org/apache/tika/cli/TikaCLI.java
+++ b/tika-app/src/main/java/org/apache/tika/cli/TikaCLI.java
@@ -907,7 +907,7 @@ public class TikaCLI {
out.println(" -J or --jsonRecursive Output metadata and content
from all");
out.println(" embedded files (choose content
type");
out.println(" with -x, -h, -t or -m; default
is --md)");
- out.println(" -a or --async Run Tika in async mode; must
specify details in a" + " tikaConfig file");
+ out.println(" -a or --async Run Tika in async mode: -a -c
<tika-config.json> [-p <pluginsDir>]");
out.println(" -l or --language Output only language");
out.println(" -d or --detect Detect document type");
out.println(" --digest=X Include digest X (md2, md5,
sha1,");