diff --git a/gitnexus/src/cli/analyze.ts b/gitnexus/src/cli/analyze.ts index c77903de0..79f60b3fc 100644 --- a/gitnexus/src/cli/analyze.ts +++ b/gitnexus/src/cli/analyze.ts @@ -290,5 +290,7 @@ export const analyzeCommand = async (inputPath?: string, options?: AnalyzeOption // LadybugDB's native module holds open handles that prevent Node from exiting. // ONNX Runtime also registers native atexit hooks that segfault on some // platforms (#38, #40). Force-exit to ensure clean termination. + // The ONNX session is disposed in runFullAnalysis after embeddings complete + // to prevent C++ atexit destructors from racing with closed DB handles. process.exit(0); }; diff --git a/gitnexus/src/core/run-analyze.ts b/gitnexus/src/core/run-analyze.ts index e8a108c71..5d2684ec2 100644 --- a/gitnexus/src/core/run-analyze.ts +++ b/gitnexus/src/core/run-analyze.ts @@ -265,6 +265,15 @@ export async function runFullAnalysis( {}, cachedEmbeddingNodeIds.size > 0 ? cachedEmbeddingNodeIds : undefined, ); + + // Release ONNX Runtime session to prevent its C++ atexit handlers from + // racing with LadybugDB cleanup during process.exit() (#38, #40). + try { + const { disposeEmbedder } = await import('./embeddings/embedder.js'); + await disposeEmbedder(); + } catch { + /* best-effort */ + } } // ── Phase 5: Finalize (98–100%) ───────────────────────────────────