All plugins

document-reader

Profile-scoped document OCR for Hermes Desktop and HUD, with a guarded per-profile Windows service.

lEWFkRAD4DesktopUpdated 1 month ago

Hermes Document Reader

Hermes Document Reader is a Windows-only Hermes plugin for profile-scoped
watched-folder OCR. It adds a Hermes Desktop reader, a HUD attachment action,
and an owned background service for each selected Hermes profile.

The service listens only on loopback. Documents, previews, exports, and history
stay under the selected profile, but page images are sent to the
OpenAI-compatible OCR endpoint configured for that profile. Choose and secure
that endpoint according to your document-handling requirements.

Status: 0.1.0 is Unreleased. No versioned GitHub Release has been
published yet. The installation commands below install the current main
branch for testing.

Requirements

  • Hermes Agent 0.20.0 or newer
  • 64-bit Windows
  • Hermes running on 64-bit CPython 3.11 or 3.14
  • Git, for hermes plugins install and hermes plugins update
  • An OpenAI-compatible multimodal OCR endpoint, model identifier, and API token

HTTPS is required for the OCR endpoint unless you deliberately pass
--allow-insecure-http. Do not use plaintext HTTP for a non-loopback endpoint.

Install for a profile

Run every command with the same profile selector. This example installs the
plugin for a profile named work:

hermes -p work plugins install lEWFkRAD/hermes-document-reader --enable
hermes -p work document-reader configure --api-base https://ocr.example.com/v1 --model model-id
hermes -p work document-reader install
hermes -p work document-reader status
hermes -p work gateway restart

The configure command prompts for the API token without placing it in shell
history or process arguments. Omit -p work for the default profile. Repeat
the complete sequence for every additional profile that should run Document
Reader.

After the first lifecycle installation, enable the Document Reader entry in
Hermes Desktop if it is disabled, then reload Desktop plugins. Do not run
service/install-autostart.ps1, service/ocr_service.py, or a hand-written
scheduled task; those paths bypass the supported ownership checks.

Use Document Reader

  • Open Document Reader from the Desktop sidebar or command palette.
  • Drag files onto the reader or choose Scan documents.
  • In the HUD composer, choose Scan with Document Reader. The action queues
    the selected files to the current profile and inserts only a count marker,
    such as [Document Reader queued 2 files], into the composer. It does not
    attach document names or source files to the chat message.
  • To use the watched folder, place documents in
    <selected HERMES_HOME>\document-reader\data\inbox.

The supported service inputs are PDF, PNG, JPEG, TIFF, and BMP. Each document
must be between 1 byte and 100 MiB. Desktop and HUD intake accept at most ten
files per action.

The reader shows live page previews and recognized text. A completed export
includes a readable .txt file and, when workbook generation succeeds, an
.xlsx workbook with a Text sheet plus one sheet per unique nontrivial table.
Duplicate table copies are omitted.

Profile ownership and storage

Hermes resolves the selected HERMES_HOME at command and request time. That
path is already the profile root; do not append another profiles\<name>
segment. Each profile receives an independent loopback port, service token,
engine token, limited current-user scheduled task, immutable runtime, Desktop
receipt, and data tree.

Runtime state lives beneath <selected HERMES_HOME>\document-reader:

| Path | Purpose |
| --- | --- |
| config | Private service and OCR endpoint configuration and tokens |
| runtime | Owned immutable service releases and runtime lock |
| install | Deployment receipts, lifecycle journal, and rollback backups |
| data\inbox | Watched input documents |
| data\processed | Completed exports and successfully processed source documents |
| data\on-hold | Source documents from cancelled jobs |
| data\needs-review | Source documents with page-level OCR failures |
| data\quarantine | Repeated failures or documents that fail integrity checks |
| data\jobs | Bounded preview and download cache |
| data\state | Bounded job history |
| data\logs | Local service log |

The preview/download cache is bounded by age, count, and total size. Completed
files in data\processed are not part of that cache-retention cleanup.

Update, recover, rollback, and uninstall

Apply a plugin source update to one profile with:

hermes -p work plugins update document-reader
hermes -p work document-reader install
hermes -p work document-reader status

Rerun document-reader install after changing the endpoint, model, token, or
CA bundle so the service restarts under the new configuration.

  • document-reader status verifies deployment receipts, the exact scheduled
    task action, runtime ownership, and authenticated service health.
  • document-reader recover completes or rolls back an interrupted lifecycle
    transaction. Use the same profile selector that reported the interruption.
  • document-reader rollback restores the immediately previous owned
    deployment when one is available.
  • document-reader uninstall removes the owned scheduled task and Desktop
    deployment while preserving configuration, releases, logs, documents, and
    history. It does not remove the Git-installed plugin source.

After lifecycle uninstall, use
hermes -p work plugins remove document-reader only if the profile should also
lose the installed plugin source. The retained
<selected HERMES_HOME>\document-reader state is intentionally not deleted.

Copy a legacy inbox

To migrate an older inbox without deleting or moving the source tree:

hermes -p work document-reader install --legacy-inbox "C:\path\to\old-inbox"

The lifecycle copies and verifies supported legacy documents before publishing
them into the selected profile. Legacy input documents use the same 100 MiB
per-file processing limit as new service inputs. Existing legacy processed
outputs are copied to the new processed tree. The source tree remains intact.

Security and privacy

  • The supported service binds to 127.0.0.1; it is not a LAN or public web
    service.
  • Every service request requires the selected profile's private token, and API
    and job requests also require the expected owner identity.
  • Profile service and engine tokens are private files. Supported lifecycle
    tasks do not receive credentials through environment variables or command
    arguments.
  • Filenames and OCR output are visible in the authenticated local reader and
    stored in the selected profile. HUD composer text contains only the queued
    file count.
  • OCR page images are transmitted to the configured api_base. A local
    loopback service does not imply that the OCR endpoint is local.

See SECURITY.md for reporting and deployment boundaries.

Source-only developer tools

The source tree contains two additional tools that are intentionally absent
from the installable plugin archive and are not registered or provisioned by
document-reader install:

  • mcp/anydoc-mcp.py provides guarded stdio MCP conversion tools. It accepts
    absolute regular files only beneath the selected profile's inbox or
    processed roots. convert_document converts supported formats locally.
    convert_with_ocr may send page images to the profile endpoint only when the
    profile was configured with --allow-remote-mcp-ocr.
  • viewer/ is an unauthenticated, loopback-only, single-run developer
    diagnostic. It is not a production or profile-authenticated service.

Root requirements.txt supports source development and these source-only
tools. The installable service ignores it and provisions exclusively from
install/service-requirements.txt plus the matching fully hashed Windows lock.

Development and releases

See CONTRIBUTING.md for the test and audit workflow. See
RELEASING.md for clean-tree archive, checksum, provenance, and
tag requirements.

The installed service uses chandra-ocr, pypdfium2, openai-python, httpx,
openpyxl, Beautiful Soup, and filetype. Source-only conversion additionally
uses firecrawl-anydoc and the MCP Python SDK. Dependency versions are pinned in
the repository; each project and model keeps its own license terms.

License

Hermes Document Reader is MIT licensed. See LICENSE.

README from the reviewed commit f3a0bed; it updates when the author re-pins.

More by lEWFkRAD

6 plugins by lEWFkRAD in the catalog.

lEWFkRADnetplaneInstall, configure and operate a self-hosted Headscale control plane from Hermes. netplane_setup previews a configuration and, after approval, installs the pinned official Headscale v0.29.6 DEB on a fresh Debian 12+ or Ubuntu 22.04+ systemd host (amd64/arm64). Installation runs on the Hermes host, requires root or noninteractive sudo, refuses existing deployments, and verifies the package SHA-256. It configures SQLite, MagicDNS, embedded DERP/STUN, local admin gRPC, and either Let's Encrypt HTTPS or a loopback backend for an existing reverse proxy. It starts the system service, creates the first user, and saves a 90-day API key and connection settings through Hermes's active-profile APIs. netplane_status reports health, netplane_nodes lists devices, and netplane_preauth lists metadata without stored join secrets or creates an approval-gated, single-use-by-default join key with a 1–168 hour lifetime. Desktop includes setup preview/confirmation, health, nodes, join keys and confirmed node expiration, with a FastAPI backend. Management requires NETPLANE_APIKEY; setup works before a key exists. Bundled protobuf stubs use pinned sources and a compatible toolchain. Disclosure — the netplane_setup tool (after Hermes approval) and the Desktop pane (after confirmation) install the pinned official Headscale v0.29.6 DEB as root through noninteractive sudo on the Hermes host, downloading it from GitHub (SHA-256 verified) and possibly contacting configured APT repositories; it writes /etc/headscale, /var/lib/headscale and a systemd drop-in, and enables a persistent headscale service that in Let's Encrypt mode listens publicly on TCP 80/443 and UDP 3478 (admin gRPC and metrics stay on loopback); Let's Encrypt receives the chosen domain and email; setup saves a new 90-day Headscale API key as NETPLANE_APIKEY in the active Hermes profile; management reads credentials only from Hermes and uses TLS with system trust off-host; approved join-key creation returns the key into the chat; status runs systemctl is-active headscale and tailscale serve status; no telemetry and no automatic software updates.CommunitytoolslEWFkRADsunshine-moonlightSet up and diagnose Moonlight game streaming (Sunshine host <-> Moonlight client) between machines that run Hermes. One tool, action-based: discover hosts on the tailnet/LAN, preflight ports, install+start Sunshine, pair clients, verify encoders, and launch a stream. Writes to remote machines only over SSH and only when the action says so. Disclosure — runs shell commands as your user on this machine and, over SSH, on hosts you name (BatchMode, your existing keys); `install` runs `sudo` with your package manager to install `sunshine` or `moonlight-qt` without a Hermes approval prompt; `configure`/`start` rewrite Sunshine's config (with a backup) and restart its user service; `discover` reads `tailscale status` and port-probes your tailnet peers; `launch` starts a Moonlight process. No credentials stored, no telemetry.CommunitytoolslEWFkRADtidalTIDAL for Hermes Agent: five tools (playback through local mpv, search, playlists, library, mixes) over the unofficial TIDAL API via tidalapi. Login is TIDAL's own PKCE login flow (hermes tidal login) — no developer app needed. Playback runs on the Hermes machine (mpv); TIDAL has no remote-device API like Spotify Connect. Needs a TIDAL subscription (any tier). Disclosure — unofficial TIDAL integration (community tidalapi library using TIDAL's own app client); stores your TIDAL access and refresh token in plaintext (owner-only, 0600) under $HERMES_HOME/plugin-data/tidal/ and refreshes it itself; playback spawns a detached local mpv process with an IPC socket and plays audio on the Hermes machine.CommunitytoolslEWFkRADwireguardRead-only status and peer list for a WireGuard server running on the same Windows machine as Hermes. Two tools: vpn_status (service state, tunnel address and port, server public key, per-peer handshake and transfer) and vpn_peers (the peer list only). The plugin runs only wg.exe show, sc.exe query, and one PowerShell adapter lookup; it never changes the tunnel and never reads the tunnel configuration file or any private key material. Windows only (WireGuard for Windows). Disclosure — runs local wg.exe show, sc.exe query and one PowerShell Get-NetIPAddress lookup (read-only, never touches the tunnel config or private key); tool results put peer public keys, allowed IPs and peer endpoint IP addresses into the conversation sent to your model provider.Communitytools