MCPcopy
hub / github.com/codeaashu/claude-code / createAndUploadGitBundle

Function createAndUploadGitBundle

src/utils/teleport/gitBundle.ts:152–292  ·  view source on GitHub ↗
(
  config: FilesApiConfig,
  opts?: { cwd?: string; signal?: AbortSignal },
)

Source from the content-addressed store, hash-verified

150// Tracked WIP via stash create → refs/seed/stash (or baked into the
151// squashed tree); untracked not captured.
152export async function createAndUploadGitBundle(
153 config: FilesApiConfig,
154 opts?: { cwd?: string; signal?: AbortSignal },
155): Promise<BundleUploadResult> {
156 const workdir = opts?.cwd ?? getCwd()
157 const gitRoot = findGitRoot(workdir)
158 if (!gitRoot) {
159 return { success: false, error: 'Not in a git repository' }
160 }
161
162 // Sweep stale refs from a crashed prior run before --all bundles them.
163 // Runs before the empty-repo check so it's never skipped by an early return.
164 for (const ref of ['refs/seed/stash', 'refs/seed/root']) {
165 await execFileNoThrowWithCwd(gitExe(), ['update-ref', '-d', ref], {
166 cwd: gitRoot,
167 })
168 }
169
170 // `git bundle create` refuses to create an empty bundle (exit 128), and
171 // `stash create` fails with "You do not have the initial commit yet".
172 // Check for any refs (not just HEAD) so orphan branches with commits
173 // elsewhere still bundle — `--all` packs those refs regardless of HEAD.
174 const refCheck = await execFileNoThrowWithCwd(
175 gitExe(),
176 ['for-each-ref', '--count=1', 'refs/'],
177 { cwd: gitRoot },
178 )
179 if (refCheck.code === 0 && refCheck.stdout.trim() === '') {
180 logEvent('tengu_ccr_bundle_upload', {
181 outcome:
182 'empty_repo' as AnalyticsMetadata_I_VERIFIED_THIS_IS_NOT_CODE_OR_FILEPATHS,
183 })
184 return {
185 success: false,
186 error: 'Repository has no commits yet',
187 failReason: 'empty_repo',
188 }
189 }
190
191 // stash create writes a dangling commit — doesn't touch refs/stash or
192 // the working tree. Untracked files intentionally excluded.
193 const stashResult = await execFileNoThrowWithCwd(
194 gitExe(),
195 ['stash', 'create'],
196 { cwd: gitRoot, abortSignal: opts?.signal },
197 )
198 // exit 0 + empty stdout = nothing to stash. Nonzero is rare; non-fatal.
199 const wipStashSha = stashResult.code === 0 ? stashResult.stdout.trim() : ''
200 const hasWip = wipStashSha !== ''
201 if (stashResult.code !== 0) {
202 logForDebugging(
203 `[gitBundle] git stash create failed (${stashResult.code}), proceeding without WIP: ${stashResult.stderr.slice(0, 200)}`,
204 )
205 } else if (hasWip) {
206 logForDebugging(`[gitBundle] Captured WIP as stash ${wipStashSha}`)
207 // env-runner reads the SHA via bundle list-heads refs/seed/stash.
208 await execFileNoThrowWithCwd(
209 gitExe(),

Callers 1

teleportToRemoteFunction · 0.85

Calls 9

getCwdFunction · 0.85
execFileNoThrowWithCwdFunction · 0.85
logEventFunction · 0.85
logForDebuggingFunction · 0.85
generateTempFilePathFunction · 0.85
_bundleWithFallbackFunction · 0.85
uploadFileFunction · 0.85
unlinkFunction · 0.85

Tested by

no test coverage detected