Local stays the default and the cheap path; mesh asks each partner for its own
sessions over SSH, live rather than cached, because a stream is true for
minutes and a cached one would be confidently wrong about the only thing the
card exists to say.
The Assistant spans both rows and grid gives a spanning item's surplus to the tracks it spans, so
at Large the card sat at the top of a row much taller than it needed.
Counting every step reported a fully scheduled system as 10 of 82, and reopening the last thread
brought its profile with it, so the tab came up as Troubleshoot pointed at nothing.
Flex items default to min-height:auto, so a view holding a log ignored the height it was given
and pushed the composer out of a panel that clips instead of scrolling.
It kept its own bar, send loop and poll, which is why a thread there died on reload while the
other two were saved and why its controls had drifted from the same controls everywhere else.
The picker sat above the transcript and the buttons below it, so the same component read
differently on each surface; size is the only thing a placement should get to choose.
A stretched grid item is measured before it is stretched, so a long card grew the row it was
meant to fit inside and then filled it; the ceiling is taken from the Assistant instead.
The AI cards sat in the monitor grid, which caps every row at a quarter of the viewport and
clips the card, so expanding grew the transcript inside a box the row had already sized.
- Auth stack: fold cert monitor into Auth Stack page as fourth tab (Certs);
remove standalone cert page and top-level tab
- cert_monitor.sh: write JSON status cache to State_Files/cert_status.json
after each run; expose per-domain days/expiry via _CERT_DAYS/_CERT_EXPIRY globals
- api/cert.php: new — serves cached cert status; falls back to configured
domains as UNKN when no cache exists; POST action=run triggers live check
- arrs db fallbacks: vv_arr_cleanup_stats/discovery_stats/recovery_stats now
read from data/*.db files when log JSON files don't yet exist
- config.php vv_conf_vars(): unescape bash \$ → $ so passwords with dollar
signs read correctly from conf files
- host1.conf: fill in HOST1_NPM_USER/PASS and HOST1_LLDAP_USER/PASS
- Partnership adapter pattern: Unraid-specific container logic extracted to
Plugin/unraid/Partnership/; platform-agnostic structure stays in Partnership/
- First-run wizard: uniform multi-step flow for all hosts; HOST2 pull moved
to checklist; auto SSH keygen and API key creation on save
- api/checklist.php: live setup checklist with pull_master action
- Fullscreen toggle: hide Unraid header/menu; state persists via localStorage
Adds a "Wrap" button to the editor status bar that toggles word wrap
on/off, persisted in localStorage. Default is nowrap with horizontal
scroll (standard code editor behaviour). In wrap mode the line-number
gutter and current-line highlight are hidden — both rely on fixed
line-height calculations that break when lines wrap visually.
CSS: textarea/overlay default to white-space:pre; .vv-ed-wrap class
(on #vv-editor-wrap) overrides to pre-wrap, hides gutter and cur-line.
JS: vvWordWrap state, vvApplyWordWrap(), vvToggleWordWrap(); guards in
vvUpdateLineNums() and vvUpdateCurLine(); restored via
vvRestoreEditorPrefs() on both script and raw-conf editor entry points.
Server badges + media type anchor to the left; device/res/codec anchor
to the right via justify-content:space-between. Right group still
disappears at ≤1024px (now a single display:none on .vv-stream-right).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Wraps each group (separator + chips) in a display:contents span so it
flows naturally at full width and collapses cleanly at the 1024px breakpoint,
leaving server badges and media type visible at intermediate sizes.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Purple-accented chips, ordered Movies → Shows → Music → Live, with
per-index shade variation matching the other chip groups.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Global webkit rule now covers all descendants, not just direct children.
Inline scrollbar-width:none added to the three inner overflow-y:auto divs
(transcode sessions, GPU processes, scripts list) so Firefox hides them too.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Device chips: blue, resolution chips: teal, codec chips: amber.
Alternating bg shades within each group to visually separate chips.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Parses each session's client string (e.g. "Emby for Roku / Bedroom TV")
into a device category using priority-ordered regex matching:
Android TV, Fire TV, Apple TV, Android, iOS, Roku, LG, Samsung,
Google TV, Kodi, Browser, Desktop.
Counts are grouped and sorted by frequency, displayed as compact chips
to the right of the server badges:
Emby 7 Jellyfin 2 · 3 Android 2 Roku 1 Fire TV 1 iOS
Unknown client strings are silently skipped (not shown as "Other").
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Find & Replace (Ctrl+H):
- Two-row find bar: expand › arrow shows replace row (VS Code pattern)
- Replace button (Enter): replaces current match, advances to next
- Replace All: replaces all occurrences, shows count
- Find input searches live; replace row preserved across open/close
Multi-line comment toggle (Ctrl+/):
- With multi-line selection: checks if ALL lines are commented
→ if all commented, uncomments all; otherwise comments all
- Empty lines in selection are skipped
- After toggle: block stays selected (same as VS Code)
- Single-line behavior unchanged
Indent guides:
- CSS repeating-linear-gradient on #vv-editor-inner: 1px guide every 2ch
- First guide at indent level 1 (col 2); then 4, 6, 8... matching 2-space indents
- Shows through the transparent overlay; scales automatically with font size
- Very subtle (0.045 opacity) — visible but not distracting
Font size A− / A+ in status bar (9–22px):
- Persisted to localStorage, restored on every editor open
- Updates textarea, overlay, gutter, and cur-line height together
- All scroll calculations use vvLH() (fontSizePx × 1.5) instead of
hardcoded 18 — find nav, goto, select-next-occurrence all correct at
any font size
Also: fixed duplicate id="vv-find-close" in goto bar (now .vv-find-x class)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Line operations:
- Alt+↑/↓ — move current line up / down (swaps with adjacent line)
- Alt+Shift+↓/↑ — duplicate line below / above
- Ctrl+Shift+K — delete current line
- Ctrl+L — select entire current line (including newline)
Auto-close brackets and quotes:
- ( [ { " ' ` — inserts matching close, cursor placed inside
- Wrap selection — if text is selected, typing an opener wraps it
- Skip-over — typing a close char when it's already next → jumps past it
- Smart backspace — deletes BOTH chars when cursor sits between a matched pair
- Guards: skip ' auto-close after word chars (contractions); skip auto-close
when next char is a word char (prevents disrupting existing text)
Navigation:
- Ctrl+G — Go to Line bar (pre-filled with current line, shows "of N")
- Smart Home — first press → first non-whitespace; second → col 0
- Ctrl+D — first press: select word at cursor; subsequent: cycle through
all occurrences (wraps around), integrates with word highlight overlay
Keyboard shortcuts panel:
- Added "Editor Keyboard Shortcuts" section to the How do I use this panel
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Native browser undo breaks when ta.value is set programmatically (tab,
enter, ctrl+/) — replaced with a custom snapshot-based undo system.
Stack behaviour:
- oninput → debounced capture (600ms) — groups rapid typing into chunks
- Tab / Enter / Ctrl+/ → immediate capture BEFORE edit, then capture AFTER
(each programmatic edit gets its own undo step)
- Content load → vvUndoCaptureInitial() seeds the stack with a clean baseline
- Max 200 history entries (VV_UNDO_MAX); old entries dropped from front
Keyboard: Ctrl/Cmd+Z = undo, Ctrl/Cmd+Y or Ctrl/Cmd+Shift+Z = redo
(both handled in vvEditorKeydown before any other key processing)
Buttons: ↩ Undo / ↪ Redo appear in toolbar beside Cancel/Save when editor
is open; disabled state with 0.28 opacity when no steps available; Undo
button shows step count "↩ Undo 5" so you can see how deep the history is
Cleanup: vvEditorReset() calls vvUndoReset() so stack is cleared on every
editor open/close — fresh baseline each time
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Selection:
- ::selection fix: text selection now visible (bright blue) even when
textarea color is transparent — the #1 complaint
- Overlay background changed transparent → #vv-editor-inner provides bg,
allowing #vv-cur-line to show through
Current line highlight:
- #vv-cur-line div positioned absolutely behind overlay, tracks cursor
line on every keyup/mouseup/click/scroll
- Gutter: current line number highlighted in bright white + bold
Word/variable occurrence highlight:
- Click or position cursor on any identifier → all occurrences highlighted
in yellow throughout the overlay (whole-word, case-sensitive)
- Select a word → same treatment for the selection text
- Clears when cursor moves off the word or find bar opens
Find in file (Ctrl+F):
- Find bar slides in above editor, pre-filled with selected word
- Highlights all matches orange, current match in bright amber
- ↑/↓ buttons + Enter/Shift+Enter to navigate between matches
- Live match count "N / M"
- Red border + "no matches" feedback when term not found
- Escape or × closes, returns focus to editor
Status bar:
- Persistent bar below editor: Ln N, Col N | selection info | language
- Shows "Bash" or "Bash / Config" depending on file type
- Hides when editor is not open
Visual polish:
- Editor wrap: unified border + border-radius 4px 4px 0 0, overflow:hidden
clips gutter and inner to rounded corners as one block
- Status bar border-radius 0 0 4px 4px — completes the block
- Gutter: 46px (was 42) — room for 3-digit line numbers
- Slim 8px scrollbar with styled track and hover state
- vvEditorReset() clears all editor state on open/close
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Selection / highlight:
- .vv-row-selected: blue tint + left accent bar (was barely-visible gray)
- .vv-sb-selected: same treatment, consistent across both panels
- .vv-df-active (containers): match new selection style
- .vv-job-row + .vv-sb-row: smooth transition on state changes
- .vv-orch-row: hover feedback + pointer cursor (was no visual response)
Drag and drop:
- .vv-drag-ghost: adds dashed ring so source item stays visible while dragging
- .vv-drop-line: blue glow to match selection accent (was flat green)
- All drop targets: unified blue theme (.vv-children, .vv-folder-children)
- .vv-library-zone drop target: improved red with inset glow
- .vv-drag-handle:active: grabbing cursor state
- document.body.vv-is-dragging: cursor:grabbing on entire page during drag
(added to all three drag start handlers + failsafe document dragend)
Keyboard navigation (scheduler):
- ↑/↓: navigate between top-level orchestrator cards
- Home/End: jump to first/last card
- Escape: close right panel, return to suggestions
- /: focus log search when log panel is open
- All shortcuts suppressed when focus is in any input/textarea/select
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Tools and Custom: args input always visible (translucent at rest, full on hover)
- Orch children: args input hidden when orch is on, shown when orch is off
(same toggle as the cron field — orch off = standalone mode)
- vvRunJob/vvDryRun: pick up .vv-script-args value, POST as extra_args
- run.php / dryrun.php: accept extra_args, validate against shell metacharacters,
append to run_job.sh invocation (flows through SCRIPT_ARGS to the script)
- CSS: .vv-script-args — 30% opacity at rest, 100% on hover/focus