stablyai/orca · error · Error
Cannot safely offer force-delete for preserved branch "${res
Error message
Cannot safely offer force-delete for preserved branch "${result.preservedBranch.branchName}" without its saved commit. What it means
Thrown by rememberPreservedBranchCleanupTarget when a RemoveWorktreeResult reports a preservedBranch but neither result.preservedBranch.head nor the fallbackHead (the registered worktree's HEAD) is available. Without a concrete commit SHA, Orca refuses to register a force-delete target because it cannot prove which commit to delete. This is a defensive invariant inside the remove flow, not a user-input error.
Source
Thrown at src/main/ipc/worktrees.ts:545
hostId: ExecutionHostId
branchName: string
head: string
pushTarget?: GitPushTarget
}
const preservedBranchCleanupByScope = new Map<string, PreservedBranchCleanupTarget>()
function rememberPreservedBranchCleanupTarget(
worktreeId: string,
hostId: ExecutionHostId,
result: RemoveWorktreeResult | undefined,
fallbackHead: string | undefined,
pushTarget: GitPushTarget | undefined
): void {
if (result?.preservedBranch) {
const head = result.preservedBranch.head ?? fallbackHead
if (!head) {
throw new Error(
`Cannot safely offer force-delete for preserved branch "${result.preservedBranch.branchName}" without its saved commit.`
)
}
preservedBranchCleanupByScope.set(preservedBranchCleanupScopeKey({ worktreeId, hostId }), {
worktreeId,
hostId,
branchName: result.preservedBranch.branchName,
head,
...(pushTarget ? { pushTarget } : {})
})
return
}
preservedBranchCleanupByScope.delete(preservedBranchCleanupScopeKey({ worktreeId, hostId }))
}
function preserveBranchHeadFallback(
result: RemoveWorktreeResult | undefined,
fallbackHead: string | undefinedView on GitHub (pinned to 1136503c6a)
Solutions
- Ensure the Git worktree list reports a HEAD for that worktree (check `git worktree list --porcelain` on the host).
- If using an SSH provider, confirm the provider version returns head in its worktree listings.
- Treat this as an internal defect: capture the remove args and the worktree list at the time of failure and report it, since the caller cannot supply the missing commit safely.
Defensive patterns
Strategy: try-catch
Try / catch
// In the remove flow, guard the remember call so a missing head does not abort cleanup.
try {
rememberPreservedBranchCleanupTarget(worktreeId, hostId, removalResult, fallbackHead, pushTarget)
} catch (e) {
// Log and skip registering a force-delete target; the branch can still be deleted manually later.
console.warn('[worktrees] cannot register preserved-branch cleanup (no head)', e)
} Prevention
- Treat a missing head as a provider/Git defect to investigate, not a user error.
- Ensure SSH providers return head in worktree listings.
- Capture the worktree list at failure time to diagnose why HEAD was unresolved.
When it happens
Trigger: A worktrees:remove whose Git result preserved a branch (preserveBranchOnDelete) but the worktree list entry carried no resolvable head, and the registeredWorktree.head passed as fallback was also undefined.
Common situations: Git reported a detached/unborn HEAD for the worktree, a remote SSH provider returned a worktree entry without head metadata, or an older provider implementation omitted the head field. Usually points to an unexpected Git/provider state rather than a config mistake.
Related errors
- No preserved branch cleanup is pending for "${branchName}".
- SSH filesystem provider unavailable
- SSH filesystem provider lstat unavailable
- ${response.error.message}
- Couldn't verify the SSH connection. Reconnect the host and t
AI-assisted analysis of stablyai/orca@1136503c6a (2026-08-12).
Data as JSON: /api/errors/259dc2dc900f3454.
Report an issue: GitHub.