@soulcraft/brainy 0.26.0 → 0.27.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.
- package/README.md +31 -0
- package/dist/brainyData.d.ts +22 -0
- package/dist/index.d.ts +4 -4
- package/dist/types/graphTypes.d.ts +269 -18
- package/dist/types/graphTypes.d.ts.map +1 -1
- package/dist/unified.js +347 -63
- package/dist/unified.min.js +290 -290
- package/package.json +6 -4
package/dist/unified.js
CHANGED
|
@@ -9916,40 +9916,251 @@ async function createStorage(options = {}) {
|
|
|
9916
9916
|
return new MemoryStorage();
|
|
9917
9917
|
}
|
|
9918
9918
|
|
|
9919
|
+
/**
|
|
9920
|
+
* Graph Types - Standardized Noun and Verb Type System
|
|
9921
|
+
*
|
|
9922
|
+
* This module defines a comprehensive, standardized set of noun and verb types
|
|
9923
|
+
* that can be used to model any kind of graph, semantic network, or data model.
|
|
9924
|
+
*
|
|
9925
|
+
* ## Purpose and Design Philosophy
|
|
9926
|
+
*
|
|
9927
|
+
* The type system is designed to be:
|
|
9928
|
+
* - **Universal**: Capable of representing any domain or use case
|
|
9929
|
+
* - **Hierarchical**: Organized into logical categories for easy navigation
|
|
9930
|
+
* - **Extensible**: Additional metadata can be attached to any entity or relationship
|
|
9931
|
+
* - **Semantic**: Types carry meaning that can be used for reasoning and inference
|
|
9932
|
+
*
|
|
9933
|
+
* ## Noun Types (Entities)
|
|
9934
|
+
*
|
|
9935
|
+
* Noun types represent entities in the graph and are organized into categories:
|
|
9936
|
+
*
|
|
9937
|
+
* ### Core Entity Types
|
|
9938
|
+
* - **Person**: Human entities and individuals
|
|
9939
|
+
* - **Organization**: Formal organizations, companies, institutions
|
|
9940
|
+
* - **Location**: Geographic locations, places, addresses
|
|
9941
|
+
* - **Thing**: Physical objects and tangible items
|
|
9942
|
+
* - **Concept**: Abstract ideas, concepts, and intangible entities
|
|
9943
|
+
* - **Event**: Occurrences with time and place dimensions
|
|
9944
|
+
*
|
|
9945
|
+
* ### Digital/Content Types
|
|
9946
|
+
* - **Document**: Text-based files and documents
|
|
9947
|
+
* - **Media**: Non-text media files (images, videos, audio)
|
|
9948
|
+
* - **File**: Generic digital files
|
|
9949
|
+
* - **Message**: Communication content
|
|
9950
|
+
* - **Content**: Generic content that doesn't fit other categories
|
|
9951
|
+
*
|
|
9952
|
+
* ### Collection Types
|
|
9953
|
+
* - **Collection**: Generic groupings of items
|
|
9954
|
+
* - **Dataset**: Structured collections of data
|
|
9955
|
+
*
|
|
9956
|
+
* ### Business/Application Types
|
|
9957
|
+
* - **Product**: Commercial products and offerings
|
|
9958
|
+
* - **Service**: Services and offerings
|
|
9959
|
+
* - **User**: User accounts and profiles
|
|
9960
|
+
* - **Task**: Actions, todos, and workflow items
|
|
9961
|
+
* - **Project**: Organized initiatives with goals and timelines
|
|
9962
|
+
*
|
|
9963
|
+
* ### Descriptive Types
|
|
9964
|
+
* - **Process**: Workflows, procedures, and sequences
|
|
9965
|
+
* - **State**: States, conditions, or statuses
|
|
9966
|
+
* - **Role**: Roles, positions, or responsibilities
|
|
9967
|
+
* - **Topic**: Subjects or themes
|
|
9968
|
+
* - **Language**: Languages or linguistic entities
|
|
9969
|
+
* - **Currency**: Currencies and monetary units
|
|
9970
|
+
* - **Measurement**: Measurements, metrics, or quantities
|
|
9971
|
+
*
|
|
9972
|
+
* ## Verb Types (Relationships)
|
|
9973
|
+
*
|
|
9974
|
+
* Verb types represent relationships between entities and are organized into categories:
|
|
9975
|
+
*
|
|
9976
|
+
* ### Core Relationship Types
|
|
9977
|
+
* - **RelatedTo**: Generic relationship (default fallback)
|
|
9978
|
+
* - **Contains**: Containment relationship
|
|
9979
|
+
* - **PartOf**: Part-whole relationship
|
|
9980
|
+
* - **LocatedAt**: Spatial relationship
|
|
9981
|
+
* - **References**: Reference or citation relationship
|
|
9982
|
+
*
|
|
9983
|
+
* ### Temporal/Causal Types
|
|
9984
|
+
* - **Precedes/Succeeds**: Temporal sequence relationships
|
|
9985
|
+
* - **Causes**: Causal relationships
|
|
9986
|
+
* - **DependsOn**: Dependency relationships
|
|
9987
|
+
* - **Requires**: Necessity relationships
|
|
9988
|
+
*
|
|
9989
|
+
* ### Creation/Transformation Types
|
|
9990
|
+
* - **Creates**: Creation relationships
|
|
9991
|
+
* - **Transforms**: Transformation relationships
|
|
9992
|
+
* - **Becomes**: State change relationships
|
|
9993
|
+
* - **Modifies**: Modification relationships
|
|
9994
|
+
* - **Consumes**: Consumption relationships
|
|
9995
|
+
*
|
|
9996
|
+
* ### Ownership/Attribution Types
|
|
9997
|
+
* - **Owns**: Ownership relationships
|
|
9998
|
+
* - **AttributedTo**: Attribution or authorship
|
|
9999
|
+
* - **CreatedBy**: Creation attribution
|
|
10000
|
+
* - **BelongsTo**: Belonging relationships
|
|
10001
|
+
*
|
|
10002
|
+
* ### Social/Organizational Types
|
|
10003
|
+
* - **MemberOf**: Membership or affiliation
|
|
10004
|
+
* - **WorksWith**: Professional relationships
|
|
10005
|
+
* - **FriendOf**: Friendship relationships
|
|
10006
|
+
* - **Follows**: Following relationships
|
|
10007
|
+
* - **Likes**: Liking relationships
|
|
10008
|
+
* - **ReportsTo**: Reporting relationships
|
|
10009
|
+
* - **Supervises**: Supervisory relationships
|
|
10010
|
+
* - **Mentors**: Mentorship relationships
|
|
10011
|
+
* - **Communicates**: Communication relationships
|
|
10012
|
+
*
|
|
10013
|
+
* ### Descriptive/Functional Types
|
|
10014
|
+
* - **Describes**: Descriptive relationships
|
|
10015
|
+
* - **Defines**: Definition relationships
|
|
10016
|
+
* - **Categorizes**: Categorization relationships
|
|
10017
|
+
* - **Measures**: Measurement relationships
|
|
10018
|
+
* - **Evaluates**: Evaluation or assessment relationships
|
|
10019
|
+
* - **Uses**: Utilization relationships
|
|
10020
|
+
* - **Implements**: Implementation relationships
|
|
10021
|
+
* - **Extends**: Extension relationships
|
|
10022
|
+
*
|
|
10023
|
+
* ## Usage with Additional Metadata
|
|
10024
|
+
*
|
|
10025
|
+
* While the type system provides a standardized vocabulary, additional metadata
|
|
10026
|
+
* can be attached to any entity or relationship to capture domain-specific
|
|
10027
|
+
* information:
|
|
10028
|
+
*
|
|
10029
|
+
* ```typescript
|
|
10030
|
+
* const person: GraphNoun = {
|
|
10031
|
+
* id: 'person-123',
|
|
10032
|
+
* noun: NounType.Person,
|
|
10033
|
+
* data: {
|
|
10034
|
+
* name: 'John Doe',
|
|
10035
|
+
* age: 30,
|
|
10036
|
+
* profession: 'Engineer'
|
|
10037
|
+
* }
|
|
10038
|
+
* }
|
|
10039
|
+
*
|
|
10040
|
+
* const worksFor: GraphVerb = {
|
|
10041
|
+
* id: 'verb-456',
|
|
10042
|
+
* source: 'person-123',
|
|
10043
|
+
* target: 'org-789',
|
|
10044
|
+
* verb: VerbType.MemberOf,
|
|
10045
|
+
* data: {
|
|
10046
|
+
* role: 'Senior Engineer',
|
|
10047
|
+
* startDate: '2020-01-01',
|
|
10048
|
+
* department: 'Engineering'
|
|
10049
|
+
* }
|
|
10050
|
+
* }
|
|
10051
|
+
* ```
|
|
10052
|
+
*
|
|
10053
|
+
* ## Modeling Different Graph Types
|
|
10054
|
+
*
|
|
10055
|
+
* This type system can model various graph structures:
|
|
10056
|
+
*
|
|
10057
|
+
* ### Knowledge Graphs
|
|
10058
|
+
* Use Person, Organization, Location, Concept entities with semantic relationships
|
|
10059
|
+
* like AttributedTo, LocatedAt, RelatedTo
|
|
10060
|
+
*
|
|
10061
|
+
* ### Social Networks
|
|
10062
|
+
* Use Person, User entities with social relationships like FriendOf, Follows,
|
|
10063
|
+
* WorksWith, Communicates
|
|
10064
|
+
*
|
|
10065
|
+
* ### Content Networks
|
|
10066
|
+
* Use Document, Media, Content entities with relationships like References,
|
|
10067
|
+
* CreatedBy, Contains, Categorizes
|
|
10068
|
+
*
|
|
10069
|
+
* ### Business Process Models
|
|
10070
|
+
* Use Task, Process, Role entities with relationships like Precedes, Requires,
|
|
10071
|
+
* DependsOn, Transforms
|
|
10072
|
+
*
|
|
10073
|
+
* ### Organizational Charts
|
|
10074
|
+
* Use Person, Role, Organization entities with relationships like ReportsTo,
|
|
10075
|
+
* Supervises, MemberOf
|
|
10076
|
+
*
|
|
10077
|
+
* The flexibility of this system allows it to represent any domain while
|
|
10078
|
+
* maintaining semantic consistency and enabling powerful graph operations
|
|
10079
|
+
* and reasoning capabilities.
|
|
10080
|
+
*/
|
|
9919
10081
|
/**
|
|
9920
10082
|
* Defines valid noun types for graph entities
|
|
9921
10083
|
* Used for categorizing different types of nodes
|
|
9922
10084
|
*/
|
|
9923
10085
|
const NounType = {
|
|
9924
|
-
|
|
9925
|
-
|
|
9926
|
-
|
|
9927
|
-
|
|
9928
|
-
|
|
9929
|
-
|
|
9930
|
-
|
|
9931
|
-
|
|
9932
|
-
|
|
10086
|
+
// Core Entity Types
|
|
10087
|
+
Person: 'person', // Human entities
|
|
10088
|
+
Organization: 'organization', // Formal organizations (companies, institutions, etc.)
|
|
10089
|
+
Location: 'location', // Geographic locations (merges previous Place and Location)
|
|
10090
|
+
Thing: 'thing', // Physical objects
|
|
10091
|
+
Concept: 'concept', // Abstract ideas, concepts, and intangible entities
|
|
10092
|
+
Event: 'event', // Occurrences with time and place
|
|
10093
|
+
// Digital/Content Types
|
|
10094
|
+
Document: 'document', // Text-based files and documents (reports, articles, etc.)
|
|
10095
|
+
Media: 'media', // Non-text media files (images, videos, audio)
|
|
10096
|
+
File: 'file', // Generic digital files (merges aspects of Digital with file-specific focus)
|
|
10097
|
+
Message: 'message', // Communication content (emails, chat messages, posts)
|
|
10098
|
+
Content: 'content', // Generic content that doesn't fit other categories
|
|
10099
|
+
// Collection Types
|
|
10100
|
+
Collection: 'collection', // Generic grouping of items (merges Group, List, and Category)
|
|
10101
|
+
Dataset: 'dataset', // Structured collections of data
|
|
10102
|
+
// Business/Application Types
|
|
10103
|
+
Product: 'product', // Commercial products and offerings
|
|
10104
|
+
Service: 'service', // Services and offerings
|
|
10105
|
+
User: 'user', // User accounts and profiles
|
|
10106
|
+
Task: 'task', // Actions, todos, and workflow items
|
|
10107
|
+
Project: 'project', // Organized initiatives with goals and timelines
|
|
10108
|
+
// Descriptive Types
|
|
10109
|
+
Process: 'process', // Workflows, procedures, and sequences
|
|
10110
|
+
State: 'state', // States, conditions, or statuses
|
|
10111
|
+
Role: 'role', // Roles, positions, or responsibilities
|
|
10112
|
+
Topic: 'topic', // Subjects or themes
|
|
10113
|
+
Language: 'language', // Languages or linguistic entities
|
|
10114
|
+
Currency: 'currency', // Currencies and monetary units
|
|
10115
|
+
Measurement: 'measurement' // Measurements, metrics, or quantities
|
|
9933
10116
|
};
|
|
9934
10117
|
/**
|
|
9935
10118
|
* Defines valid verb types for relationships
|
|
9936
10119
|
* Used for categorizing different types of connections
|
|
9937
10120
|
*/
|
|
9938
10121
|
const VerbType = {
|
|
9939
|
-
|
|
9940
|
-
|
|
9941
|
-
|
|
9942
|
-
|
|
9943
|
-
|
|
9944
|
-
|
|
9945
|
-
|
|
9946
|
-
|
|
9947
|
-
|
|
9948
|
-
|
|
9949
|
-
|
|
9950
|
-
|
|
9951
|
-
|
|
9952
|
-
|
|
10122
|
+
// Core Relationship Types
|
|
10123
|
+
RelatedTo: 'relatedTo', // Generic relationship (default fallback)
|
|
10124
|
+
Contains: 'contains', // Containment relationship (parent contains child)
|
|
10125
|
+
PartOf: 'partOf', // Part-whole relationship (child is part of parent)
|
|
10126
|
+
LocatedAt: 'locatedAt', // Spatial relationship
|
|
10127
|
+
References: 'references', // Reference or citation relationship
|
|
10128
|
+
// Temporal/Causal Types
|
|
10129
|
+
Precedes: 'precedes', // Temporal sequence (comes before)
|
|
10130
|
+
Succeeds: 'succeeds', // Temporal sequence (comes after)
|
|
10131
|
+
Causes: 'causes', // Causal relationship (merges Influences and Causes)
|
|
10132
|
+
DependsOn: 'dependsOn', // Dependency relationship
|
|
10133
|
+
Requires: 'requires', // Necessity relationship (new)
|
|
10134
|
+
// Creation/Transformation Types
|
|
10135
|
+
Creates: 'creates', // Creation relationship (merges Created and Produces)
|
|
10136
|
+
Transforms: 'transforms', // Transformation relationship
|
|
10137
|
+
Becomes: 'becomes', // State change relationship
|
|
10138
|
+
Modifies: 'modifies', // Modification relationship
|
|
10139
|
+
Consumes: 'consumes', // Consumption relationship
|
|
10140
|
+
// Ownership/Attribution Types
|
|
10141
|
+
Owns: 'owns', // Ownership relationship (merges Controls and Owns)
|
|
10142
|
+
AttributedTo: 'attributedTo', // Attribution or authorship
|
|
10143
|
+
CreatedBy: 'createdBy', // Creation attribution (new, distinct from Creates)
|
|
10144
|
+
BelongsTo: 'belongsTo', // Belonging relationship (new)
|
|
10145
|
+
// Social/Organizational Types
|
|
10146
|
+
MemberOf: 'memberOf', // Membership or affiliation
|
|
10147
|
+
WorksWith: 'worksWith', // Professional relationship
|
|
10148
|
+
FriendOf: 'friendOf', // Friendship relationship
|
|
10149
|
+
Follows: 'follows', // Following relationship
|
|
10150
|
+
Likes: 'likes', // Liking relationship
|
|
10151
|
+
ReportsTo: 'reportsTo', // Reporting relationship
|
|
10152
|
+
Supervises: 'supervises', // Supervisory relationship
|
|
10153
|
+
Mentors: 'mentors', // Mentorship relationship
|
|
10154
|
+
Communicates: 'communicates', // Communication relationship (merges Communicates and Collaborates)
|
|
10155
|
+
// Descriptive/Functional Types
|
|
10156
|
+
Describes: 'describes', // Descriptive relationship
|
|
10157
|
+
Defines: 'defines', // Definition relationship
|
|
10158
|
+
Categorizes: 'categorizes', // Categorization relationship
|
|
10159
|
+
Measures: 'measures', // Measurement relationship
|
|
10160
|
+
Evaluates: 'evaluates', // Evaluation or assessment relationship
|
|
10161
|
+
Uses: 'uses', // Utilization relationship (new)
|
|
10162
|
+
Implements: 'implements', // Implementation relationship
|
|
10163
|
+
Extends: 'extends' // Extension relationship (merges Extends and Inherits)
|
|
9953
10164
|
};
|
|
9954
10165
|
|
|
9955
10166
|
/** Common types for the augmentation system */
|
|
@@ -12202,6 +12413,12 @@ class BrainyData {
|
|
|
12202
12413
|
config.storage?.requestPersistentStorage || false;
|
|
12203
12414
|
// Set read-only flag
|
|
12204
12415
|
this.readOnly = config.readOnly || false;
|
|
12416
|
+
// Set write-only flag
|
|
12417
|
+
this.writeOnly = config.writeOnly || false;
|
|
12418
|
+
// Validate that readOnly and writeOnly are not both true
|
|
12419
|
+
if (this.readOnly && this.writeOnly) {
|
|
12420
|
+
throw new Error('Database cannot be both read-only and write-only');
|
|
12421
|
+
}
|
|
12205
12422
|
// Store storage configuration for later use in init()
|
|
12206
12423
|
this.storageConfig = config.storage || {};
|
|
12207
12424
|
// Store timeout and retry configuration
|
|
@@ -12228,6 +12445,15 @@ class BrainyData {
|
|
|
12228
12445
|
throw new Error('Cannot perform write operation: database is in read-only mode');
|
|
12229
12446
|
}
|
|
12230
12447
|
}
|
|
12448
|
+
/**
|
|
12449
|
+
* Check if the database is in write-only mode and throw an error if it is
|
|
12450
|
+
* @throws Error if the database is in write-only mode
|
|
12451
|
+
*/
|
|
12452
|
+
checkWriteOnly() {
|
|
12453
|
+
if (this.writeOnly) {
|
|
12454
|
+
throw new Error('Cannot perform search operation: database is in write-only mode');
|
|
12455
|
+
}
|
|
12456
|
+
}
|
|
12231
12457
|
/**
|
|
12232
12458
|
* Start real-time updates if enabled in the configuration
|
|
12233
12459
|
* This will periodically check for new data in storage and update the in-memory index and statistics
|
|
@@ -12242,14 +12468,16 @@ class BrainyData {
|
|
|
12242
12468
|
return;
|
|
12243
12469
|
}
|
|
12244
12470
|
// Set the initial last known noun count
|
|
12245
|
-
this.getNounCount()
|
|
12471
|
+
this.getNounCount()
|
|
12472
|
+
.then((count) => {
|
|
12246
12473
|
this.lastKnownNounCount = count;
|
|
12247
|
-
})
|
|
12474
|
+
})
|
|
12475
|
+
.catch((error) => {
|
|
12248
12476
|
console.warn('Failed to get initial noun count for real-time updates:', error);
|
|
12249
12477
|
});
|
|
12250
12478
|
// Start the update timer
|
|
12251
12479
|
this.updateTimerId = setInterval(() => {
|
|
12252
|
-
this.checkForUpdates().catch(error => {
|
|
12480
|
+
this.checkForUpdates().catch((error) => {
|
|
12253
12481
|
console.warn('Error during real-time update check:', error);
|
|
12254
12482
|
});
|
|
12255
12483
|
}, this.realtimeUpdateConfig.interval);
|
|
@@ -12415,7 +12643,8 @@ class BrainyData {
|
|
|
12415
12643
|
// Continue with other changes
|
|
12416
12644
|
}
|
|
12417
12645
|
}
|
|
12418
|
-
if (this.loggingConfig?.verbose &&
|
|
12646
|
+
if (this.loggingConfig?.verbose &&
|
|
12647
|
+
(addedCount > 0 || updatedCount > 0 || deletedCount > 0)) {
|
|
12419
12648
|
console.log(`Real-time update: Added ${addedCount}, updated ${updatedCount}, deleted ${deletedCount} nouns using change log`);
|
|
12420
12649
|
}
|
|
12421
12650
|
// Update the last known noun count
|
|
@@ -12442,7 +12671,7 @@ class BrainyData {
|
|
|
12442
12671
|
const indexNouns = this.index.getNouns();
|
|
12443
12672
|
const indexNounIds = new Set(indexNouns.keys());
|
|
12444
12673
|
// Find nouns that are in storage but not in the index
|
|
12445
|
-
const newNouns = nouns.filter(noun => !indexNounIds.has(noun.id));
|
|
12674
|
+
const newNouns = nouns.filter((noun) => !indexNounIds.has(noun.id));
|
|
12446
12675
|
// Add new nouns to the index
|
|
12447
12676
|
for (const noun of newNouns) {
|
|
12448
12677
|
// Check if the vector dimensions match the expected dimensions
|
|
@@ -12574,23 +12803,31 @@ class BrainyData {
|
|
|
12574
12803
|
if (this.useOptimizedIndex && this.index instanceof HNSWIndexOptimized) {
|
|
12575
12804
|
this.index.setStorage(this.storage);
|
|
12576
12805
|
}
|
|
12577
|
-
//
|
|
12578
|
-
|
|
12579
|
-
|
|
12580
|
-
|
|
12581
|
-
|
|
12582
|
-
|
|
12583
|
-
|
|
12584
|
-
|
|
12585
|
-
|
|
12586
|
-
|
|
12587
|
-
|
|
12806
|
+
// In write-only mode, skip loading the index into memory
|
|
12807
|
+
if (this.writeOnly) {
|
|
12808
|
+
if (this.loggingConfig?.verbose) {
|
|
12809
|
+
console.log('Database is in write-only mode, skipping index loading');
|
|
12810
|
+
}
|
|
12811
|
+
}
|
|
12812
|
+
else {
|
|
12813
|
+
// Load all nouns from storage
|
|
12814
|
+
const nouns = await this.storage.getAllNouns();
|
|
12815
|
+
// Clear the index and add all nouns
|
|
12816
|
+
this.index.clear();
|
|
12817
|
+
for (const noun of nouns) {
|
|
12818
|
+
// Check if the vector dimensions match the expected dimensions
|
|
12819
|
+
if (noun.vector.length !== this._dimensions) {
|
|
12820
|
+
console.warn(`Deleting noun ${noun.id} due to dimension mismatch: expected ${this._dimensions}, got ${noun.vector.length}`);
|
|
12821
|
+
// Delete the mismatched noun from storage to prevent future issues
|
|
12822
|
+
await this.storage.deleteNoun(noun.id);
|
|
12823
|
+
continue;
|
|
12824
|
+
}
|
|
12825
|
+
// Add to index
|
|
12826
|
+
await this.index.addItem({
|
|
12827
|
+
id: noun.id,
|
|
12828
|
+
vector: noun.vector
|
|
12829
|
+
});
|
|
12588
12830
|
}
|
|
12589
|
-
// Add to index
|
|
12590
|
-
await this.index.addItem({
|
|
12591
|
-
id: noun.id,
|
|
12592
|
-
vector: noun.vector
|
|
12593
|
-
});
|
|
12594
12831
|
}
|
|
12595
12832
|
// Connect to remote server if configured with autoConnect
|
|
12596
12833
|
if (this.remoteServerConfig && this.remoteServerConfig.autoConnect) {
|
|
@@ -12664,8 +12901,7 @@ class BrainyData {
|
|
|
12664
12901
|
}
|
|
12665
12902
|
}
|
|
12666
12903
|
// Check if input is already a vector
|
|
12667
|
-
if (Array.isArray(vectorOrData) &&
|
|
12668
|
-
!options.forceEmbed) {
|
|
12904
|
+
if (Array.isArray(vectorOrData) && !options.forceEmbed) {
|
|
12669
12905
|
// Input is already a vector (and we've validated it contains only numbers)
|
|
12670
12906
|
vector = vectorOrData;
|
|
12671
12907
|
}
|
|
@@ -12706,7 +12942,9 @@ class BrainyData {
|
|
|
12706
12942
|
// Save metadata if provided and not empty
|
|
12707
12943
|
if (metadata !== undefined) {
|
|
12708
12944
|
// Skip saving if metadata is an empty object
|
|
12709
|
-
if (metadata &&
|
|
12945
|
+
if (metadata &&
|
|
12946
|
+
typeof metadata === 'object' &&
|
|
12947
|
+
Object.keys(metadata).length === 0) {
|
|
12710
12948
|
// Don't save empty metadata
|
|
12711
12949
|
// Explicitly save null to ensure no metadata is stored
|
|
12712
12950
|
await this.storage.saveMetadata(id, null);
|
|
@@ -12938,7 +13176,7 @@ class BrainyData {
|
|
|
12938
13176
|
filterResultsByService(results, service) {
|
|
12939
13177
|
if (!service)
|
|
12940
13178
|
return results;
|
|
12941
|
-
return results.filter(result => {
|
|
13179
|
+
return results.filter((result) => {
|
|
12942
13180
|
if (!result.metadata || typeof result.metadata !== 'object')
|
|
12943
13181
|
return false;
|
|
12944
13182
|
if (!('createdBy' in result.metadata))
|
|
@@ -12961,6 +13199,8 @@ class BrainyData {
|
|
|
12961
13199
|
if (!this.isInitialized) {
|
|
12962
13200
|
throw new Error('BrainyData must be initialized before searching. Call init() first.');
|
|
12963
13201
|
}
|
|
13202
|
+
// Check if database is in write-only mode
|
|
13203
|
+
this.checkWriteOnly();
|
|
12964
13204
|
try {
|
|
12965
13205
|
let queryVector;
|
|
12966
13206
|
// Check if input is already a vector
|
|
@@ -13087,6 +13327,8 @@ class BrainyData {
|
|
|
13087
13327
|
if (!this.isInitialized) {
|
|
13088
13328
|
throw new Error('BrainyData must be initialized before searching. Call init() first.');
|
|
13089
13329
|
}
|
|
13330
|
+
// Check if database is in write-only mode
|
|
13331
|
+
this.checkWriteOnly();
|
|
13090
13332
|
// If searching for verbs directly
|
|
13091
13333
|
if (options.searchVerbs) {
|
|
13092
13334
|
const verbResults = await this.searchVerbs(queryVectorOrData, k, {
|
|
@@ -13138,6 +13380,8 @@ class BrainyData {
|
|
|
13138
13380
|
if (!this.isInitialized) {
|
|
13139
13381
|
throw new Error('BrainyData must be initialized before searching. Call init() first.');
|
|
13140
13382
|
}
|
|
13383
|
+
// Check if database is in write-only mode
|
|
13384
|
+
this.checkWriteOnly();
|
|
13141
13385
|
// If input is a string and not a vector, automatically vectorize it
|
|
13142
13386
|
let queryToUse = queryVectorOrData;
|
|
13143
13387
|
if (typeof queryVectorOrData === 'string' && !options.forceEmbed) {
|
|
@@ -13202,9 +13446,9 @@ class BrainyData {
|
|
|
13202
13446
|
// Get all verbs (relationships) from the source entity
|
|
13203
13447
|
const outgoingVerbs = await this.storage.getVerbsBySource(id);
|
|
13204
13448
|
// Filter to only include verbs of the specified type
|
|
13205
|
-
const verbsOfType = outgoingVerbs.filter(verb => verb.type === options.relationType);
|
|
13449
|
+
const verbsOfType = outgoingVerbs.filter((verb) => verb.type === options.relationType);
|
|
13206
13450
|
// Get the target IDs
|
|
13207
|
-
const targetIds = verbsOfType.map(verb => verb.target);
|
|
13451
|
+
const targetIds = verbsOfType.map((verb) => verb.target);
|
|
13208
13452
|
// Get the actual entities for these IDs
|
|
13209
13453
|
const results = [];
|
|
13210
13454
|
for (const targetId of targetIds) {
|
|
@@ -13382,7 +13626,7 @@ class BrainyData {
|
|
|
13382
13626
|
const service = options.service || this.getCurrentAugmentation();
|
|
13383
13627
|
const graphNoun = metadata;
|
|
13384
13628
|
// Preserve existing createdBy and createdAt if they exist
|
|
13385
|
-
const existingMetadata = await this.storage.getMetadata(id);
|
|
13629
|
+
const existingMetadata = (await this.storage.getMetadata(id));
|
|
13386
13630
|
if (existingMetadata &&
|
|
13387
13631
|
typeof existingMetadata === 'object' &&
|
|
13388
13632
|
'createdBy' in existingMetadata) {
|
|
@@ -13791,7 +14035,7 @@ class BrainyData {
|
|
|
13791
14035
|
// Get all verbs from storage
|
|
13792
14036
|
const allVerbs = await this.storage.getAllVerbs();
|
|
13793
14037
|
// Create a set of verb IDs for faster lookup
|
|
13794
|
-
const verbIds = new Set(allVerbs.map(verb => verb.id));
|
|
14038
|
+
const verbIds = new Set(allVerbs.map((verb) => verb.id));
|
|
13795
14039
|
// Get all nouns from the index
|
|
13796
14040
|
const nouns = this.index.getNouns();
|
|
13797
14041
|
// Count nouns that are not verbs
|
|
@@ -13853,8 +14097,14 @@ class BrainyData {
|
|
|
13853
14097
|
};
|
|
13854
14098
|
// Filter by service if specified
|
|
13855
14099
|
const services = options.service
|
|
13856
|
-
?
|
|
13857
|
-
|
|
14100
|
+
? Array.isArray(options.service)
|
|
14101
|
+
? options.service
|
|
14102
|
+
: [options.service]
|
|
14103
|
+
: Object.keys({
|
|
14104
|
+
...stats.nounCount,
|
|
14105
|
+
...stats.verbCount,
|
|
14106
|
+
...stats.metadataCount
|
|
14107
|
+
});
|
|
13858
14108
|
// Calculate totals and service breakdown
|
|
13859
14109
|
for (const service of services) {
|
|
13860
14110
|
const nounCount = stats.nounCount[service] || 0;
|
|
@@ -13959,6 +14209,28 @@ class BrainyData {
|
|
|
13959
14209
|
*/
|
|
13960
14210
|
setReadOnly(readOnly) {
|
|
13961
14211
|
this.readOnly = readOnly;
|
|
14212
|
+
// Ensure readOnly and writeOnly are not both true
|
|
14213
|
+
if (readOnly && this.writeOnly) {
|
|
14214
|
+
this.writeOnly = false;
|
|
14215
|
+
}
|
|
14216
|
+
}
|
|
14217
|
+
/**
|
|
14218
|
+
* Check if the database is in write-only mode
|
|
14219
|
+
* @returns True if the database is in write-only mode, false otherwise
|
|
14220
|
+
*/
|
|
14221
|
+
isWriteOnly() {
|
|
14222
|
+
return this.writeOnly;
|
|
14223
|
+
}
|
|
14224
|
+
/**
|
|
14225
|
+
* Set the database to write-only mode
|
|
14226
|
+
* @param writeOnly True to set the database to write-only mode, false to allow searches
|
|
14227
|
+
*/
|
|
14228
|
+
setWriteOnly(writeOnly) {
|
|
14229
|
+
this.writeOnly = writeOnly;
|
|
14230
|
+
// Ensure readOnly and writeOnly are not both true
|
|
14231
|
+
if (writeOnly && this.readOnly) {
|
|
14232
|
+
this.readOnly = false;
|
|
14233
|
+
}
|
|
13962
14234
|
}
|
|
13963
14235
|
/**
|
|
13964
14236
|
* Embed text or data into a vector using the same embedding function used by this instance
|
|
@@ -13986,6 +14258,8 @@ class BrainyData {
|
|
|
13986
14258
|
*/
|
|
13987
14259
|
async searchVerbs(queryVectorOrData, k = 10, options = {}) {
|
|
13988
14260
|
await this.ensureInitialized();
|
|
14261
|
+
// Check if database is in write-only mode
|
|
14262
|
+
this.checkWriteOnly();
|
|
13989
14263
|
try {
|
|
13990
14264
|
let queryVector;
|
|
13991
14265
|
// Check if input is already a vector
|
|
@@ -14052,9 +14326,11 @@ class BrainyData {
|
|
|
14052
14326
|
verbs = allVerbs;
|
|
14053
14327
|
}
|
|
14054
14328
|
// Calculate similarity for each verb not already in results
|
|
14055
|
-
const existingIds = new Set(verbResults.map(v => v.id));
|
|
14329
|
+
const existingIds = new Set(verbResults.map((v) => v.id));
|
|
14056
14330
|
for (const verb of verbs) {
|
|
14057
|
-
if (!existingIds.has(verb.id) &&
|
|
14331
|
+
if (!existingIds.has(verb.id) &&
|
|
14332
|
+
verb.vector &&
|
|
14333
|
+
verb.vector.length > 0) {
|
|
14058
14334
|
const distance = this.index.getDistanceFunction()(queryVector, verb.vector);
|
|
14059
14335
|
verbResults.push({
|
|
14060
14336
|
...verb,
|
|
@@ -14082,6 +14358,8 @@ class BrainyData {
|
|
|
14082
14358
|
*/
|
|
14083
14359
|
async searchNounsByVerbs(queryVectorOrData, k = 10, options = {}) {
|
|
14084
14360
|
await this.ensureInitialized();
|
|
14361
|
+
// Check if database is in write-only mode
|
|
14362
|
+
this.checkWriteOnly();
|
|
14085
14363
|
try {
|
|
14086
14364
|
// First, search for nouns
|
|
14087
14365
|
const nounResults = await this.searchByNounTypes(queryVectorOrData, k * 2, // Get more results initially to account for filtering
|
|
@@ -14171,6 +14449,8 @@ class BrainyData {
|
|
|
14171
14449
|
*/
|
|
14172
14450
|
async searchText(query, k = 10, options = {}) {
|
|
14173
14451
|
await this.ensureInitialized();
|
|
14452
|
+
// Check if database is in write-only mode
|
|
14453
|
+
this.checkWriteOnly();
|
|
14174
14454
|
try {
|
|
14175
14455
|
// Embed the query text
|
|
14176
14456
|
const queryVector = await this.embed(query);
|
|
@@ -14195,6 +14475,8 @@ class BrainyData {
|
|
|
14195
14475
|
*/
|
|
14196
14476
|
async searchRemote(queryVectorOrData, k = 10, options = {}) {
|
|
14197
14477
|
await this.ensureInitialized();
|
|
14478
|
+
// Check if database is in write-only mode
|
|
14479
|
+
this.checkWriteOnly();
|
|
14198
14480
|
// Check if connected to a remote server
|
|
14199
14481
|
if (!this.isConnectedToRemoteServer()) {
|
|
14200
14482
|
throw new Error('Not connected to a remote server. Call connectToRemoteServer() first.');
|
|
@@ -14234,6 +14516,8 @@ class BrainyData {
|
|
|
14234
14516
|
*/
|
|
14235
14517
|
async searchCombined(queryVectorOrData, k = 10, options = {}) {
|
|
14236
14518
|
await this.ensureInitialized();
|
|
14519
|
+
// Check if database is in write-only mode
|
|
14520
|
+
this.checkWriteOnly();
|
|
14237
14521
|
// Check if connected to a remote server
|
|
14238
14522
|
if (!this.isConnectedToRemoteServer()) {
|
|
14239
14523
|
// If not connected to a remote server, just search locally
|
|
@@ -14669,14 +14953,14 @@ class BrainyData {
|
|
|
14669
14953
|
const nounIds = [];
|
|
14670
14954
|
const nounDescriptions = {
|
|
14671
14955
|
[NounType.Person]: 'A person with unique characteristics',
|
|
14672
|
-
[NounType.
|
|
14956
|
+
[NounType.Location]: 'A location with specific attributes',
|
|
14673
14957
|
[NounType.Thing]: 'An object with distinct properties',
|
|
14674
14958
|
[NounType.Event]: 'An occurrence with temporal aspects',
|
|
14675
14959
|
[NounType.Concept]: 'An abstract idea or notion',
|
|
14676
14960
|
[NounType.Content]: 'A piece of content or information',
|
|
14677
|
-
[NounType.
|
|
14678
|
-
[NounType.
|
|
14679
|
-
[NounType.
|
|
14961
|
+
[NounType.Collection]: 'A collection of related entities',
|
|
14962
|
+
[NounType.Organization]: 'An organization or institution',
|
|
14963
|
+
[NounType.Document]: 'A document or text-based file'
|
|
14680
14964
|
};
|
|
14681
14965
|
for (let i = 0; i < nounCount; i++) {
|
|
14682
14966
|
// Select a random noun type
|
|
@@ -14702,10 +14986,10 @@ class BrainyData {
|
|
|
14702
14986
|
const verbIds = [];
|
|
14703
14987
|
const verbDescriptions = {
|
|
14704
14988
|
[VerbType.AttributedTo]: 'Attribution relationship',
|
|
14705
|
-
[VerbType.Controls]: 'Control relationship',
|
|
14706
|
-
[VerbType.Created]: 'Creation relationship',
|
|
14707
|
-
[VerbType.Earned]: 'Achievement relationship',
|
|
14708
14989
|
[VerbType.Owns]: 'Ownership relationship',
|
|
14990
|
+
[VerbType.Creates]: 'Creation relationship',
|
|
14991
|
+
[VerbType.Uses]: 'Utilization relationship',
|
|
14992
|
+
[VerbType.BelongsTo]: 'Belonging relationship',
|
|
14709
14993
|
[VerbType.MemberOf]: 'Membership relationship',
|
|
14710
14994
|
[VerbType.RelatedTo]: 'General relationship',
|
|
14711
14995
|
[VerbType.WorksWith]: 'Collaboration relationship',
|