agentic-qe 3.6.19 → 3.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (118) hide show
  1. package/.claude/skills/skills-manifest.json +1 -1
  2. package/README.md +29 -1
  3. package/package.json +2 -1
  4. package/scripts/rvf-baseline-benchmark.ts +843 -0
  5. package/v3/CHANGELOG.md +30 -0
  6. package/v3/dist/audit/witness-chain.d.ts +148 -0
  7. package/v3/dist/audit/witness-chain.d.ts.map +1 -0
  8. package/v3/dist/audit/witness-chain.js +269 -0
  9. package/v3/dist/audit/witness-chain.js.map +1 -0
  10. package/v3/dist/cli/brain-commands.d.ts +39 -0
  11. package/v3/dist/cli/brain-commands.d.ts.map +1 -0
  12. package/v3/dist/cli/brain-commands.js +60 -0
  13. package/v3/dist/cli/brain-commands.js.map +1 -0
  14. package/v3/dist/cli/bundle.js +4509 -2452
  15. package/v3/dist/cli/command-registry.d.ts.map +1 -1
  16. package/v3/dist/cli/command-registry.js +3 -1
  17. package/v3/dist/cli/command-registry.js.map +1 -1
  18. package/v3/dist/cli/handlers/brain-handler.d.ts +22 -0
  19. package/v3/dist/cli/handlers/brain-handler.d.ts.map +1 -0
  20. package/v3/dist/cli/handlers/brain-handler.js +148 -0
  21. package/v3/dist/cli/handlers/brain-handler.js.map +1 -0
  22. package/v3/dist/cli/handlers/index.d.ts +1 -0
  23. package/v3/dist/cli/handlers/index.d.ts.map +1 -1
  24. package/v3/dist/cli/handlers/index.js +1 -0
  25. package/v3/dist/cli/handlers/index.js.map +1 -1
  26. package/v3/dist/domains/coverage-analysis/services/hnsw-index.d.ts +31 -44
  27. package/v3/dist/domains/coverage-analysis/services/hnsw-index.d.ts.map +1 -1
  28. package/v3/dist/domains/coverage-analysis/services/hnsw-index.js +73 -178
  29. package/v3/dist/domains/coverage-analysis/services/hnsw-index.js.map +1 -1
  30. package/v3/dist/domains/quality-assessment/coordinator.d.ts.map +1 -1
  31. package/v3/dist/domains/quality-assessment/coordinator.js +8 -0
  32. package/v3/dist/domains/quality-assessment/coordinator.js.map +1 -1
  33. package/v3/dist/domains/test-execution/coordinator.d.ts +14 -0
  34. package/v3/dist/domains/test-execution/coordinator.d.ts.map +1 -1
  35. package/v3/dist/domains/test-execution/coordinator.js +18 -0
  36. package/v3/dist/domains/test-execution/coordinator.js.map +1 -1
  37. package/v3/dist/domains/test-execution/services/index.d.ts +1 -0
  38. package/v3/dist/domains/test-execution/services/index.d.ts.map +1 -1
  39. package/v3/dist/domains/test-execution/services/index.js +1 -0
  40. package/v3/dist/domains/test-execution/services/index.js.map +1 -1
  41. package/v3/dist/domains/test-execution/services/mincut-test-optimizer.d.ts +118 -0
  42. package/v3/dist/domains/test-execution/services/mincut-test-optimizer.d.ts.map +1 -0
  43. package/v3/dist/domains/test-execution/services/mincut-test-optimizer.js +358 -0
  44. package/v3/dist/domains/test-execution/services/mincut-test-optimizer.js.map +1 -0
  45. package/v3/dist/integrations/ruvector/brain-exporter.d.ts +66 -0
  46. package/v3/dist/integrations/ruvector/brain-exporter.d.ts.map +1 -0
  47. package/v3/dist/integrations/ruvector/brain-exporter.js +537 -0
  48. package/v3/dist/integrations/ruvector/brain-exporter.js.map +1 -0
  49. package/v3/dist/integrations/ruvector/index.d.ts +4 -0
  50. package/v3/dist/integrations/ruvector/index.d.ts.map +1 -1
  51. package/v3/dist/integrations/ruvector/index.js +5 -0
  52. package/v3/dist/integrations/ruvector/index.js.map +1 -1
  53. package/v3/dist/integrations/ruvector/mincut-wrapper.d.ts +204 -0
  54. package/v3/dist/integrations/ruvector/mincut-wrapper.d.ts.map +1 -0
  55. package/v3/dist/integrations/ruvector/mincut-wrapper.js +310 -0
  56. package/v3/dist/integrations/ruvector/mincut-wrapper.js.map +1 -0
  57. package/v3/dist/integrations/ruvector/rvf-dual-writer.d.ts +141 -0
  58. package/v3/dist/integrations/ruvector/rvf-dual-writer.d.ts.map +1 -0
  59. package/v3/dist/integrations/ruvector/rvf-dual-writer.js +367 -0
  60. package/v3/dist/integrations/ruvector/rvf-dual-writer.js.map +1 -0
  61. package/v3/dist/integrations/ruvector/rvf-native-adapter.d.ts +60 -0
  62. package/v3/dist/integrations/ruvector/rvf-native-adapter.d.ts.map +1 -0
  63. package/v3/dist/integrations/ruvector/rvf-native-adapter.js +240 -0
  64. package/v3/dist/integrations/ruvector/rvf-native-adapter.js.map +1 -0
  65. package/v3/dist/kernel/hnsw-adapter.d.ts +99 -0
  66. package/v3/dist/kernel/hnsw-adapter.d.ts.map +1 -0
  67. package/v3/dist/kernel/hnsw-adapter.js +218 -0
  68. package/v3/dist/kernel/hnsw-adapter.js.map +1 -0
  69. package/v3/dist/kernel/hnsw-index-provider.d.ts +90 -0
  70. package/v3/dist/kernel/hnsw-index-provider.d.ts.map +1 -0
  71. package/v3/dist/kernel/hnsw-index-provider.js +23 -0
  72. package/v3/dist/kernel/hnsw-index-provider.js.map +1 -0
  73. package/v3/dist/kernel/progressive-hnsw-backend.d.ts +67 -0
  74. package/v3/dist/kernel/progressive-hnsw-backend.d.ts.map +1 -0
  75. package/v3/dist/kernel/progressive-hnsw-backend.js +266 -0
  76. package/v3/dist/kernel/progressive-hnsw-backend.js.map +1 -0
  77. package/v3/dist/kernel/unified-memory-hnsw.d.ts +71 -0
  78. package/v3/dist/kernel/unified-memory-hnsw.d.ts.map +1 -1
  79. package/v3/dist/kernel/unified-memory-hnsw.js +87 -0
  80. package/v3/dist/kernel/unified-memory-hnsw.js.map +1 -1
  81. package/v3/dist/kernel/unified-memory-schemas.d.ts +1 -0
  82. package/v3/dist/kernel/unified-memory-schemas.d.ts.map +1 -1
  83. package/v3/dist/kernel/unified-memory-schemas.js +16 -0
  84. package/v3/dist/kernel/unified-memory-schemas.js.map +1 -1
  85. package/v3/dist/learning/dream/dream-engine.d.ts +16 -0
  86. package/v3/dist/learning/dream/dream-engine.d.ts.map +1 -1
  87. package/v3/dist/learning/dream/dream-engine.js +70 -0
  88. package/v3/dist/learning/dream/dream-engine.js.map +1 -1
  89. package/v3/dist/learning/dream/index.d.ts +2 -0
  90. package/v3/dist/learning/dream/index.d.ts.map +1 -1
  91. package/v3/dist/learning/dream/index.js +8 -0
  92. package/v3/dist/learning/dream/index.js.map +1 -1
  93. package/v3/dist/learning/dream/rvcow-branch-manager.d.ts +170 -0
  94. package/v3/dist/learning/dream/rvcow-branch-manager.d.ts.map +1 -0
  95. package/v3/dist/learning/dream/rvcow-branch-manager.js +263 -0
  96. package/v3/dist/learning/dream/rvcow-branch-manager.js.map +1 -0
  97. package/v3/dist/learning/dream/speculative-dreamer.d.ts +129 -0
  98. package/v3/dist/learning/dream/speculative-dreamer.d.ts.map +1 -0
  99. package/v3/dist/learning/dream/speculative-dreamer.js +214 -0
  100. package/v3/dist/learning/dream/speculative-dreamer.js.map +1 -0
  101. package/v3/dist/learning/qe-reasoning-bank.d.ts +9 -0
  102. package/v3/dist/learning/qe-reasoning-bank.d.ts.map +1 -1
  103. package/v3/dist/learning/qe-reasoning-bank.js +50 -1
  104. package/v3/dist/learning/qe-reasoning-bank.js.map +1 -1
  105. package/v3/dist/mcp/bundle.js +8900 -7163
  106. package/v3/dist/mcp/services/mincut-routing-service.d.ts +148 -0
  107. package/v3/dist/mcp/services/mincut-routing-service.d.ts.map +1 -0
  108. package/v3/dist/mcp/services/mincut-routing-service.js +198 -0
  109. package/v3/dist/mcp/services/mincut-routing-service.js.map +1 -0
  110. package/v3/dist/mcp/services/task-router.d.ts +4 -0
  111. package/v3/dist/mcp/services/task-router.d.ts.map +1 -1
  112. package/v3/dist/mcp/services/task-router.js +57 -15
  113. package/v3/dist/mcp/services/task-router.js.map +1 -1
  114. package/v3/dist/monitoring/structural-health.d.ts +142 -0
  115. package/v3/dist/monitoring/structural-health.d.ts.map +1 -0
  116. package/v3/dist/monitoring/structural-health.js +201 -0
  117. package/v3/dist/monitoring/structural-health.js.map +1 -0
  118. package/v3/package.json +1 -1
@@ -0,0 +1,367 @@
1
+ /**
2
+ * RVF Dual-Writer Service
3
+ *
4
+ * Phase 3 Task 3.1: Writes learning data to both SQLite (existing) and
5
+ * an RVF container (new native backend). Ensures SQLite writes are never
6
+ * broken by RVF failures, and supports gradual promotion from SQLite-only
7
+ * to dual-write to RVF-primary mode.
8
+ *
9
+ * The dual-writer sits between the QEReasoningBank and the storage layer,
10
+ * intercepting pattern embedding writes/deletes/searches and routing them
11
+ * to one or both backends depending on the configured mode.
12
+ */
13
+ /**
14
+ * Wraps the real RvfNativeAdapter to conform to the simpler RvfStore interface.
15
+ */
16
+ function wrapNativeAdapter(adapter, dim) {
17
+ return {
18
+ ingest(entries) {
19
+ adapter.ingest(entries);
20
+ },
21
+ search(query, k) {
22
+ return adapter.search(query, k).map((r) => ({ id: r.id, score: r.score }));
23
+ },
24
+ delete(ids) {
25
+ adapter.delete(ids);
26
+ },
27
+ status() {
28
+ const s = adapter.status();
29
+ return {
30
+ totalVectors: s.totalVectors,
31
+ dimensions: dim,
32
+ totalSegments: s.totalSegments,
33
+ fileSizeBytes: s.fileSizeBytes,
34
+ epoch: s.epoch,
35
+ witnessValid: s.witnessValid,
36
+ witnessEntries: s.witnessEntries,
37
+ };
38
+ },
39
+ close() {
40
+ adapter.close();
41
+ },
42
+ };
43
+ }
44
+ function tableExists(db, name) {
45
+ const row = db.prepare("SELECT COUNT(*) as cnt FROM sqlite_master WHERE type='table' AND name=?").get(name);
46
+ return (row?.cnt ?? 0) > 0;
47
+ }
48
+ // ============================================================================
49
+ // RvfDualWriter
50
+ // ============================================================================
51
+ export class RvfDualWriter {
52
+ db;
53
+ config;
54
+ rvfStore = null;
55
+ rvfAvailable = false;
56
+ constructor(db, config) {
57
+ this.db = db;
58
+ this.config = {
59
+ ...config,
60
+ dimensions: config.dimensions ?? 384,
61
+ };
62
+ }
63
+ /**
64
+ * Initialize the RVF store (create or open).
65
+ *
66
+ * If the native adapter is not available, the writer degrades gracefully
67
+ * to sqlite-only regardless of the configured mode.
68
+ */
69
+ async initialize() {
70
+ if (this.config.mode === 'sqlite-only') {
71
+ this.rvfAvailable = false;
72
+ return;
73
+ }
74
+ try {
75
+ // Dynamic import so the module is optional
76
+ const adapter = await import('./rvf-native-adapter.js');
77
+ if (!adapter.isRvfNativeAvailable()) {
78
+ this.rvfAvailable = false;
79
+ return;
80
+ }
81
+ // Try open first, create if it fails
82
+ let nativeAdapter;
83
+ try {
84
+ nativeAdapter = adapter.openRvfStore(this.config.rvfPath);
85
+ }
86
+ catch {
87
+ nativeAdapter = adapter.createRvfStore(this.config.rvfPath, this.config.dimensions);
88
+ }
89
+ this.rvfStore = wrapNativeAdapter(nativeAdapter, this.config.dimensions);
90
+ this.rvfAvailable = true;
91
+ }
92
+ catch {
93
+ // Native adapter module not available at all
94
+ this.rvfAvailable = false;
95
+ }
96
+ }
97
+ /**
98
+ * Allow injecting an RVF store directly (useful for testing).
99
+ */
100
+ setRvfStore(store) {
101
+ this.rvfStore = store;
102
+ this.rvfAvailable = true;
103
+ }
104
+ // --------------------------------------------------------------------------
105
+ // Write
106
+ // --------------------------------------------------------------------------
107
+ /**
108
+ * Write a pattern embedding to both stores.
109
+ *
110
+ * SQLite is always written first. RVF failures never propagate to SQLite.
111
+ */
112
+ writePattern(patternId, embedding) {
113
+ const result = {
114
+ sqliteSuccess: false,
115
+ rvfSuccess: false,
116
+ };
117
+ // 1. Always write to SQLite qe_pattern_embeddings
118
+ try {
119
+ this.writeSqliteEmbedding(patternId, embedding);
120
+ result.sqliteSuccess = true;
121
+ }
122
+ catch {
123
+ result.sqliteSuccess = false;
124
+ }
125
+ // 2. Write to RVF if mode requires it and adapter is available
126
+ if (this.shouldWriteRvf()) {
127
+ try {
128
+ this.rvfStore.ingest([{
129
+ id: patternId,
130
+ vector: embedding instanceof Float32Array ? Array.from(embedding) : embedding,
131
+ }]);
132
+ result.rvfSuccess = true;
133
+ }
134
+ catch {
135
+ result.rvfSuccess = false;
136
+ result.divergence = 'rvf-write-failed';
137
+ }
138
+ }
139
+ return result;
140
+ }
141
+ // --------------------------------------------------------------------------
142
+ // Delete
143
+ // --------------------------------------------------------------------------
144
+ /**
145
+ * Delete a pattern embedding from both stores.
146
+ */
147
+ deletePattern(patternId) {
148
+ const result = {
149
+ sqliteSuccess: false,
150
+ rvfSuccess: false,
151
+ };
152
+ // 1. Always delete from SQLite
153
+ try {
154
+ this.deleteSqliteEmbedding(patternId);
155
+ result.sqliteSuccess = true;
156
+ }
157
+ catch {
158
+ result.sqliteSuccess = false;
159
+ }
160
+ // 2. Delete from RVF if applicable
161
+ if (this.shouldWriteRvf()) {
162
+ try {
163
+ this.rvfStore.delete([patternId]);
164
+ result.rvfSuccess = true;
165
+ }
166
+ catch {
167
+ result.rvfSuccess = false;
168
+ result.divergence = 'rvf-delete-failed';
169
+ }
170
+ }
171
+ return result;
172
+ }
173
+ // --------------------------------------------------------------------------
174
+ // Search
175
+ // --------------------------------------------------------------------------
176
+ /**
177
+ * Search for similar vectors. In rvf-primary mode, tries RVF first and
178
+ * falls back to SQLite on error. Otherwise uses SQLite.
179
+ */
180
+ search(query, k) {
181
+ if (this.config.mode === 'rvf-primary' && this.rvfAvailable && this.rvfStore) {
182
+ try {
183
+ return this.rvfStore.search(query, k);
184
+ }
185
+ catch {
186
+ // Fall back to SQLite
187
+ }
188
+ }
189
+ // SQLite-based search (brute-force cosine similarity)
190
+ return this.searchSqlite(query, k);
191
+ }
192
+ // --------------------------------------------------------------------------
193
+ // Divergence
194
+ // --------------------------------------------------------------------------
195
+ /**
196
+ * Generate a divergence report between SQLite embeddings and RVF vectors.
197
+ */
198
+ getDivergenceReport() {
199
+ const report = {
200
+ totalChecked: 0,
201
+ divergences: 0,
202
+ details: [],
203
+ };
204
+ // Get SQLite embedding count
205
+ const sqliteCount = this.getSqliteEmbeddingCount();
206
+ report.totalChecked = sqliteCount;
207
+ if (!this.rvfAvailable || !this.rvfStore) {
208
+ // If RVF is not available, every SQLite embedding is "missing in RVF"
209
+ if (this.config.mode !== 'sqlite-only' && sqliteCount > 0) {
210
+ report.divergences = 1;
211
+ report.details.push({
212
+ patternId: '*',
213
+ issue: 'count-mismatch',
214
+ });
215
+ }
216
+ return report;
217
+ }
218
+ // Get RVF vector count
219
+ const rvfStatus = this.rvfStore.status();
220
+ const rvfCount = rvfStatus.totalVectors;
221
+ if (sqliteCount !== rvfCount) {
222
+ report.divergences = 1;
223
+ report.details.push({
224
+ patternId: '*',
225
+ issue: 'count-mismatch',
226
+ });
227
+ }
228
+ return report;
229
+ }
230
+ /**
231
+ * Returns true when promotion from dual-write to rvf-primary is safe
232
+ * (zero divergences between the two stores).
233
+ */
234
+ isPromotionSafe() {
235
+ const report = this.getDivergenceReport();
236
+ return report.divergences === 0;
237
+ }
238
+ // --------------------------------------------------------------------------
239
+ // Status
240
+ // --------------------------------------------------------------------------
241
+ /**
242
+ * Combined status from both backends.
243
+ */
244
+ status() {
245
+ const sqlitePatternCount = this.getSqlitePatternCount();
246
+ const sqliteVectorCount = this.getSqliteEmbeddingCount();
247
+ let rvfStatus = null;
248
+ if (this.rvfAvailable && this.rvfStore) {
249
+ try {
250
+ rvfStatus = this.rvfStore.status();
251
+ }
252
+ catch {
253
+ rvfStatus = null;
254
+ }
255
+ }
256
+ return {
257
+ sqlite: {
258
+ patternCount: sqlitePatternCount,
259
+ vectorCount: sqliteVectorCount,
260
+ },
261
+ rvf: rvfStatus,
262
+ mode: this.config.mode,
263
+ };
264
+ }
265
+ // --------------------------------------------------------------------------
266
+ // Lifecycle
267
+ // --------------------------------------------------------------------------
268
+ /**
269
+ * Close the RVF store. SQLite is managed externally.
270
+ */
271
+ close() {
272
+ if (this.rvfStore) {
273
+ try {
274
+ this.rvfStore.close();
275
+ }
276
+ catch {
277
+ // Ignore close errors
278
+ }
279
+ this.rvfStore = null;
280
+ this.rvfAvailable = false;
281
+ }
282
+ }
283
+ // --------------------------------------------------------------------------
284
+ // Private helpers
285
+ // --------------------------------------------------------------------------
286
+ shouldWriteRvf() {
287
+ return ((this.config.mode === 'dual-write' || this.config.mode === 'rvf-primary') &&
288
+ this.rvfAvailable &&
289
+ this.rvfStore !== null);
290
+ }
291
+ writeSqliteEmbedding(patternId, embedding) {
292
+ const blob = Buffer.from(embedding instanceof Float32Array
293
+ ? embedding.buffer
294
+ : new Float32Array(embedding).buffer);
295
+ const dimension = embedding.length;
296
+ // Upsert into qe_pattern_embeddings
297
+ if (tableExists(this.db, 'qe_pattern_embeddings')) {
298
+ this.db.prepare(`
299
+ INSERT INTO qe_pattern_embeddings (pattern_id, embedding, dimension, model, created_at)
300
+ VALUES (?, ?, ?, 'all-MiniLM-L6-v2', datetime('now'))
301
+ ON CONFLICT(pattern_id) DO UPDATE SET
302
+ embedding = excluded.embedding,
303
+ dimension = excluded.dimension,
304
+ created_at = datetime('now')
305
+ `).run(patternId, blob, dimension);
306
+ }
307
+ }
308
+ deleteSqliteEmbedding(patternId) {
309
+ if (tableExists(this.db, 'qe_pattern_embeddings')) {
310
+ this.db.prepare('DELETE FROM qe_pattern_embeddings WHERE pattern_id = ?').run(patternId);
311
+ }
312
+ }
313
+ getSqliteEmbeddingCount() {
314
+ if (!tableExists(this.db, 'qe_pattern_embeddings'))
315
+ return 0;
316
+ const row = this.db.prepare('SELECT COUNT(*) as cnt FROM qe_pattern_embeddings').get();
317
+ return row?.cnt ?? 0;
318
+ }
319
+ getSqlitePatternCount() {
320
+ if (!tableExists(this.db, 'qe_patterns'))
321
+ return 0;
322
+ const row = this.db.prepare('SELECT COUNT(*) as cnt FROM qe_patterns').get();
323
+ return row?.cnt ?? 0;
324
+ }
325
+ /**
326
+ * Brute-force cosine similarity search over SQLite embeddings.
327
+ * This is the fallback when RVF is unavailable.
328
+ */
329
+ searchSqlite(query, k) {
330
+ if (!tableExists(this.db, 'qe_pattern_embeddings'))
331
+ return [];
332
+ const rows = this.db.prepare('SELECT pattern_id, embedding, dimension FROM qe_pattern_embeddings').all();
333
+ const queryArr = query instanceof Float32Array ? Array.from(query) : query;
334
+ const queryMag = Math.sqrt(queryArr.reduce((s, v) => s + v * v, 0));
335
+ if (queryMag === 0)
336
+ return [];
337
+ const scored = [];
338
+ for (const row of rows) {
339
+ const float32 = new Float32Array(row.embedding.buffer, row.embedding.byteOffset, row.dimension);
340
+ const vec = Array.from(float32);
341
+ let dot = 0;
342
+ let mag = 0;
343
+ for (let i = 0; i < vec.length && i < queryArr.length; i++) {
344
+ dot += vec[i] * queryArr[i];
345
+ mag += vec[i] * vec[i];
346
+ }
347
+ mag = Math.sqrt(mag);
348
+ const score = mag > 0 ? dot / (queryMag * mag) : 0;
349
+ scored.push({ id: row.pattern_id, score });
350
+ }
351
+ scored.sort((a, b) => b.score - a.score);
352
+ return scored.slice(0, k);
353
+ }
354
+ }
355
+ // ============================================================================
356
+ // Factory
357
+ // ============================================================================
358
+ /**
359
+ * Create a new RvfDualWriter instance.
360
+ *
361
+ * @param db - better-sqlite3 Database instance
362
+ * @param config - Dual-write configuration
363
+ */
364
+ export function createDualWriter(db, config) {
365
+ return new RvfDualWriter(db, config);
366
+ }
367
+ //# sourceMappingURL=rvf-dual-writer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"rvf-dual-writer.js","sourceRoot":"","sources":["../../../src/integrations/ruvector/rvf-dual-writer.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,60 @@
1
+ /**
2
+ * RVF Native Adapter — thin wrapper around @ruvector/rvf-node N-API binding.
3
+ *
4
+ * Bypasses the buggy @ruvector/rvf SDK wrapper and talks directly to the
5
+ * native layer. Adds string-ID mapping on top of the numeric labels the
6
+ * native API requires, and persists the mapping as a sidecar JSON file.
7
+ */
8
+ export interface RvfSearchResult {
9
+ /** String ID (mapped back from numeric label) */
10
+ id: string;
11
+ /** Raw distance from the native HNSW index */
12
+ distance: number;
13
+ /** Similarity score: 1 / (1 + distance) — cosine-compatible */
14
+ score: number;
15
+ }
16
+ export interface RvfStatus {
17
+ totalVectors: number;
18
+ totalSegments: number;
19
+ fileSizeBytes: number;
20
+ epoch: number;
21
+ witnessValid: boolean;
22
+ witnessEntries: number;
23
+ }
24
+ export interface RvfNativeAdapter {
25
+ /** Insert vectors with string IDs */
26
+ ingest(entries: Array<{
27
+ id: string;
28
+ vector: Float32Array | number[];
29
+ }>): {
30
+ accepted: number;
31
+ rejected: number;
32
+ };
33
+ /** Search k nearest neighbours */
34
+ search(query: Float32Array | number[], k: number): RvfSearchResult[];
35
+ /** Delete by string IDs — returns count deleted */
36
+ delete(ids: string[]): number;
37
+ /** COW fork — creates an independent copy at `childPath` */
38
+ fork(childPath: string): RvfNativeAdapter;
39
+ /** Database status including witness-chain verification */
40
+ status(): RvfStatus;
41
+ /** Vector dimensionality */
42
+ dimension(): number;
43
+ /** Total vector count */
44
+ size(): number;
45
+ /** Compact to reclaim space from deleted vectors */
46
+ compact(): void;
47
+ /** Close and release native resources */
48
+ close(): void;
49
+ /** Whether the underlying database handle is still open */
50
+ isOpen(): boolean;
51
+ /** Filesystem path of the RVF container */
52
+ path(): string;
53
+ }
54
+ /** Create a new RVF container */
55
+ export declare function createRvfStore(path: string, dimensions: number): RvfNativeAdapter;
56
+ /** Open an existing RVF container (loads persisted ID mapping) */
57
+ export declare function openRvfStore(path: string): RvfNativeAdapter;
58
+ /** Check whether the native binding is loadable on this platform */
59
+ export declare function isRvfNativeAvailable(): boolean;
60
+ //# sourceMappingURL=rvf-native-adapter.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"rvf-native-adapter.d.ts","sourceRoot":"","sources":["../../../src/integrations/ruvector/rvf-native-adapter.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AA4BH,MAAM,WAAW,eAAe;IAC9B,iDAAiD;IACjD,EAAE,EAAE,MAAM,CAAC;IACX,8CAA8C;IAC9C,QAAQ,EAAE,MAAM,CAAC;IACjB,+DAA+D;IAC/D,KAAK,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,SAAS;IACxB,YAAY,EAAE,MAAM,CAAC;IACrB,aAAa,EAAE,MAAM,CAAC;IACtB,aAAa,EAAE,MAAM,CAAC;IACtB,KAAK,EAAE,MAAM,CAAC;IACd,YAAY,EAAE,OAAO,CAAC;IACtB,cAAc,EAAE,MAAM,CAAC;CACxB;AAED,MAAM,WAAW,gBAAgB;IAC/B,qCAAqC;IACrC,MAAM,CAAC,OAAO,EAAE,KAAK,CAAC;QAAE,EAAE,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,YAAY,GAAG,MAAM,EAAE,CAAA;KAAE,CAAC,GAAG;QACvE,QAAQ,EAAE,MAAM,CAAC;QACjB,QAAQ,EAAE,MAAM,CAAC;KAClB,CAAC;IAEF,kCAAkC;IAClC,MAAM,CAAC,KAAK,EAAE,YAAY,GAAG,MAAM,EAAE,EAAE,CAAC,EAAE,MAAM,GAAG,eAAe,EAAE,CAAC;IAErE,mDAAmD;IACnD,MAAM,CAAC,GAAG,EAAE,MAAM,EAAE,GAAG,MAAM,CAAC;IAE9B,4DAA4D;IAC5D,IAAI,CAAC,SAAS,EAAE,MAAM,GAAG,gBAAgB,CAAC;IAE1C,2DAA2D;IAC3D,MAAM,IAAI,SAAS,CAAC;IAEpB,4BAA4B;IAC5B,SAAS,IAAI,MAAM,CAAC;IAEpB,yBAAyB;IACzB,IAAI,IAAI,MAAM,CAAC;IAEf,oDAAoD;IACpD,OAAO,IAAI,IAAI,CAAC;IAEhB,yCAAyC;IACzC,KAAK,IAAI,IAAI,CAAC;IAEd,2DAA2D;IAC3D,MAAM,IAAI,OAAO,CAAC;IAElB,2CAA2C;IAC3C,IAAI,IAAI,MAAM,CAAC;CAChB;AA+PD,iCAAiC;AACjC,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,GAAG,gBAAgB,CAiBjF;AAED,kEAAkE;AAClE,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,GAAG,gBAAgB,CAW3D;AAED,oEAAoE;AACpE,wBAAgB,oBAAoB,IAAI,OAAO,CAE9C"}
@@ -0,0 +1,240 @@
1
+ /**
2
+ * RVF Native Adapter — thin wrapper around @ruvector/rvf-node N-API binding.
3
+ *
4
+ * Bypasses the buggy @ruvector/rvf SDK wrapper and talks directly to the
5
+ * native layer. Adds string-ID mapping on top of the numeric labels the
6
+ * native API requires, and persists the mapping as a sidecar JSON file.
7
+ */
8
+ import { readFileSync, writeFileSync, copyFileSync, existsSync } from 'fs';
9
+ // ---------------------------------------------------------------------------
10
+ // Native binding — lazy-loaded, failure-safe
11
+ // ---------------------------------------------------------------------------
12
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
13
+ let _native = null;
14
+ let _nativeChecked = false;
15
+ function getNative() {
16
+ if (_nativeChecked)
17
+ return _native;
18
+ _nativeChecked = true;
19
+ try {
20
+ // eslint-disable-next-line @typescript-eslint/no-require-imports
21
+ _native = require('@ruvector/rvf-node');
22
+ }
23
+ catch {
24
+ _native = null;
25
+ }
26
+ return _native;
27
+ }
28
+ function idMapPath(rvfPath) {
29
+ return `${rvfPath}.idmap.json`;
30
+ }
31
+ function loadIdMap(rvfPath) {
32
+ const p = idMapPath(rvfPath);
33
+ const strToNum = new Map();
34
+ const numToStr = new Map();
35
+ let nextLabel = 1;
36
+ if (existsSync(p)) {
37
+ try {
38
+ const raw = JSON.parse(readFileSync(p, 'utf-8'));
39
+ nextLabel = raw.nextLabel;
40
+ for (const [str, num] of raw.entries) {
41
+ strToNum.set(str, num);
42
+ numToStr.set(num, str);
43
+ }
44
+ }
45
+ catch {
46
+ // corrupted file — start fresh
47
+ }
48
+ }
49
+ return { strToNum, numToStr, nextLabel };
50
+ }
51
+ function saveIdMap(rvfPath, strToNum, nextLabel) {
52
+ const data = {
53
+ nextLabel,
54
+ entries: Array.from(strToNum.entries()),
55
+ };
56
+ writeFileSync(idMapPath(rvfPath), JSON.stringify(data), 'utf-8');
57
+ }
58
+ // ---------------------------------------------------------------------------
59
+ // Implementation
60
+ // ---------------------------------------------------------------------------
61
+ class RvfNativeAdapterImpl {
62
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
63
+ db;
64
+ _path;
65
+ _dimension;
66
+ strToNum;
67
+ numToStr;
68
+ nextLabel;
69
+ _open;
70
+ constructor(
71
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
72
+ db, filePath, dim, strToNum, numToStr, nextLabel) {
73
+ this.db = db;
74
+ this._path = filePath;
75
+ this._dimension = dim;
76
+ this.strToNum = strToNum;
77
+ this.numToStr = numToStr;
78
+ this.nextLabel = nextLabel;
79
+ this._open = true;
80
+ }
81
+ // -- ingest ---------------------------------------------------------------
82
+ ingest(entries) {
83
+ this.ensureOpen();
84
+ if (entries.length === 0)
85
+ return { accepted: 0, rejected: 0 };
86
+ const dim = this._dimension;
87
+ const flat = new Float32Array(entries.length * dim);
88
+ const ids = [];
89
+ for (let i = 0; i < entries.length; i++) {
90
+ const { id, vector } = entries[i];
91
+ // Resolve or assign numeric label
92
+ let label = this.strToNum.get(id);
93
+ if (label === undefined) {
94
+ label = this.nextLabel++;
95
+ this.strToNum.set(id, label);
96
+ this.numToStr.set(label, id);
97
+ }
98
+ ids.push(label);
99
+ // Copy vector data into flat buffer
100
+ const src = vector instanceof Float32Array ? vector : new Float32Array(vector);
101
+ flat.set(src.subarray(0, dim), i * dim);
102
+ }
103
+ const result = this.db.ingestBatch(flat, ids);
104
+ this.persistIdMap();
105
+ return { accepted: result.accepted, rejected: result.rejected };
106
+ }
107
+ // -- search ---------------------------------------------------------------
108
+ search(query, k) {
109
+ this.ensureOpen();
110
+ const q = query instanceof Float32Array ? query : new Float32Array(query);
111
+ const raw = this.db.query(q, k);
112
+ return raw
113
+ .map((r) => {
114
+ const strId = this.numToStr.get(r.id);
115
+ if (strId === undefined)
116
+ return null;
117
+ return {
118
+ id: strId,
119
+ distance: r.distance,
120
+ score: 1 / (1 + r.distance),
121
+ };
122
+ })
123
+ .filter((r) => r !== null);
124
+ }
125
+ // -- delete ---------------------------------------------------------------
126
+ delete(ids) {
127
+ this.ensureOpen();
128
+ const numericIds = [];
129
+ for (const id of ids) {
130
+ const label = this.strToNum.get(id);
131
+ if (label !== undefined) {
132
+ numericIds.push(label);
133
+ }
134
+ }
135
+ if (numericIds.length === 0)
136
+ return 0;
137
+ const result = this.db.delete(numericIds);
138
+ // Remove from maps
139
+ for (const id of ids) {
140
+ const label = this.strToNum.get(id);
141
+ if (label !== undefined) {
142
+ this.strToNum.delete(id);
143
+ this.numToStr.delete(label);
144
+ }
145
+ }
146
+ this.persistIdMap();
147
+ return result.deleted;
148
+ }
149
+ // -- fork -----------------------------------------------------------------
150
+ fork(childPath) {
151
+ this.ensureOpen();
152
+ // Copy the RVF file to get an independent snapshot with all data
153
+ copyFileSync(this._path, childPath);
154
+ // Copy the ID map
155
+ const childStrToNum = new Map(this.strToNum);
156
+ const childNumToStr = new Map(this.numToStr);
157
+ saveIdMap(childPath, childStrToNum, this.nextLabel);
158
+ const native = getNative();
159
+ const childDb = native.RvfDatabase.open(childPath);
160
+ return new RvfNativeAdapterImpl(childDb, childPath, this._dimension, childStrToNum, childNumToStr, this.nextLabel);
161
+ }
162
+ // -- status ---------------------------------------------------------------
163
+ status() {
164
+ this.ensureOpen();
165
+ const s = this.db.status();
166
+ // Count witness segments from the segment list
167
+ const segs = this.db.segments();
168
+ const witnessSegs = segs.filter((seg) => seg.segType === 'witness');
169
+ return {
170
+ totalVectors: s.totalVectors,
171
+ totalSegments: s.totalSegments,
172
+ fileSizeBytes: s.fileSize,
173
+ epoch: s.currentEpoch,
174
+ witnessValid: witnessSegs.length > 0,
175
+ witnessEntries: witnessSegs.length,
176
+ };
177
+ }
178
+ // -- accessors ------------------------------------------------------------
179
+ dimension() {
180
+ return this._dimension;
181
+ }
182
+ size() {
183
+ this.ensureOpen();
184
+ return this.db.status().totalVectors;
185
+ }
186
+ compact() {
187
+ this.ensureOpen();
188
+ this.db.compact();
189
+ }
190
+ close() {
191
+ if (this._open) {
192
+ this.db.close();
193
+ this._open = false;
194
+ }
195
+ }
196
+ isOpen() {
197
+ return this._open;
198
+ }
199
+ path() {
200
+ return this._path;
201
+ }
202
+ // -- internal -------------------------------------------------------------
203
+ ensureOpen() {
204
+ if (!this._open) {
205
+ throw new Error('RVF database is closed');
206
+ }
207
+ }
208
+ persistIdMap() {
209
+ saveIdMap(this._path, this.strToNum, this.nextLabel);
210
+ }
211
+ }
212
+ // ---------------------------------------------------------------------------
213
+ // Factory functions
214
+ // ---------------------------------------------------------------------------
215
+ /** Create a new RVF container */
216
+ export function createRvfStore(path, dimensions) {
217
+ const native = getNative();
218
+ if (!native) {
219
+ throw new Error('@ruvector/rvf-node is not available — install the package or check platform compatibility');
220
+ }
221
+ const db = native.RvfDatabase.create(path, { dimension: dimensions });
222
+ const dim = db.dimension();
223
+ return new RvfNativeAdapterImpl(db, path, dim, new Map(), new Map(), 1);
224
+ }
225
+ /** Open an existing RVF container (loads persisted ID mapping) */
226
+ export function openRvfStore(path) {
227
+ const native = getNative();
228
+ if (!native) {
229
+ throw new Error('@ruvector/rvf-node is not available — install the package or check platform compatibility');
230
+ }
231
+ const db = native.RvfDatabase.open(path);
232
+ const dim = db.dimension();
233
+ const { strToNum, numToStr, nextLabel } = loadIdMap(path);
234
+ return new RvfNativeAdapterImpl(db, path, dim, strToNum, numToStr, nextLabel);
235
+ }
236
+ /** Check whether the native binding is loadable on this platform */
237
+ export function isRvfNativeAvailable() {
238
+ return getNative() !== null;
239
+ }
240
+ //# sourceMappingURL=rvf-native-adapter.js.map