@brimveyn/aimux-config 0.6.10 → 0.6.12

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@brimveyn/aimux-config",
3
- "version": "0.6.10",
3
+ "version": "0.6.12",
4
4
  "description": "TypeScript configuration API for aimux — keymaps, themes, and backends with a fluent builder.",
5
5
  "keywords": [
6
6
  "aimux",
package/src/actions.ts CHANGED
@@ -403,7 +403,10 @@ export const openWorktreeMove: ActionFn = (ctx: ModeContext) => {
403
403
  }
404
404
  // Overlay: no mode transition — deriveModeId routes input to the picker and
405
405
  // focusMode stays 'git' so the git view remains mounted underneath.
406
- return r([{ sourceWorktreeId: source.id, type: 'open-worktree-move-modal' }])
406
+ return r(
407
+ [{ sourceWorktreeId: source.id, type: 'open-worktree-move-modal' }],
408
+ [{ type: 'load-worktree-move-stats' }]
409
+ )
407
410
  }
408
411
 
409
412
  export const toggleWorktreeMoveDelete: KeyResult = r([{ type: 'toggle-worktree-move-delete' }])
@@ -436,6 +439,27 @@ export const confirmWorktreeMove: ActionFn = (ctx: ModeContext) => {
436
439
  )
437
440
  }
438
441
 
442
+ // Confirms the dialog opened after a recoverable move failure: re-runs the
443
+ // move with the flag matching the failure (stash the target / keep conflicts).
444
+ export const confirmWorktreeMoveRetry: ActionFn = (ctx: ModeContext) => {
445
+ const modal = ctx.state.modal
446
+ if (modal.type !== 'worktree-move-confirm') return null
447
+ return r(
448
+ [{ type: 'close-modal' }],
449
+ [
450
+ {
451
+ deleteSource: modal.deleteSource,
452
+ sessionId: modal.sessionId,
453
+ sourceWorktreeId: modal.sourceWorktreeId,
454
+ targetWorktreeId: modal.targetWorktreeId,
455
+ type: 'move-worktree',
456
+ ...(modal.variant === 'stash-target' ? { stashTarget: true } : { keepConflicts: true }),
457
+ },
458
+ ],
459
+ 'navigation'
460
+ )
461
+ }
462
+
439
463
  export const closePane: ActionFn = (ctx: ModeContext) => {
440
464
  const tabId = ctx.state.activeTabId
441
465
  if (!(tabId != null && tabId !== '')) return null
@@ -501,6 +525,25 @@ export const confirmRenameTab: ActionFn = (ctx: ModeContext) => {
501
525
  return r(actions, [], 'navigation')
502
526
  }
503
527
 
528
+ // Rename worktree modal
529
+ export const confirmRenameWorktree: ActionFn = (ctx: ModeContext) => {
530
+ const { modal } = ctx.state
531
+ const trimmed = (modal.editBuffer ?? '').trim()
532
+ const worktreeId = modal.sessionTargetId
533
+ const sessionId = modal.type === 'rename-worktree' ? modal.worktreeSessionId : null
534
+ const actions: KeyResult['actions'] = []
535
+ if (trimmed && worktreeId != null && worktreeId !== '' && sessionId != null && sessionId !== '') {
536
+ actions.push({
537
+ patch: { name: trimmed },
538
+ sessionId,
539
+ type: 'update-worktree-record',
540
+ worktreeId,
541
+ })
542
+ }
543
+ actions.push({ type: 'close-modal' })
544
+ return r(actions, [], 'navigation')
545
+ }
546
+
504
547
  // Create session modal
505
548
  export const confirmCreateSession: ActionFn = (ctx: ModeContext) => {
506
549
  const modal = ctx.state.modal as {
package/src/defaults.ts CHANGED
@@ -204,6 +204,17 @@ export function getDefaultKeymapConfig(): ResolvedKeymapConfig {
204
204
  .map('<CR>', actions.confirmWorktreeMove, 'Move')
205
205
  )
206
206
 
207
+ // -----------------------------------------------------------------------
208
+ // Modal: worktree-move recoverable-failure confirmation (stash / conflicts)
209
+ // -----------------------------------------------------------------------
210
+ .mode('modal.worktree-move-confirm', (m) =>
211
+ m
212
+ .map('<Esc>', actions.closeModal, 'Cancel')
213
+ .map('n', actions.closeModal, 'Cancel')
214
+ .map('<CR>', actions.confirmWorktreeMoveRetry, 'Confirm')
215
+ .map('y', actions.confirmWorktreeMoveRetry, 'Confirm')
216
+ )
217
+
207
218
  // -----------------------------------------------------------------------
208
219
  // Modal: standalone worktree delete confirmation (sidebar "Remove worktree")
209
220
  // -----------------------------------------------------------------------
@@ -225,6 +236,16 @@ export function getDefaultKeymapConfig(): ResolvedKeymapConfig {
225
236
  .passthrough()
226
237
  )
227
238
 
239
+ // -----------------------------------------------------------------------
240
+ // Modal: rename-worktree
241
+ // -----------------------------------------------------------------------
242
+ .mode('modal.rename-worktree', (m) =>
243
+ m
244
+ .map('<Esc>', actions.closeModal, 'Cancel')
245
+ .map('<CR>', actions.confirmRenameWorktree, 'Confirm')
246
+ .passthrough()
247
+ )
248
+
228
249
  // -----------------------------------------------------------------------
229
250
  // Modal: new-tab (always in filter mode via Picker)
230
251
  // -----------------------------------------------------------------------
package/src/types.ts CHANGED
@@ -20,6 +20,7 @@ export type ModeId =
20
20
  | 'modal.session-name'
21
21
  | 'modal.create-session'
22
22
  | 'modal.rename-tab'
23
+ | 'modal.rename-worktree'
23
24
  | 'modal.snippet-picker.filtering'
24
25
  | 'modal.snippet-editor'
25
26
  | 'modal.theme-picker.filtering'
@@ -30,6 +31,7 @@ export type ModeId =
30
31
  | 'modal.git-commit.generating'
31
32
  | 'modal.update-available'
32
33
  | 'modal.worktree-move'
34
+ | 'modal.worktree-move-confirm'
33
35
  | 'modal.ai-usage'
34
36
 
35
37
  // ─── Primitive app types ──────────────────────────────────────────────────────
@@ -324,6 +326,10 @@ export interface ModalSessionName extends ModalBase {
324
326
  export interface ModalRenameTab extends ModalBase {
325
327
  type: 'rename-tab'
326
328
  }
329
+ export interface ModalRenameWorktree extends ModalBase {
330
+ type: 'rename-worktree'
331
+ worktreeSessionId: string
332
+ }
327
333
  export interface ModalSnippetPicker extends ModalBase {
328
334
  type: 'snippet-picker'
329
335
  actionMessage?: string | null
@@ -378,6 +384,26 @@ export interface ModalWorktreeMove extends ModalBase {
378
384
  /** The worktree being moved (may differ from the active one, e.g. a tab menu). */
379
385
  sourceWorktreeId: string
380
386
  deleteSource: boolean
387
+ /** Per-worktree dirty file counts, loaded async when the modal opens. */
388
+ stats: { kind: 'loading' } | { kind: 'ready'; dirtyFiles: Record<string, number> }
389
+ }
390
+
391
+ /**
392
+ * Confirmation for a recoverable move failure: the target's dirty files
393
+ * overlap the incoming changes (stash-target) or the squash conflicts
394
+ * (keep-conflicts). Both worktrees are already restored; confirming re-runs
395
+ * move-worktree with the matching flag.
396
+ */
397
+ export interface ModalWorktreeMoveConfirm extends ModalBase {
398
+ type: 'worktree-move-confirm'
399
+ variant: 'stash-target' | 'keep-conflicts'
400
+ files: string[]
401
+ sessionId: string
402
+ sourceWorktreeId: string
403
+ targetWorktreeId: string
404
+ deleteSource: boolean
405
+ sourceLabel: string
406
+ targetLabel: string
381
407
  }
382
408
 
383
409
  /**
@@ -402,6 +428,7 @@ export type ModalState =
402
428
  | ModalSessionPicker
403
429
  | ModalSessionName
404
430
  | ModalRenameTab
431
+ | ModalRenameWorktree
405
432
  | ModalSnippetPicker
406
433
  | ModalThemePicker
407
434
  | ModalHelp
@@ -412,6 +439,7 @@ export type ModalState =
412
439
  | ModalUpdateAvailable
413
440
  | ModalAIUsage
414
441
  | ModalWorktreeMove
442
+ | ModalWorktreeMoveConfirm
415
443
  | ModalWorktreeDeleteConfirm
416
444
 
417
445
  export interface LayoutState {
@@ -515,6 +543,12 @@ export type ModalAction =
515
543
  | { type: 'switch-create-session-field' }
516
544
  | { type: 'select-directory' }
517
545
  | { type: 'open-rename-tab-modal' }
546
+ | {
547
+ type: 'open-rename-worktree-modal'
548
+ sessionId: string
549
+ worktreeId: string
550
+ initialName: string
551
+ }
518
552
  | { type: 'open-snippet-picker' }
519
553
  | { type: 'open-snippet-editor'; snippetId?: string }
520
554
  | { type: 'set-help-entry-count'; count: number }
@@ -526,6 +560,18 @@ export type ModalAction =
526
560
  | { type: 'open-edit-custom-command'; assistantId: AssistantId }
527
561
  | { type: 'open-worktree-move-modal'; sourceWorktreeId: string }
528
562
  | { type: 'toggle-worktree-move-delete' }
563
+ | { type: 'set-worktree-move-stats'; dirtyFiles: Record<string, number> }
564
+ | {
565
+ type: 'open-worktree-move-confirm'
566
+ variant: 'stash-target' | 'keep-conflicts'
567
+ files: string[]
568
+ sessionId: string
569
+ sourceWorktreeId: string
570
+ targetWorktreeId: string
571
+ deleteSource: boolean
572
+ sourceLabel: string
573
+ targetLabel: string
574
+ }
529
575
  | {
530
576
  type: 'open-worktree-delete-confirm'
531
577
  sessionId: string
@@ -799,7 +845,11 @@ export type SideEffect =
799
845
  sourceWorktreeId: string
800
846
  targetWorktreeId: string
801
847
  deleteSource?: boolean
848
+ // Retry flags set by the worktree-move-confirm dialog.
849
+ stashTarget?: boolean
850
+ keepConflicts?: boolean
802
851
  }
852
+ | { type: 'load-worktree-move-stats' }
803
853
  | { type: 'toggle-transparent' }
804
854
  | { type: 'toggle-mode' }
805
855
  | { type: 'open-file-in-editor'; path: string }