Skip to content

academic-ocr-drain vlm.sh ships two defects against the Halogen it now targets: no thinking control, and 200 dpi renders that exceed the server's pixel cap #438

Description

@mecattaf

pkgs/academic-ocr-drain/ was retargeted to Halogen Flash on the worker in f32289c (2026-09-11): default.nix:43-51 generates INFERENCE_URL defaulting to http://worker:8731. Two things in the request path were not retargeted with it. Both are measured below against the running 0.7.0 server.

1. The request never sets a thinking control, so every page reasons at xhigh

vlm.sh:15-20 builds the body with model, temperature: 0, max_tokens: 16384 and the messages, and nothing else.

MEASURED 2026-09-19, curl http://worker:8731/health:

reasoning_effort_default: "xhigh"
token_budget_covers_reasoning: true
supported: [..., "enable_thinking", "reasoning_effort", "preserve_thinking", ...]

So a request that omits the field takes the server default and reasons at xhigh before it transcribes, out of the same 16,384-token budget that has to hold the page. A recorded vision run on this server (notes/references/devlogs/2h26/huion-notepad-pipeline/huion/ocr/runs/halogen-vanilla-2026-09-14/p01-metadata.json) spent 443 of 650 completion tokens on reasoning, so about two thirds of the budget went to thinking on a handwriting page with 56 words on it.

vlm.sh:25 rejects finish_reason=length outright, which is correct and is the point: a page that reasons its way into the cap is discarded after paying for the whole generation.

MEASURED tonight with enable_thinking: false on a 10-column regression table rendered at 150 dpi:

value
reasoning tokens 0
completion tokens 893
finish reason stop
elapsed 41.8 s

The transcription was correct, including the significance stars that the PDF text layer renders as the mojibake úúú. Thinking off is enough for this work.

Fix: add enable_thinking: false to the body in vlm.sh. The server's own rule is "a field the request sends always wins; a default fills only a field the request omits", so one field settles it. This is also the standing default already written down for FRONT-07 (notes/references/continuity/2026-09-16-orchestration-day/.../menial-rulings.md F14 Q4, "orchestrator may default").

2. Renders are made at 200 dpi, which is above the server's pixel cap

drain.sh sets dpi: 200 in the flow args and raster.sh takes the dpi as an argument.

MEASURED, /health:

vision.max_pixels: 3686400
vision.size_multiple: 32
vision.input: "data: URL or bare base64 in an image content part; http(s) URLs are refused"

US Letter at 200 dpi is 1700 x 2200 = 3,740,000 px and A4 is 1654 x 2339 = 3,868,706 px. Both are over the cap. The health report does not say whether the frontend refuses such an image or silently downsizes it, and the answer matters: a silent downsize makes the effective resolution unpredictable per page size, and a refusal fails the page.

MEASURED at 150 dpi on two real pages from the corpus:

page render pixels under cap
A4 journal page 1240 x 1754 2,176,714 yes
US Letter handout 1275 x 1650 2,103,750 yes

Fix: compute the dpi per page from its media box so the render lands under max_pixels, and step it down rather than fail if it does not. 150 dpi clears both common page sizes with room to spare; a runner that wants a fixed number should use 150, not 200.

3. While this file is open

mech.sh calls mutool draw for its second mechanical extraction. mupdf-headless is in the package closure so the store build is fine, but there is no mutool on the coordinator's login PATH (MEASURED), so nothing outside the wrapper can reproduce the mech gate. Worth a line in the README if the gate is ever meant to be run by hand.

Context

This is the engine half of reviving the academic OCR drain. The corpus is intact on the NAS (/mnt/nas/documents/academic-papers, 3,367 PDFs, 8.1 GB) and the completion join against notes is 1,880 papers done, 1,467 pending, 156,811 pending pages (MEASURED 2026-09-19). The drain itself last wrote on 2026-08-09 and stopped on its own free-space floor.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions