Files
orca/src/main/git/git-capability-state.ts
T
OrcaWinandOrcaWin 9deb72f9ed fix(git): support Windows-linked worktrees in WSL projects (#13483)
* fix(git): support Windows-linked worktrees in WSL projects

* fix(git): harden WSL linked worktree routing

* fix(test): defer WSL routing filesystem access

* test(git): type WSL routing probe mock

* fix(git): retry transient WSL route probes safely

---------

Co-authored-by: OrcaWin <293788423+OrcaWin@users.noreply.github.com>
2026-08-10 21:19:01 -07:00

72 lines
2.3 KiB
TypeScript

import { GitCapabilityCache } from '../../shared/git-capability-cache'
import { parseWslUncPath } from '../../shared/wsl-paths'
import {
isWslLinkedWorktreeGitRoutingCandidate,
prepareWslLinkedWorktreeGitRouting
} from './wsl-linked-worktree-git-routing'
type LocalGitCapabilityTarget = {
cwd?: string
wslDistro?: string
signal?: AbortSignal
}
const localCapabilitiesByExecutionHost = new Map<string, GitCapabilityCache>()
// Why: reconnecting creates a new provider, while concurrent IPC/runtime users
// of one SSH connection must share the same remote Git capability results.
let sshCapabilitiesByProvider = new WeakMap<object, GitCapabilityCache>()
function getLocalGitExecutionHostKey(target: LocalGitCapabilityTarget): string {
const wslDistro =
target.wslDistro ?? (target.cwd ? parseWslUncPath(target.cwd)?.distro : undefined)
return wslDistro ? `wsl:${wslDistro}` : 'local'
}
export function getLocalGitCapabilityCache(
target: LocalGitCapabilityTarget = {}
): GitCapabilityCache {
const executionHost = getLocalGitExecutionHostKey(target)
let cache = localCapabilitiesByExecutionHost.get(executionHost)
if (!cache) {
cache = new GitCapabilityCache()
localCapabilitiesByExecutionHost.set(executionHost, cache)
}
return cache
}
export function withLocalGitCapabilityCacheForExecution<T>(
target: LocalGitCapabilityTarget,
run: (capabilities: GitCapabilityCache) => Promise<T>
): Promise<T> {
if (!target.cwd || !isWslLinkedWorktreeGitRoutingCandidate(target.cwd, target.wslDistro)) {
try {
return run(getLocalGitCapabilityCache(target))
} catch (error) {
return Promise.reject(error)
}
}
return prepareWslLinkedWorktreeGitRouting(target.cwd, target.wslDistro, {
signal: target.signal
}).then((usesHostGit) =>
run(
getLocalGitCapabilityCache(
usesHostGit ? { cwd: target.cwd } : { cwd: target.cwd, wslDistro: target.wslDistro }
)
)
)
}
export function getSshGitCapabilityCache(provider: object): GitCapabilityCache {
let cache = sshCapabilitiesByProvider.get(provider)
if (!cache) {
cache = new GitCapabilityCache()
sshCapabilitiesByProvider.set(provider, cache)
}
return cache
}
export function clearGitCapabilityStateForTests(): void {
localCapabilitiesByExecutionHost.clear()
sshCapabilitiesByProvider = new WeakMap()
}