Files
orca/tests/e2e/worktree-delete-shortcut.spec.ts
T
JinjingandBrennan Benson 7b9529da22 Add keyboard shortcut for workspace deletion (#16271)
* Add keyboard shortcut for workspace deletion

Default Mod+Shift+Backspace (⌘⇧⌫ on Mac) lets users delete the hovered
worktree or folder workspace immediately. The shortcut targets the
sidebar hover state rather than requiring focus, and avoids terminal
pane D-based split shortcuts on all platforms.

Co-authored-by: Brennan Benson <brennankbenson@gmail.com>

* Omit delete shortcut from disabled Delete Worktree for primary checkout

- Remove shortcut badge from the disabled "Delete Worktree" action when it cannot be executed
- Only show shortcut in multi-context delete actions where the command is available
- Extract host identity parsing into reusable helper function to prevent inline string manipulation
- Fix folder workspace deletion to use correct host-qualified identity comparison

* Document host extraction safety for destructive worktree ops

Unqualified identities must stay undefined rather than defaulting to
'local'. Destructive operations depend on correct host identification.
Added tests and JSDoc to clarify this safety-critical behavior.

* fix test

---------

Co-authored-by: Brennan Benson <brennankbenson@gmail.com>
2026-08-24 10:12:38 -07:00

77 lines
2.5 KiB
TypeScript

import { test, expect } from './helpers/orca-app'
import { getAllWorktreeIds, waitForActiveWorktree, waitForSessionReady } from './helpers/store'
import { pressShortcut } from './helpers/shortcuts'
import { worktreeRow } from './worktree-row-locators'
async function createIsolatedWorktree(
page: Parameters<typeof waitForActiveWorktree>[0]
): Promise<string> {
const name = `e2e-delete-shortcut-${Date.now()}`
return page.evaluate(async (worktreeName) => {
const state = window.__store?.getState()
if (!state?.activeWorktreeId) {
throw new Error('No active worktree to derive repo from')
}
const worktree = Object.values(state.worktreesByRepo)
.flat()
.find((candidate) => candidate.id === state.activeWorktreeId)
if (!worktree) {
throw new Error('Active worktree was not found')
}
const result = await state.createWorktree(worktree.repoId, worktreeName)
await state.fetchWorktrees(worktree.repoId)
return result.worktree.id
}, name)
}
test.describe('Worktree Delete Shortcut', () => {
let createdWorktreeId: string | null = null
test.beforeEach(async ({ orcaPage }) => {
await waitForSessionReady(orcaPage)
await waitForActiveWorktree(orcaPage)
})
test.afterEach(async ({ orcaPage }) => {
if (!createdWorktreeId) {
return
}
const worktreeId = createdWorktreeId
createdWorktreeId = null
await orcaPage
.evaluate(async (id) => {
const state = window.__store?.getState()
await state?.removeWorktree(
{ id, executionHostId: state.getKnownWorktreeById(id)?.hostId ?? null },
true
)
}, worktreeId)
.catch(() => undefined)
})
test('deletes the hovered worktree after Mod+Shift+Backspace confirmation', async ({
orcaPage
}) => {
createdWorktreeId = await createIsolatedWorktree(orcaPage)
const worktreeId = createdWorktreeId
const row = worktreeRow(orcaPage, worktreeId)
await expect(row).toBeVisible()
await row.hover()
await pressShortcut(orcaPage, 'Backspace', { shift: true })
const dialog = orcaPage.getByRole('dialog')
await expect(dialog).toBeVisible()
await dialog.getByRole('button', { name: 'Delete Workspace', exact: true }).click()
await expect
.poll(async () => getAllWorktreeIds(orcaPage), {
timeout: 15_000,
message: 'hovered worktree was not removed by the delete shortcut'
})
.not.toContain(worktreeId)
createdWorktreeId = null
})
})