github nesquena/hermes-webui v0.50.255

latest releases: v0.50.259, v0.50.258, v0.50.257...
5 hours ago

v0.50.255 — provider context, P3 features, TTS+Ollama hotfixes

Substantial release. Three independently-approved PRs merged into a single batch, plus four Opus pre-release advisor fixes including a path-traversal MUST-FIX in the new rollback API.

Added

  • Insights panel — usage analytics dashboard (#464) — new nav rail entry between Todos and Settings. Stats cards (sessions / messages / tokens / cost), token breakdown row, and ASCII-style horizontal-bar charts for activity by day-of-week + hour. New GET /api/insights?days=N endpoint walks _index.json (no full session loads). Period filter (7/30/90 days). (#1405, @bergeouss)

  • Rollback UI — restore from agent checkpoints (#466) — new api/rollback.py exposes GET /api/rollback/list, GET /api/rollback/diff, POST /api/rollback/restore over the agent's CheckpointManager shadow git repos at {hermes_home}/checkpoints/<sha256-of-canonical-workspace>/<commit_hash>/.git. Workspace is allowlisted via load_workspaces(). _validate_checkpoint_id() regex-guards the checkpoint parameter against path-traversal. Restore copies files via shutil.copy2 and never deletes; diff uses difflib.unified_diff. (#1405, @bergeouss)

  • Turn-based voice mode — STT + TTS chained flow — new voice-mode button in the composer kicks off a listen → send → think → speak → listen loop. Uses the browser's Web Speech API (gated on both SpeechRecognition AND speechSynthesis support). Auto-send on 1.8s silence after a final transcript. Honors saved voice preferences. Bails out on not-allowed/service-not-allowed/audio-capture errors. (#1405, @bergeouss)

  • API redact toggleapi_redact_enabled setting (defaults to True) lets users opt out of response-layer redaction when piping the API into automation. (#1405, @bergeouss)

  • Subagent tree visualization — UI affordance for sessions that spawn subagents. (#1405, @bergeouss)

Fixed

  • Session provider context preserved across model picker → runtime resolution (#1240) — the WebUI model picker can show multiple providers exposing the same bare model id (e.g. gpt-5.5 from OpenAI Codex, OpenRouter, Copilot). Previously sessions persisted only the bare model, so a session selected as "gpt-5.5 from OpenAI Codex" silently rerouted through whatever provider became default after a config change. New model_provider: str | None field on Session is persisted in metadata, threaded through every chat path, and is gated in compact() to emit only when truthy. (#1390, @starship-s)

  • TTS toggle: speaker icon never appeared when "Text-to-Speech for responses" was ticked (#1409) — _applyTtsEnabled() set btn.style.display=enabled?'':'none' on every .msg-tts-btn. The '' branch removes the inline override, after which the .msg-tts-btn{display:none;} rule from style.css re-hid the button. Both branches left the icon hidden, so the toggle had no visible effect since the feature shipped in #499. Fixed via body-class toggle (body.tts-enabled) plus a compound CSS selector. The new shape bypasses the cascade collision and survives subsequent renderMd() re-renders without re-querying every button. (#1411, reported by @AvidFuturist via Discord)

  • Ollama (local) no longer falsely reports "API key configured" when only Ollama Cloud key is set (#1410) — both providers were mapped to the same OLLAMA_API_KEY env var in _PROVIDER_ENV_VAR, so configuring Ollama Cloud lit up the local Ollama card too. The runtime in hermes_cli/runtime_provider.py only consumes OLLAMA_API_KEY when the base URL hostname is ollama.com — local Ollama is keyless by design — so the WebUI was reporting "configured" for a key local Ollama doesn't even read. Dropped the bare "ollama": "OLLAMA_API_KEY" mapping; local Ollama users with explicit providers.ollama.api_key in config.yaml continue to be honored. (#1411, reported by @AvidFuturist via Discord)

Security & performance hardening (Opus pre-release advisor)

  • api/rollback.py — checkpoint id regex validation (path-traversal MUST-FIX) — the checkpoint parameter on /api/rollback/diff and /api/rollback/restore was joined into the path via _checkpoint_root() / ws_hash / checkpoint. Path("/a/b") / "../escape" does NOT normalize, so an authenticated caller could pass ../<other-ws-hash>/<sha> and read or restore from another allowlisted workspace's checkpoint store. New _validate_checkpoint_id() regex-guards with ^[A-Za-z0-9_-][A-Za-z0-9_.-]{0,63}$ and rejects literal . / ...

  • redact_session_data() reads api_redact_enabled once per response, not per string — the new redact toggle introduced a perf cliff: _redact_text recursed across messages[] and tool_calls[] calling uncached load_settings() on every nested string. For a 50-message session, that was hundreds of disk reads + JSON parses per /api/session?session_id=X response. Now read once at the top of redact_session_data() and threaded through via a private _enabled keyword.

  • Voice mode pins active session id at thinking-time — the patched autoReadLastAssistant fires globally; if the user navigated to a different session between sending a turn and stream completion, TTS would speak the wrong session's last assistant message. New _voiceModeThinkingSid closure variable captures S.session.session_id in _voiceModeSend; _speakResponse bails to _startListening() if the current sid no longer matches.

  • _inspect_checkpoint drops bare Exception from except tuple — the previous except (subprocess.TimeoutExpired, OSError, Exception) made the specific catches redundant and swallowed everything. Now (subprocess.TimeoutExpired, OSError) only.

Tests

3592 passed, 2 skipped, 3 xpassed (master = 3567, +25 net). Browser tests + Agent Browser CDP visual QA all green. Opus advisor reviewed the combined stage diff. Independent end-to-end review by @nesquena on both #1411 (CSS specificity calculation, behavioral matrix) and #1412 (31-case path-traversal behavioral harness on the rollback regex guard).

Contributors

@bergeouss · @starship-s · @AvidFuturist (Discord bug reporter) · @nesquena (review)

Full Changelog: v0.50.254...v0.50.255

Don't miss a new hermes-webui release

NewReleases is sending notifications on new releases.