Commit graph

812 commits

Author SHA1 Message Date
Nathan Esquenazi
c86545b6a7 chore(repo): remove accidentally-committed graphify artifacts; ignore them going forward
Two artifacts from a contributor's local graphify (code-graph) tooling
slipped into PR #1233 (workspace drag-to-reorder):

  .graphify_cached.json    (3.5MB)
  .graphify_uncached.txt   (refs /home/fr33m1nd/hermes-webui-src/...)

Neither belongs in source control: the .json is an autogenerated cache
of node IDs for a graph visualisation tool, and the .txt is a
file-discovery index pointing at the contributor's local workspace
(/home/fr33m1nd/hermes-webui-src/) — paths that aren't valid for any
other developer.

The repo already ignores graphify-out/ but these two top-level dotfiles
weren't covered. Add explicit ignore entries and remove the tracked
copies.

No code change. CI remains green on 3.11/3.12/3.13.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 22:12:44 -07:00
Hermes Agent
bbd754a496 chore: CHANGELOG for v0.50.237 batch (21 PRs) 2026-04-29 05:08:28 +00:00
Hermes Agent
867f2a3f81 absorb: address Opus review findings (security + correctness)
B1: fix stored XSS in MCP delete button — replace inline onclick with
    data-mcp-name attribute + event delegation (panels.js)
B2: fix zip/tar-slip via startswith prefix collision — use
    is_relative_to(); track actual extracted bytes instead of trusting
    member.file_size (upload.py)
B3: add NVIDIA NIM endpoint to _OPENAI_COMPAT_ENDPOINTS and
    _SUPPORTED_PROVIDER_SETUPS so provider is reachable (routes.py,
    onboarding.py)
H1: add terminalResizeHandle element to index.html and return it from
    _terminalEls() so resize-by-drag works (index.html, terminal.js)
H2: fix dead get_terminal() branch — return None for dead terminals
    instead of always returning term (terminal.py)
H3: replace os.environ.copy() with a safe allowlist in PTY shell env
    so API keys are not exposed inside the terminal (terminal.py)
H5: make model dedup deterministic — sort groups by provider_id
    alphabetically before first-occurrence assignment (config.py)
H7: add pid regex validation before OAuth probe; constrain key_source
    to a closed set of safe values (providers.py)
M8: add double-run guard for cron run-now — reject if job is already
    tracked as running (routes.py)
2026-04-29 05:06:34 +00:00
Hermes Agent
74ecc58afa fix(test): extend renderMd window to 15000 chars (renderMd grew with diff+tree viewers) 2026-04-29 04:39:50 +00:00
Frank Song
2f0d036455 Add terminal locale coverage 2026-04-29 04:37:31 +00:00
Frank Song
eb9614854e Refine embedded terminal card entrypoint 2026-04-29 04:37:31 +00:00
Frank Song
940c82b2da Synchronize initial terminal open layout 2026-04-29 04:37:30 +00:00
Frank Song
70417359e3 Synchronize dock expand layout 2026-04-29 04:37:28 +00:00
Frank Song
8e67e4aa78 Add controlled terminal card resizing 2026-04-29 04:37:27 +00:00
Frank Song
4575cae9db Keep terminal card from covering transcript 2026-04-29 04:37:26 +00:00
Frank Song
38c0912da1 Add collapsible embedded terminal dock 2026-04-29 04:37:12 +00:00
Frank Song
d501daafe1 Fix collapsed terminal dock layering 2026-04-29 04:36:40 +00:00
Frank Song
7df55b9789 Smooth collapsed terminal expansion 2026-04-29 04:36:14 +00:00
Frank Song
10c4ea24f1 Disable dock expand slide jank 2026-04-29 04:35:43 +00:00
Frank Song
60a4cb057e Add embedded workspace terminal 2026-04-29 04:35:11 +00:00
bergeouss
9806a42a26 fix: protect secrets from masked-value round-trip overwrite (#1237)
- Add _strip_masked_values() to skip masked placeholders in PUT endpoint,
  preserving the original stored secret values instead of overwriting them
- Fix transport badge to gracefully handle unknown/future transport types
  with a fallback that shows the raw string
- Add TestStripMaskedValues (5 tests) for the round-trip protection logic
- Addresses reviewer feedback on secret masking semantics and transport badge
2026-04-29 04:34:55 +00:00
bergeouss
b2771ebf69 feat: MCP server management UI (#538)
- Add GET /api/mcp/servers (list with masked secrets)
- Add PUT /api/mcp/servers/<name> (add/update stdio and http servers)
- Add DELETE /api/mcp/servers/<name> (remove server)
- MCP section in System settings with server list, add/delete form
- Auto-detect transport type (stdio vs http) from server config
- Mask sensitive values (API keys, tokens, passwords) in list response
- Uses showConfirmDialog for delete confirmation (no native confirm)
- i18n: 21 keys across 7 locales
- 21 tests (list, save, delete, mask_secrets, validation)
2026-04-29 04:34:55 +00:00
bergeouss
29a31a6e26 fix(484): lazy-load js-yaml CDN for YAML tree view, add parse_failed_note i18n 2026-04-29 04:34:27 +00:00
bergeouss
49a2a424d5 feat: collapsible JSON/YAML tree viewer (#484)
- Fenced code blocks with json/yaml lang get Tree/Raw toggle
- Recursive DOM builder (_buildTreeDOM) with type-colored values
  (green strings, blue numbers, amber booleans, muted nulls)
- Auto-collapse at depth 2+, default tree for >=10 lines blocks
- YAML parsing via js-yaml (lazy, CDN-loaded)
- CSS: tree-view, tree-node, collapsible, type-colored classes
- i18n: tree_view, raw_view keys in all 7 locales
- 14 tests: renderer, types, collapse, CSS, i18n

Closes #484
2026-04-29 04:34:26 +00:00
Frank Song
6f37da38a6 Clarify model scope in composer and settings 2026-04-29 04:33:29 +00:00
Frank Song
2487de2cc0 Harden model cache invalidation paths 2026-04-29 04:33:28 +00:00
Frank Song
eefa1bbad8 fix(models): preserve model cache metadata 2026-04-29 04:33:28 +00:00
bergeouss
1f602b47ec fix: add file size cap and error i18n keys for diff viewer (#1234)
- Add 512 KB cap for inline diff rendering to prevent DOM bloat on large patch files
- Add diff_error and diff_too_large i18n keys in all 7 locales for clear error messages
- Improve error state to show explanatory message instead of just filename
- Addresses reviewer feedback on file size cap and missing diff_error i18n key
2026-04-29 04:33:25 +00:00
bergeouss
9a371f06f5 feat: inline diff/patch viewer (#483)
- Fenced code blocks with diff/patch lang hint render with colored lines
  (green +lines, red -lines, italic @@ hunks)
- MEDIA:.patch/.diff files render inline instead of download link
  (async fetch via loadDiffInline() in post-render pipeline)
- CSS: diff-block, diff-line, diff-plus/minus/hunk classes
- i18n: diff_loading key in all 7 locales
- 12 tests: renderer, MEDIA inline, CSS classes, i18n parity

Closes #483
2026-04-29 04:33:25 +00:00
bergeouss
acbd0c14f2 fix: sanitize err.message in workspace reorder error toast (#1233)
- Remove raw err.message from error toast to prevent leaking internal error
  details to the UI (Path Trust Boundary Rule)
- Use i18n key workspace_reorder_failed for the sanitized message
- Addresses reviewer concern about optimistic vs confirmed reorder:
  the reorder is confirmed (API-first), not optimistic
2026-04-29 04:33:25 +00:00
bergeouss
103a9833d5 feat: workspace drag-to-reorder (#492)
- Add POST /api/workspaces/reorder endpoint to reorder workspace list
- Implement HTML5 drag-and-drop in workspace panel (panels.js)
- Add grip-vertical drag handle icon (icons.js)
- Add drag visual states: dragging, drag-over, cursor styles (style.css)
- Add i18n keys (workspace_drag_hint, workspace_reorder_failed) in all 7 locales
- 11 tests: 7 backend (order, strip, preserve, dedup, unknown, validation) + 4 frontend

Closes #492
2026-04-29 04:33:24 +00:00
bergeouss
63dee0a87c feat(#524): add compress affordance to context ring tooltip
When context usage reaches 50% (yellow), a subtle hint button appears
in the context ring tooltip suggesting /compress.  At 75%+ (red), the
hint intensifies with a warning style.

Clicking the button pre-fills /compress into the composer and focuses
it, so the user can add a focus topic or just hit send.  No auto-fire
— the user stays in control.

- static/ui.js: conditional visibility + click handler in _syncCtxIndicator
- static/index.html: ctxCompressBtn element inside ctxTooltip
- static/style.css: muted button style, red variant for ctx-high
- static/i18n.js: ctx_compress_hint / ctx_compress_action in all 7 locales

Closes #524
2026-04-29 04:33:09 +00:00
Andy
b0aed07fe0 fix: keep clarify countdown steady 2026-04-29 04:32:52 +00:00
Andy
47e91ee84b fix: handle clarify review edge cases 2026-04-29 04:32:52 +00:00
Andy
9fabd12e41 fix: preserve clarify drafts on timeout 2026-04-29 04:32:40 +00:00
bergeouss
4dbc9ac3e1 fix(i18n): add cron_status_running to de locale and fix es fallback 2026-04-29 04:32:00 +00:00
bergeouss
d734efa8af fix: stop cron watch when clearing cron panel detail view
_stopCronWatch() was only called when switching between cron job details
but not when the panel was cleared entirely (_clearCronDetail). This could
leave orphaned polling intervals if the user navigated away or the panel
was dismissed while a job was running.
2026-04-29 04:32:00 +00:00
bergeouss
98ed2d804b feat: cron run status tracking and watch mode (#526)
Backend:
- Track running cron jobs in thread-safe dict (job_id → start_time)
- Wrapper _run_cron_tracked() marks done on completion
- New GET /api/crons/status?job_id=... returns {running, elapsed}
- New GET /api/crons/status returns all running jobs

Frontend:
- After 'Run Now', enters watch mode with 3s polling
- Shows running indicator (spinner + elapsed timer) in detail card
- Auto-detects running jobs when opening detail view
- Stops watch and refreshes output on job completion
- Cleanup on detail view switch

Note: True SSE streaming is not possible because the hermes-agent
scheduler writes output files only on completion. This polling
approach provides real-time status feedback within that constraint.
2026-04-29 04:32:00 +00:00
bergeouss
f2f7224b8d fix: add zip-bomb protection and partial extraction cleanup
- Add cumulative extraction size limit (_MAX_EXTRACTED_BYTES = 200 MB)
  that tracks uncompressed file sizes during extraction to guard against
  zip/tar bombs (small compressed archives that expand to huge sizes).
- On any extraction failure (disk full, corrupted member, size limit),
  clean up the partially-extracted destination directory to avoid
  leaving orphaned folders in the workspace.
2026-04-29 04:31:59 +00:00
bergeouss
8c24b24dcd feat: upload and extract zip/tar archives into workspace (#525)
- Add extract_archive() with zip-slip and tar-slip protection
- New /api/upload/extract endpoint for archive uploads
- Auto-detect archive files (.zip, .tar.gz, .tgz, .bz2, .xz)
- Archives extracted into named subfolder (avoids overwrites)
- Workspace file tree auto-refreshes after extraction
- Archive extensions added to file picker accept list
- i18n: archive_extracted key in all 7 locales

Security: path traversal blocked via resolve() prefix check,
matching existing safe_resolve_ws() sandbox pattern.
2026-04-29 04:31:59 +00:00
bergeouss
d08d96f864 fix: deduplicate clone name + explicit enabled:false for duplicates
- Name dedup: 'Job (copy)', 'Job (copy 2)', 'Job (copy 3)' etc.
- Duplicates explicitly pass enabled:false to backend
- Normal cron create is unaffected (no enabled field sent)

Addresses reviewer feedback on #1225 (points 1 + 4).
2026-04-29 04:31:59 +00:00
bergeouss
8c63324ff7 feat: duplicate cron job with form pre-fill (#528)
- Add duplicate button in cron detail header
- Pre-fills create form with original job settings
- New job created as paused copy with '(copy)' suffix
- i18n keys in all 7 locales
2026-04-29 04:31:59 +00:00
bergeouss
9c57d36156 fix: update expanded dirs cache on double-click directory rename
The inline rename via double-click (nameEl.ondblclick) was not updating
the _expandedDirs and _dirCache when renaming a directory, unlike the
context-menu rename path (_inlineRenameFileItem) which already had this
logic. This could cause the tree view to show stale expand state after
a directory was renamed via double-click.
2026-04-29 04:31:58 +00:00
bergeouss
38df294af9 feat(#1104): workspace directory CRUD — delete, rename, context menu
The file tree already supported file rename (double-click), file delete
(button), and create file/folder.  This adds the missing directory
operations:

Backend:
- _handle_file_delete now supports directories when recursive=true
  (uses shutil.rmtree instead of blocking with an error)

Frontend:
- Right-click context menu on all file/directory items with Rename
  and Delete options (follows the project context menu pattern)
- Directory delete button (x) with confirmation dialog
- _inlineRenameFileItem() for renaming dirs via context menu prompt
- Expanded-dir cache is updated on rename/delete to stay consistent
- Context menu auto-positions within viewport bounds

i18n: delete_dir_confirm, rename_title, rename_prompt in all 7 locales

Closes #1104
2026-04-29 04:31:58 +00:00
starship-s
03b7714f65 docs: note Lucide source for composer icons 2026-04-29 04:31:56 +00:00
starship-s
62650e6a0d fix: add missing commas after approval_skip_all_title in all locales 2026-04-29 04:31:56 +00:00
starship-s
9d5480565f fix: remove deprecated btnCancel; localise composer tooltips with disabled reason branching
- Drop btnCancel element and all JS show/hide call sites across
  boot.js, messages.js, sessions.js, ui.js (superseded by single
  primary action button)
- Remove .cancel-btn CSS rules including mobile media-query override
- Route updateSendBtn() title/aria-label through t() with English
  fallbacks; add composer_send/queue/interrupt/steer/stop keys to all
  7 locales (en, ru, es, de, zh, zh-Hant, ko)
- Branch disabled-state tooltip on reason: clarify lock, compression
  running, or idle-empty, each with its own i18n key
- Update test_sprint10 / test_sprint36 to reflect single-button model:
  assert btnSend present and id="btnCancel" absent; replace
  test_hides_cancel_button with test_clears_composer_status
2026-04-29 04:31:55 +00:00
starship-s
b57134bf2b ui: reflect explicit busy slash command in send button 2026-04-29 04:31:55 +00:00
starship-s
be291498cf ui: swap composer action icons to Lucide (ISC-licensed)
- queue: list-end (append to queue)
- interrupt: skip-forward (jump ahead)
- steer: compass (course correction)
2026-04-29 04:31:54 +00:00
starship-s
8eb3d8bdbc chore: strip remaining btnCancel inline-flex references (superseded by single-button model) 2026-04-29 04:31:54 +00:00
starship-s
96182e5f51 fix: keep busy-input send available on mobile 2026-04-29 04:31:54 +00:00
starship-s
59abbd1300 fix: retry stale repair after lock contention 2026-04-29 04:31:37 +00:00
starship-s
93e7ba5a6b test: stabilize session time bucket boundary 2026-04-29 04:31:36 +00:00
starship-s
014f16c359 fix: harden session sidecar repair 2026-04-29 04:31:36 +00:00
fxd-jason
26f51b7190 fix: address review feedback — restore V3 as legacy, fix zai base_url
- Restore deepseek-chat-v3-0324 and deepseek-reasoner with '(legacy)' labels;
  these are deprecated 2026-07-24 but still live until then
- Fix zai (Z.AI/GLM) default_base_url: use /api/paas/v4 instead of /api/coding/paas/v4;
  the coding plan path is for the glmcode custom provider, not the general API
- Update test assertions to match
2026-04-29 04:31:16 +00:00