@soulcraft/brainy 3.31.0 → 3.32.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.
@@ -789,6 +789,7 @@ export class GcsStorage extends BaseStorage {
789
789
  : undefined;
790
790
  return {
791
791
  nodes,
792
+ totalCount: this.totalNounCount,
792
793
  hasMore: !!nextCursor,
793
794
  nextCursor
794
795
  };
@@ -797,6 +798,7 @@ export class GcsStorage extends BaseStorage {
797
798
  if (response?.nextPageToken) {
798
799
  return {
799
800
  nodes,
801
+ totalCount: this.totalNounCount,
800
802
  hasMore: true,
801
803
  nextCursor: `${shardIndex}:${response.nextPageToken}`
802
804
  };
@@ -806,6 +808,7 @@ export class GcsStorage extends BaseStorage {
806
808
  // No more shards or nodes
807
809
  return {
808
810
  nodes,
811
+ totalCount: this.totalNounCount,
809
812
  hasMore: false,
810
813
  nextCursor: undefined
811
814
  };
@@ -943,6 +946,7 @@ export class GcsStorage extends BaseStorage {
943
946
  }
944
947
  return {
945
948
  items: filteredVerbs,
949
+ totalCount: this.totalVerbCount,
946
950
  hasMore: !!response?.nextPageToken,
947
951
  nextCursor: response?.nextPageToken
948
952
  };
@@ -81,6 +81,8 @@ export class OPFSStorage extends BaseStorage {
81
81
  this.indexDir = await this.rootDir.getDirectoryHandle(INDEX_DIR, {
82
82
  create: true
83
83
  });
84
+ // Initialize counts from storage
85
+ await this.initializeCounts();
84
86
  this.isInitialized = true;
85
87
  }
86
88
  catch (error) {
@@ -235,6 +235,8 @@ export class S3CompatibleStorage extends BaseStorage {
235
235
  this.initializeCoalescer();
236
236
  // Auto-cleanup legacy /index folder on initialization
237
237
  await this.cleanupLegacyIndexFolder();
238
+ // Initialize counts from storage
239
+ await this.initializeCounts();
238
240
  this.isInitialized = true;
239
241
  this.logger.info(`Initialized ${this.serviceType} storage with bucket ${this.bucketName}`);
240
242
  }
@@ -1425,6 +1427,7 @@ export class S3CompatibleStorage extends BaseStorage {
1425
1427
  }
1426
1428
  return {
1427
1429
  items: filteredGraphVerbs,
1430
+ totalCount: this.totalVerbCount, // Use pre-calculated count from init()
1428
1431
  hasMore: result.hasMore,
1429
1432
  nextCursor: result.nextCursor
1430
1433
  };
@@ -2633,21 +2636,9 @@ export class S3CompatibleStorage extends BaseStorage {
2633
2636
  filteredNodes = filteredByMetadata;
2634
2637
  }
2635
2638
  }
2636
- // Calculate total count efficiently
2637
- // For the first page (no cursor), we can estimate total count
2638
- let totalCount;
2639
- if (!cursor) {
2640
- try {
2641
- totalCount = await this.estimateTotalNounCount();
2642
- }
2643
- catch (error) {
2644
- this.logger.warn('Failed to estimate total noun count:', error);
2645
- // totalCount remains undefined
2646
- }
2647
- }
2648
2639
  return {
2649
2640
  items: filteredNodes,
2650
- totalCount,
2641
+ totalCount: this.totalNounCount, // Use pre-calculated count from init()
2651
2642
  hasMore: result.hasMore,
2652
2643
  nextCursor: result.nextCursor
2653
2644
  };
@@ -422,9 +422,18 @@ export class BaseStorage extends BaseStorageAdapter {
422
422
  // If we have no items but hasMore is true, force hasMore to false
423
423
  // This prevents pagination bugs from causing infinite loops
424
424
  const safeHasMore = items.length > 0 ? result.hasMore : false;
425
+ // VALIDATION: Ensure adapter returns totalCount (prevents restart bugs)
426
+ // If adapter forgets to return totalCount, log warning and use pre-calculated count
427
+ let finalTotalCount = result.totalCount || totalCount;
428
+ if (result.totalCount === undefined && this.totalNounCount > 0) {
429
+ console.warn(`⚠️ Storage adapter missing totalCount in getNounsWithPagination result! ` +
430
+ `Using pre-calculated count (${this.totalNounCount}) as fallback. ` +
431
+ `Please ensure your storage adapter returns totalCount: this.totalNounCount`);
432
+ finalTotalCount = this.totalNounCount;
433
+ }
425
434
  return {
426
435
  items,
427
- totalCount: result.totalCount || totalCount,
436
+ totalCount: finalTotalCount,
428
437
  hasMore: safeHasMore,
429
438
  nextCursor: result.nextCursor
430
439
  };
@@ -571,9 +580,18 @@ export class BaseStorage extends BaseStorageAdapter {
571
580
  // If we have no items but hasMore is true, force hasMore to false
572
581
  // This prevents pagination bugs from causing infinite loops
573
582
  const safeHasMore = items.length > 0 ? result.hasMore : false;
583
+ // VALIDATION: Ensure adapter returns totalCount (prevents restart bugs)
584
+ // If adapter forgets to return totalCount, log warning and use pre-calculated count
585
+ let finalTotalCount = result.totalCount || totalCount;
586
+ if (result.totalCount === undefined && this.totalVerbCount > 0) {
587
+ console.warn(`⚠️ Storage adapter missing totalCount in getVerbsWithPagination result! ` +
588
+ `Using pre-calculated count (${this.totalVerbCount}) as fallback. ` +
589
+ `Please ensure your storage adapter returns totalCount: this.totalVerbCount`);
590
+ finalTotalCount = this.totalVerbCount;
591
+ }
574
592
  return {
575
593
  items,
576
- totalCount: result.totalCount || totalCount,
594
+ totalCount: finalTotalCount,
577
595
  hasMore: safeHasMore,
578
596
  nextCursor: result.nextCursor
579
597
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@soulcraft/brainy",
3
- "version": "3.31.0",
3
+ "version": "3.32.0",
4
4
  "description": "Universal Knowledge Protocol™ - World's first Triple Intelligence database unifying vector, graph, and document search in one API. 31 nouns × 40 verbs for infinite expressiveness.",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.js",