Merge dev → main (automated) - #2012
Merged
Merged
Conversation
added 30 commits
July 26, 2026 19:05
Implements a Herdr plugin (worklog-selection-list) that provides a keyboard-navigable work item selection list pane for browsing, filtering, and selecting Worklog work items from within the Herdr environment. Key files: - packages/herdr/herdr-plugin.toml - Plugin manifest with actions and pane - packages/herdr/src/index.ts - Main TUI entry point - packages/herdr/src/worklist.ts - Core list UI state, rendering, keyboard - packages/herdr/src/fetcher.ts - wl CLI data fetching with test injection - packages/herdr/scripts/open.sh - Action: open worklist pane - packages/herdr/scripts/toggle.sh - Action: toggle worklist pane - packages/herdr/README.md - Plugin documentation - tests/herdr/ - 63 tests across 3 test files Features: work item listing, stage filtering, detail view, keyboard navigation (arrows/jk, pgup/pgdn, g/G, enter, escape), refresh, quit.
Herdr resolves command paths relative to the plugin directory (packages/herdr/), not the repo root.
The extractItems function was checking workItems array before results,
but wl next -n returns both an empty workItems array AND a populated
results array — causing items to be silently dropped. Fixed by:
1. Checking results array first (takes priority when both present)
2. Adding length guard to skip empty arrays
3. Adding fallback for empty results/workItems arrays
4. Adding handling for single-item { workItem: {...} } wrapper
format used by wl next (no -n) and wl show
Port icon system from Pi TUI browse.ts with: - icons.ts: statusIcon, stageIcon, priorityIcon, auditIcon, epicIcon, riskIcon, effortIcon, needsProducerReviewIcon, auditStaleIcon - isAuditFresh() for 60-second staleness detection - getIconPrefix() with multi-column layout (status, stage/audit, producer review, epic+children) - applyStageColour() for ANSI stage-based colouring - stageColor() for ANSI 256-color codes per stage Updated worklist.ts: - formatItemLine now uses icon prefix, stage colouring, priority icons - createListRenderer renders group separators (── Group ──) - createListRenderer accepts totalCount for 'top N of M' display - ANSI-aware truncation preserves escape codes 93 tests passing (4 test files).
Port chord shortcut system from Pi TUI with: - ShortcutRegistry class: lookup, lookupChord, getChordByPrefix, getChordByLeader, getChordEntries, getEntriesForStage - shortcuts.json: non-agent-triggering shortcuts (c, n, p, s single keys + f- chords for filter stage switching) - loadShortcutConfig(): parses shortcuts.json with validation - Chord state machine in worklist.ts: pendingChordKeys, hints, processChordInput, isChordLeader, formatChordHintsForHelp, getChordHelpHints - Dynamic help bar: shows chord-mode hints when in chord input, regular hints otherwise - runWorklistTui: chord-aware key dispatching, accepts ShortcutRegistry parameter - index.ts: loads shortcut config and passes to TUI loop 125 tests passing, TypeScript compiles cleanly.
Add scrollable detail view with: - formatDetailContent(): returns full content as line array with metadata, wrapped description, and footer - formatDetailView(): scrollable viewport rendering with offset and viewport height parameters - detailScrollOffset on WorkItemListState with detailScrollUp() and detailScrollDown() methods - Keyboard handling: j/k/arrows for line scroll, PgUp/PgDn for page scroll, g/G for top/bottom - Scroll position indicator: 'Lines X-Y of Z (P%)' shown on last visible line when content exceeds viewport - auto-clamping of scroll offset using formatDetailContent length - Resets scroll offset when entering/exiting detail mode - createListRenderer accepts detailScrollOffset parameter 154 tests passing, TypeScript compiles cleanly.
Add auto-refresh support with: - runWorklistTui options parameter: autoRefresh (default: true) and refreshIntervalMs (default: 30000) - Periodic fetch via setInterval every 30s - Refresh notifications: '[Refreshed: +N new]', '[Refreshed]', '[Refresh failed]' with 3s auto-dismiss - Auto-refresh timer cleanup on exit - createListRenderer autoRefresh parameter showing indicator in header: '[auto-refresh on]' - index.ts passes auto-refresh options to TUI loop 162 tests passing, TypeScript compiles cleanly.
Add hierarchical display with expand/collapse: - WorkItem.children and depth fields for child item data - WorkItemListState.expandedItems set with isExpanded(), toggleExpand(), getFlattenedItems() - Expand/collapse icons: ▶ (collapsed) and ▼ (expanded) for items with childCount > 0 - Depth-based indentation for child items - Enter toggles expand/collapse for parent items, shows detail view for leaf items - createListRenderer accepts expandedItems Set parameter and flattens items for display - runWorklistTui passes expanded items state to renderer - WorkItem interface extended with children, depth, _expanded 177 tests passing, TypeScript compiles cleanly.
Add final polish features: - WlError interface and formatWlError() for user-facing error messages - Empty list edge case handling (no crash on navigation, clamping) - goToLast safety check for empty lists - Error handling tests for init/generic/unknown error cases - Small terminal size handling in both list and detail modes - Footer key hints verification in render output - chordState hint display in footer 197 tests passing (9 test files), TypeScript compiles cleanly.
Add settings system with: - PluginSettings interface: autoRefresh, refreshIntervalMs, showIcons, wlCount - defaultSettings with sensible defaults (30s auto-refresh, 20 items, icons on) - loadSettings(): merge file settings with defaults, handles missing/malformed - saveSettings(): writes JSON with directory creation - getDefaultSettingsPath(): ~/.config/herdr/worklog-plugin.json - index.ts integration: loads settings and passes to TUI loop 207 tests passing (10 test files), TypeScript compiles cleanly.
…Count The hierarchy expand/collapse on enter was triggered by checking childCount > 0, but the real wl CLI returns childCount on items without actual children data. Changed condition to check for a populated children array instead, so enter opens the detail view for normal items and only toggles expand when children data exists. Fixes: enter-to-select broken for all worklog items
The select-and-confirm check at the end of handleKeypress was using state.mode === 'detail' after handleKeypress had already changed mode to 'detail' via selectItem(). This caused the TUI to immediately exit on the first enter press. Fix: save prevMode before the keypress, so we only resolve when pressing enter while already in detail mode (i.e., confirming a selection, not entering detail view for the first time). Adds regression test: enters detail mode on enter for items without children. 208 tests passing (10 files), TypeScript compiles cleanly.
Two related fixes for detail view rendering: 1. getTermSize() now uses process.stdout.columns/rows first (reflects actual terminal dimensions), with env var fallback. Herdr panes may not have COLUMNS/LINES set, causing content wider than the terminal and visual wrapping artifacts. 2. formatDetailContent now truncates every line to fit the terminal width (ANSI-aware), preventing overflow/wrapping that caused duplicate-looking content when lines wrapped in the terminal. 3. Separator and description wrap width now use contentWidth (maxCols - 2) matching the 2-space line indent. 208 tests passing, TypeScript compiles cleanly.
cursorHome (\x1b[H) moves to top-left but does not erase old content. When detail view (fewer lines than list view) replaces list view, old lines and wrapped overflow remnants remained visible, causing visual garbage like duplicate text and mixed content from different views. Fix: emit ANSI.clear (\x1b[2J) before cursorHome to wipe the entire screen before each render. 208 tests passing, TypeScript compiles cleanly.
The chordHelpHints variable was computed in runWorklistTui() but never passed to the renderer or displayed. This made the chord shortcut system invisible — no visual indication that chords are available. - Added chordHelpHints parameter to createListRenderer() signature - Shows '[f] chords' in the footer when shortcuts are loaded - Pass chordHelpHints from runWorklistTui to the render function WL-0MS31Q7FD00710B7
When a chord sequence completed (e.g. f-r for filter review), the TUI would call cleanup() and resolve(undefined), simply exiting. The resolved command was ignored entirely. Added dispatchChordCommand() that maps /wl <stage> commands to the corresponding stage filter action via state.applyFilter(). Now pressing f-r applies the 'in_review' filter and stays in the TUI, the same applies to f-i (idea), f-n (intake), f-p (plan). Also fixed chord help hints not being displayed in the footer (committed separately in b704809, merged here for atomicity). WL-0MS31Q7FD00710B7
- Removed '/' case from keyToAction() — no longer opens filter prompt - Updated footer hint: removed [/] filter, [f] chords remains - Updated 'No filter' message to reference f-* chords - Updated test to expect null instead of 'filter' for '/' key - Added postbuild script to copy shortcuts.json to dist/ WL-0MS31Q7FD00710B7
The footer now dynamically shows only shortcuts applicable to the currently selected work item's stage, matching the Pi TUI behavior: - Calls shortcutRegistry.getEntriesForStage(selectedStage) to get relevant entries for the selected item's stage - Filters to list/both views - Deduplicates chord leaders (only one hint per leader key) - Excludes commands requiring <id> when the list is empty - Formats as key:label pairs (e.g., 'c:create new', 'f:filter...') Hints update on each render as the user navigates between items. WL-0MS31Q7FD00710B7
Auto-refresh is on by default (30s interval), header shows [auto-refresh on]. Removed nav/enter/refresh/quit hints from the footer — they're redundant: - 'r' refresh: auto-refresh handles it - nav/select/quit: basic TUI keys, no need to clutter the footer - filter: handled by f-* chords Footer now shows only stage-appropriate shortcut hints (e.g. 'c:create new s:Search f:filter...') or is left minimal. WL-0MS31Q7FD00710B7
Updated stage icon mapping in Herdr plugin to match the main project: idea: 🔍 → 💡 (magnifying glass → light bulb) intake_cpl: 📋 → 📥 (clipboard → inbox tray) plan_cpl: 📝 → 📋 (memo → clipboard) in_progress: ◐ → 🛠️ (half circle → hammer wrench) in_review: 🔎 → 🔍 (right-facing → left-facing magnifying glass) Previously Herdr used 🔍 for idea (which is the main project's in_review icon), causing the reported regression. WL-0MS31Q7FD00710B7
Add auditedAt to WorkItem interface and normalizeItem() mapping in fetcher.ts so the data flows through the pipeline. Display three audit fields in formatDetailContent() metadata section: - Audit: uses auditIcon() — ✅ ready / ❌ failed / ❓ unknown - Reviewed: uses needsProducerReviewIcon() — ❌ needs review / ✅ reviewed - Audited At: ISO timestamp (same pattern as createdAt/updatedAt) Adds 7 test cases covering all three fields (present, absent, null/undefined states). Closes WL-0MS3ALBD40006RGD
…ands When a chord completes in the Herdr worklist plugin, non-/wl commands were previously silently dropped. This change adds an onCommand callback to runWorklistTui that receives resolved commands with <id> placeholders replaced by the selected item ID. - Export dispatchChordCommand and add executeResolvedCommand() helper - Add onCommand option to runWorklistTui parameter - Update index.ts to pass callback writing CMD:<command> to stdout - Add 12 tests covering all acceptance criteria - Update README documentation Closes WL-0MS4GICML0015GW5
…ommand Update dispatchChordCommand to recognize and route the following command families through the stdout output mechanism: - /skill:implement, /skill:audit (agent skill invocations) - /intake, /plan (agent workflow commands) - !!wl reviewed (producer review toggle) - Compound audit commands (&& wl audit-set) Add resolveAndRouteCommand helper that resolves <id> placeholders from the selected item and calls the onCommand callback for routing to the output mechanism (CMD: prefix + process.exit). Update executeResolvedCommand to pass onCommand to dispatchChordCommand, so recognized command families are dispatched (return 'dispatched') rather than falling through to the generic callback path. Update shortcuts.json with new single-key and chord shortcuts for implement, audit, producer review, and audit approve/reject. Add 53 tests covering all new command families, <id> resolution, no-op handling, and backward compatibility with existing /wl commands. Refs: WL-0MS4GIMB80084PC5
Adds tests verifying: - dispatchChordCommand returns false for !!wl update/close/delete/search - executeResolvedCommand routes !!wl close/delete through onCommand - No-op when no item selected and <id> required - Backward compatible behavior without callback - Full dispatch chain for all !!wl command families Child: WL-0MS4GIMBD008GWVM Epic: WL-0MS4GHV30000HXL0
The chord leader check in onData only ran when action === null, but 'r' returns 'refresh' from handleKeypress. Changed condition to also check isChordLeader, so chord leaders start chord mode even when the key has a direct action binding. Fixes review chords (r v, r a, r r) being unreachable. Bug: WL-0MS4LDWHW0062FTA
With the chord leader check fix, 'r' is now handled entirely by the chord system in list mode (review chords r-v, r-a, r-r). The direct 'refresh' action mapping was dead code and conflicted with the chord leader. Detail mode still maps 'r' to refresh since chords don't apply there. Bug: WL-0MS4LDWHW0062FTA
Replace the dual 'key' (single-press) and 'chord' (multi-press) fields with a single 'chord' array. A single-key shortcut is now chord: ['i'], consistent with multi-key chords like chord: ['r', 'v']. Changes: - Remove 'key' from ShortcutEntry interface — 'chord' is now required - Remove lookup() method (replaced by lookupChord with any-length array) - Remove chordEntries Map indexing (superceded by getChordByPrefix) - isChordLeader now accepts chords of any length >= 1 - loadShortcutConfig validates chord.length >= 1 instead of key presence - hints fallback uses chord[0] instead of key - All entries in shortcuts.json use 'chord' uniformly - getChordEntries() returns all entries (not filtered to length >= 2) - getChordByLeader delegates to getChordByPrefix
…h Tab in Herdr TUI Root cause: createListRenderer had its own flattening logic that re-flattened items already flattened by state.getFlattenedItems() upstream, causing each child to appear twice. Fix: Remove the redundant flattening logic from createListRenderer. The caller (render callback in runWorklistTui) already passes flattened items from state.getFlattenedItems(), so re-flattening inside the renderer adds children a second time. Tests: - New tests verify no duplication when expandedItems set is provided with already-flattened items - Updated hierarchy tests to pass flattened items (matching real caller) - 284/284 Herdr tests pass, all 3626 non-pre-existing tests pass
Adds explicit documentation for the audit metadata fields (Audit, Reviewed, Audited At) that were added in a36f62d: - packages/herdr/README.md: Add 'Audit indicators' feature bullet and mention audit fields in the 'View details' description - packages/herdr/src/worklist.ts: Add JSDoc for formatDetailContent() listing all metadata fields including audit-related ones Part of WL-0MS3ALBD40006RGD
…d hierarchy Changes: - moveUp() wraps to last item when at index 0 (uses flatCount) - moveDown() wraps to first item when at last (uses flatCount) - goToLast() uses flatCount - 1 instead of items.length - 1 - pageDown() uses flatCount bounds instead of items.length - _clampSelection() uses flatCount to properly clamp when hierarchy expanded - _adjustScroll() uses flatCount for scroll offset calculation - Updated tests for wrap-around and expanded hierarchy navigation - Updated README documentation Closes WL-0MS4QIJLF0090Q9Y
added 29 commits
July 31, 2026 16:16
…ed/in_review items in TUI lists Implements the always-show rule for the default selection lists in both TUIs (Herdr plugin worklist + Pi TUI Worklog extension), including auto-refresh and DB-backed paths: - New per-TUI pure selectWorkItems(items, browseItemCount) helper (duplicated per decision Q2c): mandatory = critical ∪ completed/in_review always shown, browseItemCount limits only "other" items, slots floored at zero. - fetchNextItems / createDefaultListWorkItems / createDefaultListWorkItemsDb now fetch the mandatory subsets explicitly via parallel wl list queries (wl list --priority critical + wl list --status completed --stage in_review) because wl next -n N hard-caps at 32 items; merged and deduplicated by ID. - Pi TUI browse flow: removed redundant .slice(0, itemCount) in runBrowseFlow re-fetch and initial paths; "top N of M" heading now reflects the actual displayed count. - Stage-filtered views unchanged (no always-show rule). - Docs: READMEs updated (Herdr + TUI extensions); CHANGELOG.md untouched. Tests: smart-selection.test.ts in both packages (20 tests covering reference examples, edge cases, ordering), browse-total-count.test.ts heading updates, settings-persistence + runWl-init-detection test adjustments for the additional mandatory-subset queries.
…lists in both TUIs Filter stage !== 'done' inside selectWorkItems (Herdr + Pi TUI copies), the single choke point covering all default-list fetch paths (wl next, mandatory subsets, DB-backed). Explicit stage-filtered views unchanged. 6 new tests per package (12 total): done excluded as critical, as completed, not consuming slots, empty-list-when-all-done, interleaved mandatory preservation, plain exclusion.
…0MS4FHW290053SH4) - tests/herdr/shortcuts.test.ts: dedicated id-substitution dispatch tests for all four u-p-* priority templates, u-s stage/status template, and a-y/a-r audit approve/reject templates (previously only covered generically) - packages/tui/tests/browse-shortcut-help.test.ts: help-line rendering tests asserting u/x/f chord families collapse to single leader hints, and that a-a/a-y stage-gated audit chords appear only for in_review items
…ILJ0079283) The live herdr session touches root-level worklog.db-shm/worklog.db-wal, which kept dirtying the working tree and blocking the implement safety gate.
Audit of WL-0MS4FI763006105Y found the NavigationStack was only exercised in unit tests — production drill-down paths never called pushNavigationState, so Escape in the live TUI never returned to the parent list. - worklist.ts: push navigation state when expanding a parent (Enter and Tab paths); clear the entry when collapsing; add NavigationStack.removeForParent + WorkItemListState.clearNavigationStateFor - doRefresh re-fetches children for expanded parents after refresh - README: document Enter/Tab expand and Escape back-to-parent - tests: production-path nav-stack tests (hierarchy), nav-stack survival across refresh (auto-refresh)
…0079283) .implement_state.json is per-worktree machine state for the implement orchestration script. The copy committed to dev was stale (pointing at a previous work item) and its presence at the repo root made implement.py finish refuse to discover worktrees.
…WL-0MS7MFILJ0079283) Adds scripts/run-in-pane.sh which splits the current pane to the right, runs the given command through a shell in the new pane (so && and quoted --summary values work), renames it, auto-closes on exit 0 after a 500ms pause, and stays open on non-zero exit for error inspection. Routes !/!! prefixed commands in the onCommand callback to this script (via new routeCommand helper) instead of the dead CMD: stdout path. Agent commands (/skill:*, /intake, /plan) still go to send-to-pi.sh; unprefixed commands keep the CMD: fallback. Adds 13 routeCommand tests.
…n a pane (WL-0MS95CEAE0080EB4) The a-y chord resolved to 'wl reviewed <id> false && wl audit-set <id> --ready-to-close yes ...' which was routed to the dead CMD: stdout path (herdr v0.7.5 has no CMD: handling), so nothing happened. Restore the !! prefix on the 12 shell-executed shortcuts (a-y, a-r, r, s, u-p-*, u-s, u-t, x-c, x-d), exactly matching the pre-a779d71 state. These now route via routeCommand to run-in-pane.sh (WL-0MS7MFILJ0079283): the command runs visibly in a new herdr pane, auto-closes on success, and stays open on failure. Agent commands and /wl filters are unaffected. Verified end-to-end: the a-y command through the pane wrapper sets needsProducerReview=false and audit-set --ready-to-close yes with the summary. Adds 7 tests (dispatch + shortcuts.json routing).
…09MR66) Criterion 6 of WL-0MS4FI763006105Y audit required a test asserting the parent scroll position is restored when navigating back. popNavigationState restores scrollOffset from the pushed entry; new test verifies a non-zero scrollOffset captured at push time is restored after pop.
…SIA0057ABR) - Add wl list --root-only flag (mutually exclusive with --parent) - Make wl next strictly root-only: orphan promotion removed; children under closed/deleted/in-progress parents are hidden entirely - Critical escalation and Stage 3 blocker surfacing never return child items; child blockers resolved to selectable parent or dropped with a clear reason - Pi TUI and Herdr fetch mandatory subsets and stage lists root-only; defensive parentId filter in both selectWorkItems copies - Update docs (CLI.md, README.md, TUI.md, herdr README) - Tests: list-root-only CLI suite, strict root-only database tests, updated next-regression expectations, TUI/Herdr fetch-arg tests
…0MS9DNFNN008R263) src/index.test.ts imported join twice (line 114 from e1c8a10, line 219 from 1fc0332), causing tsc TS2300 and making 'npm run build' exit 2, which fails herdr's [[build]] step for the linked plugin. The line-114 import already covers the whole file; the duplicate at line 219 is removed. Build now exits 0.
… (WL-0MS9EK4ED005CSQH) Root cause: tests/setup-tests.ts (8889958) installs a global vi.mock('child_process') for the forks pool, which: 1. Silently bypassed runWl-init-detection.test.ts's vi.mock('node:child_process') factory — runWl fell through to the real execFile + tests/cli/mock-bin wl mock, resolving instead of rejecting (24/25 tests failing). 2. Broke promisify(child_process.execFile) in mock-timeout.test.ts — a vi.fn() wrapper breaks callback-arity detection, returning undefined stdout/stderr even with real delegation. Fixes: - lib/tools.ts: promisify(execFile) lazily inside runWl so the mock binding is observable regardless of module-load order. - tests/child-process-mocks.ts + setup-tests.ts: add a shared mockExecFile to the globalThis store and register BOTH child_process and node:child_process to the same instances; execFile delegates to real by default. - runWl-init-detection.test.ts: use the shared store mock; restore real execFile delegation in beforeEach so recycled workers keep real behavior. - mock-timeout.test.ts: resolve the truly-real child_process via createRequire for its promisify (this test drives the mock-bin scripts and needs the real 4-arity execFile). Full suite: 3897 passed, 0 failed (previously 24 runWl + 6 mock-timeout failures, plus intermittent cli-utils-markdown flakes).
…FI763006105Y) - packages/herdr/README.md: document the [esc] back / (N levels) footer hint - packages/tui/extensions/README.md: correct hierarchical navigation docs — Tab drills into children (Enter opens the detail view, not children); add back-hint note
…and (WL-0MS9HIUE0002JAKQ) The run-in-pane.sh --exec wrapper previously auto-closed the pane after a 500ms pause on exit 0, which was too fast for the user to read the output. Now the pane stays open for any exit status; the wrapper reports the exit status and prints a hint to close the pane manually (herdr prefix+x). - packages/herdr/scripts/run-in-pane.sh: remove sleep+pane close on success; print status line + close hint - packages/herdr/src/index.ts: update onCommand comment - packages/herdr/README.md: update routing docs - tests/herdr/run-in-pane.test.ts: 6 tests for --exec mode with mock herdr
…alive (WL-0MS9HIUE0002JAKQ) Root cause: herdr tears down a pane when its primary process exits. The previous fix only removed the explicit 'herdr pane close' call, but the --exec wrapper still exited after printing the status, so herdr still terminated the pane ~0.7s after spawn (no pane.close API call observed). Real fix: the --exec wrapper now keeps the pane's process alive after the command finishes: - TTY stdin (interactive pane): waits for Enter, hint mentions prefix+x - HERDR_PANE_ID set, non-TTY stdin: blocks on read from /dev/zero until the user closes the pane with prefix+x - Otherwise (tests/automation): exits immediately with the command status - packages/herdr/scripts/run-in-pane.sh: keep-alive logic + comments - packages/herdr/src/index.ts: updated onCommand comment - packages/herdr/README.md: updated wording (Enter / prefix+x dismiss) - tests/herdr/run-in-pane.test.ts: 8 tests incl. PTY-based 'stays alive' checks and HERDR_PANE_ID non-TTY keep-alive via timeout (124)
…L-0MS9PL90F002MR8G) Global ~/.pi/agent/AGENTS.md now uses absolute /home/rgardler/.pi/agent/skills/... paths; update the doc example to match (was showing a 'skills/' prefix that did not exist).
…flake (WL-0MS9TGA4X004ZPOD) Audit fixes: - browse.ts: auto-refresh now re-fetches the total actionable count so the 'top N of M' title stays fresh (WL-0MS4FIEN40037GB9); heading N is the actual displayed count, not capped to M, when the mandatory set exceeds the actionable total (WL-0MS8XOOMN0022LLH) - worklist.ts: fix stale formatDetailContent JSDoc metadata list (WL-0MS4FIM8T001XAVF) - herdr index.ts + settings.ts: showHelpText re-read on each TUI invocation (no restart needed); centralize browseItemCount clamp in settings.ts (WL-0MS4FJ2TX009V7V5) - CHANGELOG.md: document recently merged features (WL-0MS4FIEN40037GB9) - tests: auto-refresh total-count test, mandatory-set-exceeds-total heading test, browseItemCount clamp tests Flake fix: - cli-utils-markdown.test.ts: use a vi.hoisted shared loadConfig mock instead of vi.spyOn on the module namespace (which was flaky in full-suite runs); reset + default re-apply in beforeEach. This was the last intermittent failure blocking the audit gate. Full suite: 3920 passed, 0 failed (twice).
…or paths (WL-0MS4FIEN40037GB9) Covers the Herdr-side total-count fetch (previously only render-level undefined handling was tested): count parse, missing-count undefined, wl-failure graceful degradation, and the open/in-progress/blocked query.
…0MS4FJ2TX009V7V5, WL-0MS4FIM8T001XAVF) - herdr index.ts + worklist.ts: showHelpText re-read via getShowHelpText() callback on every render, so the setting applies on next refresh without a plugin restart (matches browseItemCount behavior) - herdr README: document browseItemCount/showHelpText/showIcons in the settings list; document GitHub Issue number in the detail view features - tests: herdr suite green (427)
…key (WL-0MS4FIUYS001K08K)
- auto-sync.ts: runSync now returns { success, error } so the UI can surface
sync status instead of silently discarding failures
- worklist.ts: doSync() renders '[Synced]' / '[Sync failed: ...]' in the
notification area; wired into the auto-refresh and auto-sync timers; new
'S' (uppercase) key triggers a manual sync
- tests: runSync success/failure/exit-code tests, manual 'S' key action test
Full suite: 3927 passed, 0 failed.
…initialized-report tests (WL-0MS6LS2TF007AV63, WL-0MS6LSFOH001E2YJ) - index.ts: route plain (non-!!) shell commands through run-in-pane.sh with --cwd targetCwd so they execute from the tab working directory (herdr has no CMD: handling, so the stdout CMD: protocol was a dead execution path) - index.ts: fetcher returns an empty list when no valid .worklog/ exists in the tab dir, so the TUI shows the uninitialized/empty state instead of resolving the plugin's own CWD worklog - index.ts: extract uninitializedReport() helper; main() uses it - index.test.ts: assert the uninitialized stderr messages (Showing empty worklist / No valid .worklog) Full suite: 3928 passed, 0 failed.
- auto-sync.ts: runSync(worklogDir?) accepts the resolved worklog dir and passes --worklog-dir to wl sync (avoids circular import with fetcher) - worklist.ts: doSync() passes getWorklogDir() so background sync targets the tab project instead of the plugin pane CWD - tests: runSync --worklog-dir argument test Full suite: 3929 passed, 0 failed.
…(WL-0MS9TGA4X004ZPOD) dev's CHANGELOG was behind main (missing v1.0.4 release notes), causing a merge conflict in the dev→main release flow. Merge main's version history into dev's CHANGELOG, keeping the Unreleased section for this release.
…004ZPOD) Importing index.js in a vitest worker previously triggered main(), which can call process.exit(1) (e.g. wl not on PATH in CI), crashing the test runner and failing the cli-tests/install-and-smoke-test CI checks on the release PR. main() now runs only when index.js is the entry point.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Automated release created by ship skill.\n\nIncludes CHANGELOG.md with work-item summaries from this release.