perf: coalesce git upstream status reads

This commit is contained in:
Neil
2026-07-30 03:52:00 -07:00
parent 6fee674c48
commit b680c59da6
8 changed files with 650 additions and 5 deletions
@@ -0,0 +1,120 @@
import { describe, expect, it, vi } from 'vitest'
import type { GitPushTarget, GitUpstreamStatus } from '../../shared/types'
import {
GitUpstreamStatusReadOwner,
type GitUpstreamStatusExecutionIdentity
} from './git-upstream-status-read-owner'
const upstreamStatus: GitUpstreamStatus = {
hasUpstream: true,
upstreamName: 'origin/main',
ahead: 1,
behind: 0
}
function deferredPromise<T>(): {
promise: Promise<T>
resolve: (value: T) => void
reject: (error: unknown) => void
} {
let resolve!: (value: T) => void
let reject!: (error: unknown) => void
const promise = new Promise<T>((innerResolve, innerReject) => {
resolve = innerResolve
reject = innerReject
})
return { promise, resolve, reject }
}
describe('GitUpstreamStatusReadOwner', () => {
it('shares one live read across ten identical callers', async () => {
const owner = new GitUpstreamStatusReadOwner()
const pending = deferredPromise<GitUpstreamStatus>()
const load = vi.fn(() => pending.promise)
const reads = Array.from({ length: 10 }, () =>
owner.read({ kind: 'native' }, '/repo', undefined, load)
)
await Promise.resolve()
expect(load).toHaveBeenCalledTimes(1)
pending.resolve(upstreamStatus)
await expect(Promise.all(reads)).resolves.toEqual(
Array.from({ length: 10 }, () => upstreamStatus)
)
})
it('isolates paths, execution hosts, and every explicit target field', async () => {
const owner = new GitUpstreamStatusReadOwner()
const load = vi.fn().mockResolvedValue(upstreamStatus)
const baseTarget: GitPushTarget = {
remoteName: 'fork',
branchName: 'feature'
}
const cases: [GitUpstreamStatusExecutionIdentity, string, GitPushTarget | undefined][] = [
[{ kind: 'native' }, '/repo-a', undefined],
[{ kind: 'native' }, '/repo-b', undefined],
[{ kind: 'wsl', distro: 'Ubuntu' }, '/repo-a', undefined],
[{ kind: 'wsl', distro: 'Debian' }, '/repo-a', undefined],
[{ kind: 'native' }, '/repo-a', baseTarget],
[{ kind: 'native' }, '/repo-a', { ...baseTarget, remoteName: 'origin' }],
[{ kind: 'native' }, '/repo-a', { ...baseTarget, branchName: 'other' }],
[
{ kind: 'native' },
'/repo-a',
{ ...baseTarget, remoteUrl: 'https://github.com/example/fork.git' }
],
[{ kind: 'native' }, '/repo-a', { ...baseTarget, remoteCreated: false }],
[{ kind: 'native' }, '/repo-a', { ...baseTarget, remoteCreated: true }],
[{ kind: 'ssh-provider' }, '/repo-a', baseTarget]
]
await Promise.all(
cases.map(([identity, worktreePath, target]) =>
owner.read(identity, worktreePath, target, load)
)
)
expect(load).toHaveBeenCalledTimes(cases.length)
})
it('runs fresh work after success and rejection', async () => {
const owner = new GitUpstreamStatusReadOwner()
const failure = new Error('upstream failed')
const load = vi
.fn<() => Promise<GitUpstreamStatus>>()
.mockResolvedValueOnce(upstreamStatus)
.mockRejectedValueOnce(failure)
.mockResolvedValueOnce(upstreamStatus)
await expect(owner.read({ kind: 'native' }, '/repo', undefined, load)).resolves.toBe(
upstreamStatus
)
await expect(owner.read({ kind: 'native' }, '/repo', undefined, load)).rejects.toBe(failure)
await expect(owner.read({ kind: 'native' }, '/repo', undefined, load)).resolves.toBe(
upstreamStatus
)
expect(load).toHaveBeenCalledTimes(3)
})
it('fences before, during, and after mutation generations', async () => {
const owner = new GitUpstreamStatusReadOwner()
const pendingReads = Array.from({ length: 3 }, () => deferredPromise<GitUpstreamStatus>())
const load = vi.fn(() => pendingReads[load.mock.calls.length - 1].promise)
const before = owner.read({ kind: 'native' }, '/repo', undefined, load)
await Promise.resolve()
owner.invalidate()
const during = owner.read({ kind: 'native' }, '/repo', undefined, load)
await Promise.resolve()
owner.invalidate()
const after = owner.read({ kind: 'native' }, '/repo', undefined, load)
await Promise.resolve()
pendingReads.forEach((pending) => pending.resolve(upstreamStatus))
await expect(Promise.all([before, during, after])).resolves.toEqual(
Array.from({ length: 3 }, () => upstreamStatus)
)
expect(load).toHaveBeenCalledTimes(3)
})
})
@@ -0,0 +1,39 @@
import type { GitPushTarget, GitUpstreamStatus } from '../../shared/types'
import { InFlightPromiseDedupe, stableInFlightKey } from '../../shared/in-flight-promise-dedupe'
export type GitUpstreamStatusExecutionIdentity =
| { kind: 'native' }
| { kind: 'wsl'; distro: string }
| { kind: 'ssh-provider' }
export class GitUpstreamStatusReadOwner {
private readonly inFlightReads = new InFlightPromiseDedupe<GitUpstreamStatus>()
read(
executionIdentity: GitUpstreamStatusExecutionIdentity,
worktreePath: string,
pushTarget: GitPushTarget | undefined,
load: () => Promise<GitUpstreamStatus>
): Promise<GitUpstreamStatus> {
const key = stableInFlightKey([
executionIdentity,
worktreePath,
pushTarget
? [
'explicit-target',
pushTarget.remoteName,
pushTarget.branchName,
pushTarget.remoteUrl ?? null,
pushTarget.remoteCreated ?? null
]
: ['configured-upstream']
])
return this.inFlightReads.run(key, load)
}
invalidate(): void {
this.inFlightReads.clear()
}
}
export const nativeAndWslGitUpstreamStatusReadOwner = new GitUpstreamStatusReadOwner()
+2
View File
@@ -54,6 +54,7 @@ import type { GitRuntimeOptions } from './git-runtime-options'
import { gitOptionsForWorktree } from './git-runtime-options'
import { GitStatusReadLeaseOwner } from './git-status-read-lease-owner'
import { parseGitRevListFirstParentOid } from '../../shared/git-rev-list-output'
import { nativeAndWslGitUpstreamStatusReadOwner } from './git-upstream-status-read-owner'
import {
beginGitStatusLineStatsCacheWrite,
clearGitStatusLineStatsCache,
@@ -99,6 +100,7 @@ const statusReadLeaseOwner = new GitStatusReadLeaseOwner<GitStatusResult>()
export function invalidateGitReadCaches(): void {
gitDiffReadDedupe.clear()
statusReadLeaseOwner.invalidate()
nativeAndWslGitUpstreamStatusReadOwner.invalidate()
clearGitStatusLineStatsCache()
clearSubmodulePathsCache()
resolvedUpstreamNameCache.clear()
+155 -1
View File
@@ -1,4 +1,6 @@
import { beforeEach, describe, expect, it, vi } from 'vitest'
import type * as NodeFs from 'node:fs'
import path from 'node:path'
const { gitExecFileAsyncMock } = vi.hoisted(() => ({
gitExecFileAsyncMock: vi.fn()
@@ -8,7 +10,8 @@ vi.mock('./runner', () => ({
gitExecFileAsync: gitExecFileAsyncMock
}))
import { getUpstreamStatus } from './upstream'
import { getUpstreamStatus, invalidateGitUpstreamStatusReads } from './upstream'
import { runWithGitReadCacheInvalidation } from './status'
const missingTrackingRefError = new Error(
"fatal: ambiguous argument 'HEAD@{u}': unknown revision or path not in the working tree.\n" +
@@ -19,6 +22,157 @@ const missingTrackingRefError = new Error(
describe('getUpstreamStatus', () => {
beforeEach(() => {
gitExecFileAsyncMock.mockReset()
invalidateGitUpstreamStatusReads()
})
it('benchmarks concurrent upstream Git command pressure', async () => {
const benchPath = process.env.ORCA_GIT_UPSTREAM_COALESCING_BENCH_JSON
if (!benchPath) {
return
}
gitExecFileAsyncMock.mockImplementation((args: string[]) => {
if (args[0] === 'symbolic-ref') {
return Promise.resolve({ stdout: 'main\n' })
}
if (args[0] === 'rev-parse') {
return Promise.resolve({ stdout: 'origin/main\n' })
}
if (args[0] === 'rev-list') {
return Promise.resolve({ stdout: '2\t3\n' })
}
if (args[0] === 'log') {
return Promise.resolve({ stdout: '+ abc123 remote work\n' })
}
throw new Error(`unexpected git args: ${args.join(' ')}`)
})
await Promise.all(Array.from({ length: 10 }, () => getUpstreamStatus('/repo')))
const commands = gitExecFileAsyncMock.mock.calls.map(([args, options]) => ({ args, options }))
const commandCounts = Object.fromEntries(
['symbolic-ref', 'rev-parse', 'rev-list', 'log'].map((command) => [
command,
commands.filter(({ args }) => args[0] === command).length
])
)
const { mkdirSync, writeFileSync } = await vi.importActual<typeof NodeFs>('node:fs')
mkdirSync(path.dirname(benchPath), { recursive: true })
writeFileSync(
benchPath,
JSON.stringify({
scenario: 'local-git-upstream-concurrent-burst',
concurrentCalls: 10,
physicalGitCalls: commands.length,
commandCounts,
commandChain: ['symbolic-ref', 'rev-parse', 'rev-list', 'log'].map((command) =>
commands.find(({ args }) => args[0] === command)
)
})
)
})
it('isolates physical reads by worktree, native or WSL host, and every target field', async () => {
gitExecFileAsyncMock.mockImplementation((args: string[]) => {
if (args[0] === 'symbolic-ref') {
return Promise.resolve({ stdout: 'main\n' })
}
if (args[0] === 'check-ref-format') {
return Promise.resolve({ stdout: '' })
}
if (args[0] === 'rev-parse' && args.includes('HEAD@{u}')) {
return Promise.resolve({ stdout: 'origin/main\n' })
}
if (args[0] === 'rev-parse' && args.includes('--verify')) {
return Promise.resolve({ stdout: 'abc123\n' })
}
if (args[0] === 'rev-list') {
return Promise.resolve({ stdout: '0\t0\n' })
}
throw new Error(`unexpected git args: ${args.join(' ')}`)
})
const baseTarget = { remoteName: 'fork', branchName: 'feature' }
await Promise.all([
getUpstreamStatus('/repo-a'),
getUpstreamStatus('/repo-b'),
getUpstreamStatus('/repo-a', undefined, { wslDistro: 'Ubuntu' }),
getUpstreamStatus('/repo-a', undefined, { wslDistro: 'Debian' }),
getUpstreamStatus('/repo-a', baseTarget),
getUpstreamStatus('/repo-a', { ...baseTarget, remoteName: 'origin' }),
getUpstreamStatus('/repo-a', { ...baseTarget, branchName: 'other' }),
getUpstreamStatus('/repo-a', {
...baseTarget,
remoteUrl: 'https://github.com/example/fork.git'
}),
getUpstreamStatus('/repo-a', { ...baseTarget, remoteCreated: false }),
getUpstreamStatus('/repo-a', { ...baseTarget, remoteCreated: true })
])
expect(
gitExecFileAsyncMock.mock.calls.filter(([args]) => args[0] === 'symbolic-ref')
).toHaveLength(4)
expect(
gitExecFileAsyncMock.mock.calls.filter(([args]) => args[0] === 'check-ref-format')
).toHaveLength(6)
})
it('runs fresh physical work after a normalized rejection', async () => {
gitExecFileAsyncMock
.mockResolvedValueOnce({ stdout: 'main\n' })
.mockResolvedValueOnce({ stdout: 'origin/main\n' })
.mockRejectedValueOnce(new Error('fatal: authentication failed'))
.mockResolvedValueOnce({ stdout: 'main\n' })
.mockResolvedValueOnce({ stdout: 'origin/main\n' })
.mockResolvedValueOnce({ stdout: '0\t0\n' })
await expect(getUpstreamStatus('/repo')).rejects.toThrow('fatal: authentication failed')
await expect(getUpstreamStatus('/repo')).resolves.toMatchObject({
hasUpstream: true,
upstreamName: 'origin/main'
})
expect(gitExecFileAsyncMock).toHaveBeenCalledTimes(6)
})
it('uses the common pre/post mutation fence for physical upstream reads', async () => {
const pendingReads: {
promise: Promise<{ stdout: string }>
resolve: (value: { stdout: string }) => void
}[] = []
gitExecFileAsyncMock.mockImplementation((args: string[]) => {
if (args[0] === 'symbolic-ref') {
let resolve!: (value: { stdout: string }) => void
const promise = new Promise<{ stdout: string }>((innerResolve) => {
resolve = innerResolve
})
pendingReads.push({ promise, resolve })
return promise
}
if (args[0] === 'rev-parse') {
return Promise.resolve({ stdout: 'origin/main\n' })
}
if (args[0] === 'rev-list') {
return Promise.resolve({ stdout: '0\t0\n' })
}
throw new Error(`unexpected git args: ${args.join(' ')}`)
})
let finishMutation!: () => void
const mutationGate = new Promise<void>((resolve) => {
finishMutation = resolve
})
const before = getUpstreamStatus('/repo')
await vi.waitFor(() => expect(pendingReads).toHaveLength(1))
const mutation = runWithGitReadCacheInvalidation(() => mutationGate)
const during = getUpstreamStatus('/repo')
await vi.waitFor(() => expect(pendingReads).toHaveLength(2))
finishMutation()
await mutation
const after = getUpstreamStatus('/repo')
await vi.waitFor(() => expect(pendingReads).toHaveLength(3))
pendingReads.forEach(({ resolve }) => resolve({ stdout: 'main\n' }))
await Promise.all([before, during, after])
expect(pendingReads).toHaveLength(3)
})
it('returns upstream and ahead/behind counts when tracking is configured', async () => {
+22 -1
View File
@@ -5,11 +5,16 @@ import { getEffectiveGitUpstreamStatus } from '../../shared/git-effective-upstre
import { getPublishTargetStatus } from '../../shared/git-publish-target-status'
import { gitExecFileAsync } from './runner'
import { validateGitPushTarget } from './push-target-validation'
import { nativeAndWslGitUpstreamStatusReadOwner } from './git-upstream-status-read-owner'
type GitExecOptions = {
wslDistro?: string
}
export function invalidateGitUpstreamStatusReads(): void {
nativeAndWslGitUpstreamStatusReadOwner.invalidate()
}
function gitExecOptions(
cwd: string,
options: GitExecOptions = {}
@@ -35,7 +40,7 @@ async function getBehindCommitsArePatchEquivalent(
}
}
export async function getUpstreamStatus(
async function readUpstreamStatus(
worktreePath: string,
pushTarget?: GitPushTarget,
options: GitExecOptions = {}
@@ -71,3 +76,19 @@ export async function getUpstreamStatus(
throw new Error(normalizeGitErrorMessage(error, 'upstream'))
}
}
export function getUpstreamStatus(
worktreePath: string,
pushTarget?: GitPushTarget,
options: GitExecOptions = {}
): Promise<GitUpstreamStatus> {
const executionIdentity = options.wslDistro
? ({ kind: 'wsl', distro: options.wslDistro } as const)
: ({ kind: 'native' } as const)
return nativeAndWslGitUpstreamStatusReadOwner.read(
executionIdentity,
worktreePath,
pushTarget,
() => readUpstreamStatus(worktreePath, pushTarget, options)
)
}
+155
View File
@@ -1002,6 +1002,125 @@ describe('SshGitProvider', () => {
expect(result).toEqual(upstreamResult)
})
it('benchmarks concurrent upstream-status RPC pressure', async () => {
const benchPath = process.env.ORCA_SSH_GIT_UPSTREAM_COALESCING_BENCH_JSON
if (!benchPath) {
return
}
mux.request.mockResolvedValue({
hasUpstream: true,
upstreamName: 'origin/main',
ahead: 1,
behind: 0
})
await Promise.all(
Array.from({ length: 10 }, () => provider.getUpstreamStatus('/home/user/repo'))
)
const upstreamRequests = mux.request.mock.calls.filter(
([method]) => method === 'git.upstreamStatus'
)
const { mkdirSync, writeFileSync } = await vi.importActual<typeof NodeFs>('node:fs')
mkdirSync(path.dirname(benchPath), { recursive: true })
writeFileSync(
benchPath,
JSON.stringify({
scenario: 'ssh-git-upstream-concurrent-burst',
concurrentCalls: 10,
upstreamStatusRequests: upstreamRequests.length,
method: 'git.upstreamStatus',
payload: { worktreePath: '/home/user/repo' }
})
)
})
it('shares one upstream-status RPC across ten identical callers', async () => {
const pending = deferredPromise<{
hasUpstream: true
upstreamName: string
ahead: number
behind: number
}>()
mux.request.mockReturnValue(pending.promise)
const reads = Array.from({ length: 10 }, () => provider.getUpstreamStatus('/home/user/repo'))
await waitForRequestCount(mux.request, 1)
expect(mux.request).toHaveBeenCalledTimes(1)
pending.resolve({ hasUpstream: true, upstreamName: 'origin/main', ahead: 1, behind: 0 })
await expect(Promise.all(reads)).resolves.toHaveLength(10)
})
it('isolates upstream-status RPCs by worktree and every target field', async () => {
mux.request.mockResolvedValue({
hasUpstream: true,
upstreamName: 'fork/feature',
ahead: 0,
behind: 0
})
const baseTarget = { remoteName: 'fork', branchName: 'feature' }
await Promise.all([
provider.getUpstreamStatus('/repo-a'),
provider.getUpstreamStatus('/repo-b'),
provider.getUpstreamStatus('/repo-a', baseTarget),
provider.getUpstreamStatus('/repo-a', { ...baseTarget, remoteName: 'origin' }),
provider.getUpstreamStatus('/repo-a', { ...baseTarget, branchName: 'other' }),
provider.getUpstreamStatus('/repo-a', {
...baseTarget,
remoteUrl: 'https://github.com/example/fork.git'
}),
provider.getUpstreamStatus('/repo-a', { ...baseTarget, remoteCreated: false }),
provider.getUpstreamStatus('/repo-a', { ...baseTarget, remoteCreated: true })
])
expect(mux.request).toHaveBeenCalledTimes(8)
})
it('keeps upstream-status reads isolated per provider instance', async () => {
const otherProvider = new SshGitProvider('conn-1', mux as never)
mux.request.mockResolvedValue({
hasUpstream: true,
upstreamName: 'origin/main',
ahead: 0,
behind: 0
})
await Promise.all([
provider.getUpstreamStatus('/home/user/repo'),
otherProvider.getUpstreamStatus('/home/user/repo')
])
expect(mux.request).toHaveBeenCalledTimes(2)
})
it('runs a fresh upstream-status RPC after result and error settlement', async () => {
const failure = new Error('upstream RPC failed')
mux.request
.mockResolvedValueOnce({
hasUpstream: true,
upstreamName: 'origin/main',
ahead: 0,
behind: 0
})
.mockRejectedValueOnce(failure)
.mockResolvedValueOnce({
hasUpstream: false,
ahead: 0,
behind: 0
})
await expect(provider.getUpstreamStatus('/home/user/repo')).resolves.toMatchObject({
hasUpstream: true
})
await expect(provider.getUpstreamStatus('/home/user/repo')).rejects.toBe(failure)
await expect(provider.getUpstreamStatus('/home/user/repo')).resolves.toMatchObject({
hasUpstream: false
})
expect(mux.request).toHaveBeenCalledTimes(3)
})
it('getUpstreamStatus forwards an explicit push target', async () => {
const upstreamResult = { hasUpstream: true, upstreamName: 'fork/feature', ahead: 0, behind: 1 }
mux.request.mockResolvedValue(upstreamResult)
@@ -1432,6 +1551,42 @@ describe('SshGitProvider', () => {
expect(mux.request.mock.calls.filter(([method]) => method === 'git.status')).toHaveLength(3)
})
it('fences upstream-status reads before, during, and after an SSH mutation', async () => {
const upstreamRequests = Array.from({ length: 3 }, () =>
deferredPromise<{ hasUpstream: false; ahead: 0; behind: 0 }>()
)
const mutation = deferredPromise<void>()
let upstreamRequestIndex = 0
mux.request.mockImplementation((method) => {
if (method === 'git.upstreamStatus') {
return upstreamRequests[upstreamRequestIndex++]?.promise
}
if (method === 'git.stage') {
return mutation.promise
}
return Promise.resolve(undefined)
})
const beforeMutation = provider.getUpstreamStatus('/home/user/repo')
await waitForRequestCount(mux.request, 1)
const mutating = provider.stageFile('/home/user/repo', 'src/file.ts')
await waitForRequestCount(mux.request, 2)
const duringMutation = provider.getUpstreamStatus('/home/user/repo')
await waitForRequestCount(mux.request, 3)
mutation.resolve(undefined)
await mutating
const afterMutation = provider.getUpstreamStatus('/home/user/repo')
await waitForRequestCount(mux.request, 4)
upstreamRequests.forEach((pending) =>
pending.resolve({ hasUpstream: false, ahead: 0, behind: 0 })
)
await Promise.all([beforeMutation, duringMutation, afterMutation])
expect(
mux.request.mock.calls.filter(([method]) => method === 'git.upstreamStatus')
).toHaveLength(3)
})
it.each([
[
'clone',
+12 -3
View File
@@ -33,6 +33,7 @@ import {
import { InFlightPromiseDedupe, stableInFlightKey } from '../../shared/in-flight-promise-dedupe'
import { gitExecMutatesRepository } from '../../shared/git-exec-mutation'
import { GitStatusReadLeaseOwner } from '../git/git-status-read-lease-owner'
import { GitUpstreamStatusReadOwner } from '../git/git-upstream-status-read-owner'
type NonInteractiveExecQueueEntry = {
started: boolean
@@ -85,6 +86,7 @@ function filterUntrackedPorcelainStatus(stdout: string | undefined): string | un
export class SshGitProvider implements IGitProvider {
private readonly gitDiffReadDedupe = new InFlightPromiseDedupe<GitDiffResult | GitDiffResult[]>()
private readonly statusReadLeaseOwner = new GitStatusReadLeaseOwner<GitStatusResult>()
private readonly upstreamStatusReadOwner = new GitUpstreamStatusReadOwner()
private connectionId: string
private mux: SshChannelMultiplexer
@@ -102,6 +104,7 @@ export class SshGitProvider implements IGitProvider {
private invalidateGitReads(): void {
this.gitDiffReadDedupe.clear()
this.statusReadLeaseOwner.invalidate()
this.upstreamStatusReadOwner.invalidate()
}
private loggedWorktreeIsCleanFallback = false
@@ -507,10 +510,16 @@ export class SshGitProvider implements IGitProvider {
worktreePath: string,
pushTarget?: GitPushTarget
): Promise<GitUpstreamStatus> {
return (await this.mux.request('git.upstreamStatus', {
return this.upstreamStatusReadOwner.read(
{ kind: 'ssh-provider' },
worktreePath,
...(pushTarget ? { pushTarget } : {})
})) as GitUpstreamStatus
pushTarget,
async () =>
(await this.mux.request('git.upstreamStatus', {
worktreePath,
...(pushTarget ? { pushTarget } : {})
})) as GitUpstreamStatus
)
}
async pushBranch(
@@ -0,0 +1,145 @@
# Phase 2 Git upstream-status in-flight sharing — 2026-07-30
## Decision
Retain in-flight-only upstream-status sharing at both physical owners. Ten concurrent identical
local callers now share one four-command Git chain, and ten concurrent identical SSH callers share
one `git.upstreamStatus` RPC. No settled result, rejected result, Git command, RPC method, payload,
or max-lines policy changed.
Checkpoint: `6fee674c48a6dc5742156f70e1fa1363a760f6c6`.
## Ownership and identity
`GitUpstreamStatusReadOwner` is the concrete bounded joinability owner. The native/WSL path uses
one module-owned instance, keyed by:
- native versus the exact WSL distro;
- worktree path;
- configured-upstream versus explicit-target mode; and
- explicit target `remoteName`, `branchName`, `remoteUrl`, and `remoteCreated`, preserving absent
versus explicit `false`.
Each `SshGitProvider` owns a separate instance, keyed by worktree path and the same complete target
identity. Provider replacement or reconnect therefore cannot reuse another connection
incarnation's work. The shared primitive removes successful and failed entries after settlement
and bounds joinability to 128 entries and 30 seconds; it does not retain a status result.
The existing local `runWithGitReadCacheInvalidation` and SSH `runWithGitReadInvalidation` wrappers
invalidate upstream joinability before and after every existing Git mutation. Already-issued
promises remain valid, while reads admitted before, during, and after a mutation use separate
generations.
## A/B physical-call measurement
The opt-in deterministic benchmarks call the actual local and SSH provider entry points with ten
concurrent identical callers. Counts are taken at the mocked physical `gitExecFileAsync` and mux
request boundaries.
| Arm | Local physical Git calls | SSH `git.upstreamStatus` RPCs |
| -------------------- | -----------------------: | ----------------------------: |
| A — checkpoint | 40 | 10 |
| B — retained sharing | 4 | 1 |
| Change | -36 | -9 |
The local command histogram changes from ten of each command to one of each. The command vectors
and execution options are otherwise byte-for-byte equivalent:
```json
[
{
"args": ["symbolic-ref", "--quiet", "--short", "HEAD"],
"options": { "cwd": "/repo" }
},
{
"args": ["rev-parse", "--abbrev-ref", "HEAD@{u}"],
"options": { "cwd": "/repo" }
},
{
"args": ["rev-list", "--left-right", "--count", "HEAD...origin/main"],
"options": { "cwd": "/repo" }
},
{
"args": ["log", "--oneline", "--cherry-mark", "--right-only", "HEAD...origin/main", "--"],
"options": { "cwd": "/repo" }
}
]
```
The SSH request remains exactly:
```json
{
"method": "git.upstreamStatus",
"payload": { "worktreePath": "/home/user/repo" }
}
```
When an explicit target exists, the existing `pushTarget` property is still present with the
unchanged object; when absent, the property remains omitted. Existing configured-upstream and
explicit-target tests continue to cover validation, remote tracking probes, URL/created metadata,
ahead/behind counts, patch equivalence, normalized errors, and no-upstream semantics.
Baseline JSON was archived at `/tmp/git-upstream-inflight-a.json` and
`/tmp/ssh-git-upstream-inflight-a.json`; retained JSON is at
`/tmp/git-upstream-inflight-b.json` and `/tmp/ssh-git-upstream-inflight-b.json`.
## Production A/B artifacts
Fresh production builds were archived outside the worktree:
- A: `/tmp/orca-phase2-git-upstream-a.vQcXwZ/out`
- B: `/tmp/orca-phase2-git-upstream-b-final.OVLh7P/out`
| Artifact | A raw / gzip | B raw / gzip | Change | A SHA-256 | B SHA-256 |
| ---------------------- | ----------------- | ----------------- | ----------- | ------------------------------------------------------------------ | ------------------------------------------------------------------ |
| Electron main entry | 778,457 / 174,582 | 779,267 / 174,769 | +810 / +187 | `c5992b64d59edfb9719ea2e19b2872f923253686615e53e356aeac6d3139e632` | `64526204d377f8ca634de5940d77b3f2eff1421bd7a8e7346b0ffcc189be21da` |
| Electron preload entry | 130,798 / 20,642 | 130,798 / 20,642 | 0 / 0 | `c388a39cdca9609760e286d95b87ad1e53793720450e507f830ff1f6c5bd259f` | `c388a39cdca9609760e286d95b87ad1e53793720450e507f830ff1f6c5bd259f` |
The Electron-main raw budget remains 825,109 bytes; B retains 45,842 bytes of headroom. Main,
preload, and renderer file counts remain 184, 1, and 787 respectively. Preload and all renderer
artifacts are byte-identical; the renderer manifest remains byte-identical with SHA-256
`92ad617f8c8aee6d4c4a23622f524266cbe9c93b3fe65544d1acb833dc3f0d67`.
Renderer entry measurements are unchanged:
| Entry | Raw bytes | Gzip bytes | JS | CSS |
| --------------- | --------: | ---------: | --: | --: |
| Renderer index | 8,416,540 | 1,877,823 | 292 | 2 |
| Renderer popout | 4,507,253 | 984,615 | 77 | 2 |
| Renderer web | 4,360,652 | 928,355 | 33 | 1 |
Complete A and B manifest validation found 778 records, three HTML entries, 6,247 static edges,
213 dynamic edges, and 860 emitted artifact references, with zero missing or escaping paths, zero
cross-entry imports, and zero cycles.
An initial non-retained wiring arm imported the full upstream implementation into the eager status
module and cost +6,686 main-entry raw bytes. Moving the common fence onto the named owner singleton
reduced the retained cost to +810 bytes without changing invalidation behavior.
## Validation
- Baseline provider/upstream suite: 112 passed.
- Focused owner/upstream/provider suite: 124 passed.
- Final owner/upstream/status/provider suite: 215 passed.
- Broad dedupe, upstream, remote, native/WSL status, SSH provider/dispatch, filesystem mutation,
and runtime-routing suite: 465 passed, 1 skipped.
- `pnpm run typecheck:node`: passed.
- Targeted `oxlint --deny-warnings`: passed.
- Targeted `oxfmt --check`: passed.
- `pnpm run check:max-lines-ratchet`: passed with 354 grandfathered suppressions and no new bypass.
- Fresh A and B `pnpm run build:electron-vite`: passed.
- `pnpm run check:electron-bundle-budgets`: passed against fresh B.
- Complete renderer manifest resolution and entry-cycle validation: passed for A and B.
- `git diff --check`: passed.
## Limitations and residual risk
- Physical call counts use deterministic mocked Git and mux boundaries. They prove admission,
exact commands, options, method, and payload, not live process startup or SSH latency.
- After the bounded primitive's 30-second joinability window, a still-hung read may be joined by no
new callers and a fresh call may start. Existing callers remain attached to their original work.
- This tranche does not add caller cancellation to the upstream-status API and does not broaden
into a repository snapshot service.
- No packaged live smoke was run across macOS, Linux, Windows, WSL, or SSH hosts. Existing routing,
folder-workspace, relay, and Git 2.25-compatible command suites cover the unchanged boundaries.