abhigyanpatwari/GitNexus · warning
Repository analysis for "${entry.repoName}" is taking longer
Error message
Repository analysis for "${entry.repoName}" is taking longer than expected. Please try again in a moment. What it means
HTTP 503 from GET /api/repo when resolveRepo located an active analysis job for the repository but timed out waiting for it to finish — the returned entry is flagged __timedOut and the handler converts that into this retryable 503 with the repo name in the message. It is a transient state: the analysis is still running server-side, so the correct client behavior is to wait and retry rather than treat the repo as missing.
Source
Thrown at gitnexus/src/server/api.ts:1030
res.status(500).json({ error: err.message || 'Failed to list repos' });
}
});
// Get repo info
// Rate-limited (CodeQL js/missing-rate-limiting): resolveRepo canonicalizes
// the attacker-supplied ?repo= param (realpathSync probe for absolute /
// Windows-shaped claims). Default 60 rpm/IP — web callers hit this route
// only on connect/switch, never in a polling loop.
app.get('/api/repo', createRouteLimiter(), async (req, res) => {
try {
const entry = await resolveRepo(requestedRepo(req), false, req);
if (!entry) {
res.status(404).json({ error: 'Repository not found. Run: gitnexus analyze' });
return;
}
// Timed out waiting for an active analysis job
if (entry.__timedOut) {
res.status(503).json({
error: `Repository analysis for "${entry.repoName}" is taking longer than expected. Please try again in a moment.`,
});
return;
}
const meta = await loadMeta(entry.storagePath);
res.json({
name: entry.name,
repoPath: entry.path,
indexedAt: meta?.indexedAt ?? entry.indexedAt,
stats: meta?.stats ?? entry.stats ?? {},
});
} catch (err: any) {
res.status(500).json({ error: err.message || 'Failed to get repo info' });
}
});
// Delete a repo — removes index, clone dir (if any), and unregisters it
// Rate-limited (CodeQL js/missing-rate-limiting): destructive operationView on GitHub (pinned to 0d1aed942f)
Solutions
- Retry GET /api/repo after a short delay (a few seconds), with backoff — the 503 resolves itself when analysis completes
- If you have a job id (upload flow), poll the job status endpoint and only hit /api/repo once it reports done
- For first-serve UX, run gitnexus analyze to completion before pointing clients at the server
- Do not re-trigger analyze on this 503 — that can queue behind or conflict with the running job
Example fix
// before
const res = await fetch(`${base}/api/repo?repo=${name}`);
if (!res.ok) throw new Error('repo failed'); // hard-fails during analysis
// after
async function waitForRepo(name: string, tries = 20) {
for (let i = 0; i < tries; i++) {
const res = await fetch(`${base}/api/repo?repo=${encodeURIComponent(name)}`);
if (res.ok) return res.json();
if (res.status !== 503) throw new Error(`repo failed: ${res.status}`);
await new Promise((r) => setTimeout(r, 3000 + i * 1000)); // analysis still running
}
throw new Error('repo analysis did not finish in time');
} Defensive patterns
Strategy: retry
Try / catch
async function fetchRepoWithRetry(name: string, tries = 20) {
for (let i = 0; i < tries; i++) {
const res = await fetch(`${base}/api/repo?repo=${encodeURIComponent(name)}`);
if (res.ok) return res.json();
const { error } = await res.json().catch(() => ({ error: '' }));
if (res.status === 503 && /taking longer than expected/.test(error)) {
await new Promise((r) => setTimeout(r, 3000 + i * 2000)); // analysis still running — back off
continue;
}
throw new Error(`repo fetch failed: HTTP ${res.status} ${error}`);
}
throw new Error('analysis still running after retry budget');
} Prevention
- Never hard-fail a connect flow on this 503 — poll with backoff instead
- Pre-warm big repos by running analyze to completion before demos or CI queries
- Do not re-trigger analyze in response to this 503 — a job is already running
- Show a progress state keyed off the job endpoint when you have a jobId
When it happens
Trigger: Polling /api/repo while a large repository is mid-analysis (or a fresh upload analysis is queued); the single analysis slot is occupied by a long job and resolution waited to the end of its budget; machines under load where indexing runs slowly.
Common situations: Web UI connect/switch screen racing the initial analyze of a monorepo; CI pipelines that start serve and immediately query metadata; very large codebases whose first index takes minutes; retry storms right after upload.
Related errors
- Embedding endpoint returned an unparseable response (${safeU
- ${source} must be a string.
- "path" must be a string
- Provide "url" (git URL) or "path" (local path)
- Worker ${workerIndex} parse job idle timeout (single item).
AI-assisted analysis of abhigyanpatwari/GitNexus@0d1aed942f (2026-08-20).
Data as JSON: /api/errors/8b533fbdfb4ef8a9.
Report an issue: GitHub.