{"record":{"id":"5f90c62b497a4827","repo":"abhigyanpatwari/GitNexus","slug":"ladybugdb-checkpoint-sidecar-is-missing-for-dbpa","errorCode":null,"errorMessage":"LadybugDB checkpoint sidecar is missing for ${dbPath}. Rebuild the index with `gitnexus analyze --force <repo-path> --index-only` and restart `gitnexus serve`.\n  Original error: ${msg.slice(0, 200)}","messagePattern":"LadybugDB checkpoint sidecar is missing for (.+?)\\. Rebuild the index with `gitnexus analyze --force <repo-path> --index-only` and restart `gitnexus serve`\\.\n  Original error: (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"gitnexus/src/core/lbug/lbug-adapter.ts","lineNumber":581,"sourceCode":"  await refuseLargeWalQuarantine(dbPath, 'read-only', err);\n  try {\n    await quarantineWalForMissingShadow(dbPath, {\n      logger,\n      level: 'warn',\n      reason: 'read-only recovery',\n    });\n  } catch (renameErr) {\n    throw new Error(renameFailureMessage(dbPath, renameErr));\n  }\n\n  const reopened = await openLbugConnection(lbug, dbPath, { readOnly: true });\n  try {\n    await queryAndDrain(reopened.conn, READ_ONLY_SHADOW_REPLAY_PROBE);\n    return reopened;\n  } catch (retryErr) {\n    await closeLbugConnection(reopened);\n    if (isMissingShadowSidecarError(retryErr) || isReadOnlyShadowReplayError(retryErr)) {\n      throw new Error(shadowSidecarRecoveryMessage(dbPath, retryErr));\n    }\n    throw retryErr;\n  }\n};\n\nconst writableFtsCrashWalEvidence = async (\n  dbPath: string,\n): Promise<WalCrashEvidence | undefined> => {\n  try {\n    const meta = await loadMeta(path.dirname(dbPath));\n    if (\n      meta &&\n      (allowsFtsCrashWalPark(meta.incrementalInProgress) ||\n        hasRecoveredInPlaceFtsAbort(meta.capabilities?.fts))\n    ) {\n      return { kind: 'fts-inplace-checkpointed' };\n    }\n  } catch {","sourceCodeStart":563,"sourceCodeEnd":599,"githubUrl":"https://github.com/abhigyanpatwari/GitNexus/blob/ac9a4e9abd8fd3058c070b72c23402a4f887929a/gitnexus/src/core/lbug/lbug-adapter.ts#L563-L599","documentation":"shadowSidecarRecoveryMessage from lbug-adapter.ts (read-only path, line 585): when a database is opened read-only, a probe query replays against the shadow/checkpoint sidecar; if the sidecar is missing, GitNexus quarantines the WAL, reopens read-only, and retries the probe. When the retry still fails with a missing-shadow or shadow-replay error, recovery is impossible without rebuilding and the error directs the operator to re-run analyze with --force --index-only.","triggerScenarios":"A previous run was interrupted between WAL checkpoint steps (kill, power loss, disk-full) leaving the checkpoint sidecar absent; someone copied or restored only the main database file without its sidecars; then serve/MCP/query tries to open the index read-only.","commonSituations":"CI runners killed mid-analyze; disk-full during checkpoint; partial backups or rsync of the storage dir that skipped sidecar files; storage cleanup scripts deleting 'unknown' files.","solutions":["Run `gitnexus analyze --force <repo-path> --index-only` to rebuild the index from the repo, then restart `gitnexus serve`","If the error recurs, remove the stale database files under the storage dir entirely and run a full `gitnexus analyze --force <repo-path>`","When copying or backing up indexes, always copy the whole storage dir including all sidecar files, never just the main db file"],"exampleFix":"# before\n$ gitnexus serve   # fails: checkpoint sidecar missing\n# after\n$ gitnexus analyze --force /path/to/repo --index-only\ngitnexus serve","handlingStrategy":"retry","validationCode":null,"typeGuard":null,"tryCatchPattern":"try {\n  await startServe(repoPath);\n} catch (err) {\n  if (err instanceof Error && err.message.includes('checkpoint sidecar is missing')) {\n    // recovery path: exec `gitnexus analyze --force <repo> --index-only`, then restart serve on success\n    await rebuildIndex(repoPath);\n    return startServe(repoPath);\n  }\n  throw err;\n}","preventionTips":["Never copy or restore just the database file — move the whole storage dir including sidecars","Treat interrupted (killed/OOM) analyze runs as suspect: verify serve starts or proactively re-run analyze --force","Keep backup/sync tools from pruning unknown sidecar files in the storage directory"],"tags":["wal","ladybugdb","checkpoint","index-corruption","recovery","serve"],"backgroundTag":"database-recovery-required","analyzedSha":"ac9a4e9abd8fd3058c070b72c23402a4f887929a","analyzedAt":"2026-08-20T23:29:22.980Z","contentChangedAt":"2026-08-20T23:29:22.980Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}