@soulcraft/brainy 1.5.0 → 2.0.1
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/CHANGELOG.md +188 -0
- package/LICENSE +2 -2
- package/README.md +200 -595
- package/bin/brainy-interactive.js +564 -0
- package/bin/brainy-ts.js +18 -0
- package/bin/brainy.js +672 -81
- package/dist/augmentationPipeline.d.ts +48 -220
- package/dist/augmentationPipeline.js +60 -508
- package/dist/augmentationRegistry.d.ts +22 -31
- package/dist/augmentationRegistry.js +28 -79
- package/dist/augmentations/apiServerAugmentation.d.ts +108 -0
- package/dist/augmentations/apiServerAugmentation.js +502 -0
- package/dist/augmentations/batchProcessingAugmentation.d.ts +95 -0
- package/dist/augmentations/batchProcessingAugmentation.js +567 -0
- package/dist/augmentations/brainyAugmentation.d.ts +153 -0
- package/dist/augmentations/brainyAugmentation.js +145 -0
- package/dist/augmentations/cacheAugmentation.d.ts +105 -0
- package/dist/augmentations/cacheAugmentation.js +238 -0
- package/dist/augmentations/conduitAugmentations.d.ts +54 -156
- package/dist/augmentations/conduitAugmentations.js +156 -1082
- package/dist/augmentations/connectionPoolAugmentation.d.ts +62 -0
- package/dist/augmentations/connectionPoolAugmentation.js +316 -0
- package/dist/augmentations/defaultAugmentations.d.ts +53 -0
- package/dist/augmentations/defaultAugmentations.js +88 -0
- package/dist/augmentations/entityRegistryAugmentation.d.ts +126 -0
- package/dist/augmentations/entityRegistryAugmentation.js +386 -0
- package/dist/augmentations/indexAugmentation.d.ts +117 -0
- package/dist/augmentations/indexAugmentation.js +284 -0
- package/dist/augmentations/intelligentVerbScoringAugmentation.d.ts +152 -0
- package/dist/augmentations/intelligentVerbScoringAugmentation.js +554 -0
- package/dist/augmentations/metricsAugmentation.d.ts +202 -0
- package/dist/augmentations/metricsAugmentation.js +291 -0
- package/dist/augmentations/monitoringAugmentation.d.ts +94 -0
- package/dist/augmentations/monitoringAugmentation.js +227 -0
- package/dist/augmentations/neuralImport.d.ts +50 -117
- package/dist/augmentations/neuralImport.js +255 -629
- package/dist/augmentations/requestDeduplicatorAugmentation.d.ts +52 -0
- package/dist/augmentations/requestDeduplicatorAugmentation.js +162 -0
- package/dist/augmentations/serverSearchAugmentations.d.ts +43 -22
- package/dist/augmentations/serverSearchAugmentations.js +125 -72
- package/dist/augmentations/storageAugmentation.d.ts +54 -0
- package/dist/augmentations/storageAugmentation.js +93 -0
- package/dist/augmentations/storageAugmentations.d.ts +96 -0
- package/dist/augmentations/storageAugmentations.js +182 -0
- package/dist/augmentations/synapseAugmentation.d.ts +156 -0
- package/dist/augmentations/synapseAugmentation.js +312 -0
- package/dist/augmentations/walAugmentation.d.ts +108 -0
- package/dist/augmentations/walAugmentation.js +515 -0
- package/dist/brainyData.d.ts +404 -130
- package/dist/brainyData.js +1331 -853
- package/dist/chat/BrainyChat.d.ts +16 -8
- package/dist/chat/BrainyChat.js +60 -32
- package/dist/chat/ChatCLI.d.ts +1 -1
- package/dist/chat/ChatCLI.js +6 -6
- package/dist/cli/catalog.d.ts +3 -3
- package/dist/cli/catalog.js +116 -70
- package/dist/cli/commands/core.d.ts +61 -0
- package/dist/cli/commands/core.js +348 -0
- package/dist/cli/commands/neural.d.ts +25 -0
- package/dist/cli/commands/neural.js +508 -0
- package/dist/cli/commands/utility.d.ts +37 -0
- package/dist/cli/commands/utility.js +276 -0
- package/dist/cli/index.d.ts +7 -0
- package/dist/cli/index.js +167 -0
- package/dist/cli/interactive.d.ts +164 -0
- package/dist/cli/interactive.js +542 -0
- package/dist/cortex/neuralImport.js +5 -5
- package/dist/critical/model-guardian.js +11 -4
- package/dist/embeddings/lightweight-embedder.d.ts +23 -0
- package/dist/embeddings/lightweight-embedder.js +136 -0
- package/dist/embeddings/universal-memory-manager.d.ts +38 -0
- package/dist/embeddings/universal-memory-manager.js +206 -0
- package/dist/embeddings/worker-embedding.d.ts +7 -0
- package/dist/embeddings/worker-embedding.js +77 -0
- package/dist/embeddings/worker-manager.d.ts +28 -0
- package/dist/embeddings/worker-manager.js +162 -0
- package/dist/examples/basicUsage.js +7 -7
- package/dist/graph/pathfinding.d.ts +78 -0
- package/dist/graph/pathfinding.js +393 -0
- package/dist/hnsw/hnswIndex.d.ts +13 -0
- package/dist/hnsw/hnswIndex.js +35 -0
- package/dist/hnsw/hnswIndexOptimized.d.ts +1 -0
- package/dist/hnsw/hnswIndexOptimized.js +3 -0
- package/dist/index.d.ts +9 -11
- package/dist/index.js +21 -11
- package/dist/indices/fieldIndex.d.ts +76 -0
- package/dist/indices/fieldIndex.js +357 -0
- package/dist/mcp/brainyMCPAdapter.js +3 -2
- package/dist/mcp/mcpAugmentationToolset.js +11 -17
- package/dist/neural/embeddedPatterns.d.ts +41 -0
- package/dist/neural/embeddedPatterns.js +4044 -0
- package/dist/neural/naturalLanguageProcessor.d.ts +94 -0
- package/dist/neural/naturalLanguageProcessor.js +317 -0
- package/dist/neural/naturalLanguageProcessorStatic.d.ts +64 -0
- package/dist/neural/naturalLanguageProcessorStatic.js +151 -0
- package/dist/neural/neuralAPI.d.ts +255 -0
- package/dist/neural/neuralAPI.js +612 -0
- package/dist/neural/patternLibrary.d.ts +101 -0
- package/dist/neural/patternLibrary.js +313 -0
- package/dist/neural/patterns.d.ts +27 -0
- package/dist/neural/patterns.js +68 -0
- package/dist/neural/staticPatternMatcher.d.ts +35 -0
- package/dist/neural/staticPatternMatcher.js +153 -0
- package/dist/scripts/precomputePatternEmbeddings.d.ts +19 -0
- package/dist/scripts/precomputePatternEmbeddings.js +100 -0
- package/dist/storage/adapters/fileSystemStorage.d.ts +5 -0
- package/dist/storage/adapters/fileSystemStorage.js +20 -0
- package/dist/storage/adapters/s3CompatibleStorage.d.ts +5 -0
- package/dist/storage/adapters/s3CompatibleStorage.js +16 -0
- package/dist/storage/enhancedClearOperations.d.ts +83 -0
- package/dist/storage/enhancedClearOperations.js +345 -0
- package/dist/storage/storageFactory.js +31 -27
- package/dist/triple/TripleIntelligence.d.ts +134 -0
- package/dist/triple/TripleIntelligence.js +548 -0
- package/dist/types/augmentations.d.ts +45 -344
- package/dist/types/augmentations.js +5 -2
- package/dist/types/brainyDataInterface.d.ts +20 -10
- package/dist/types/graphTypes.d.ts +46 -0
- package/dist/types/graphTypes.js +16 -2
- package/dist/utils/BoundedRegistry.d.ts +29 -0
- package/dist/utils/BoundedRegistry.js +54 -0
- package/dist/utils/embedding.js +20 -3
- package/dist/utils/hybridModelManager.js +10 -5
- package/dist/utils/metadataFilter.d.ts +33 -19
- package/dist/utils/metadataFilter.js +58 -23
- package/dist/utils/metadataIndex.d.ts +37 -6
- package/dist/utils/metadataIndex.js +427 -64
- package/dist/utils/requestDeduplicator.d.ts +10 -0
- package/dist/utils/requestDeduplicator.js +24 -0
- package/dist/utils/unifiedCache.d.ts +103 -0
- package/dist/utils/unifiedCache.js +311 -0
- package/package.json +40 -125
- package/scripts/ensure-models.js +108 -0
- package/scripts/prepare-models.js +387 -0
- package/OFFLINE_MODELS.md +0 -56
- package/dist/intelligence/neuralEngine.d.ts +0 -207
- package/dist/intelligence/neuralEngine.js +0 -706
- package/dist/utils/modelLoader.d.ts +0 -32
- package/dist/utils/modelLoader.js +0 -219
- package/dist/utils/modelManager.d.ts +0 -77
- package/dist/utils/modelManager.js +0 -219
|
@@ -0,0 +1,313 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 🧠 Pattern Library for Natural Language Processing
|
|
3
|
+
* Manages pre-computed pattern embeddings and smart matching
|
|
4
|
+
*
|
|
5
|
+
* Uses Brainy's own features for self-leveraging intelligence:
|
|
6
|
+
* - Embeddings for semantic similarity
|
|
7
|
+
* - Pattern caching for performance
|
|
8
|
+
* - Progressive learning from usage
|
|
9
|
+
*/
|
|
10
|
+
import { EMBEDDED_PATTERNS, getPatternEmbeddings, PATTERNS_METADATA } from './embeddedPatterns.js';
|
|
11
|
+
export class PatternLibrary {
|
|
12
|
+
constructor(brain) {
|
|
13
|
+
this.brain = brain;
|
|
14
|
+
this.patterns = new Map();
|
|
15
|
+
this.patternEmbeddings = new Map();
|
|
16
|
+
this.embeddingCache = new Map();
|
|
17
|
+
this.successMetrics = new Map();
|
|
18
|
+
}
|
|
19
|
+
/**
|
|
20
|
+
* Initialize pattern library with pre-computed embeddings
|
|
21
|
+
*/
|
|
22
|
+
async init() {
|
|
23
|
+
// Try to load pre-computed embeddings first
|
|
24
|
+
const precomputedEmbeddings = getPatternEmbeddings();
|
|
25
|
+
if (precomputedEmbeddings.size > 0) {
|
|
26
|
+
// Use pre-computed embeddings (instant!)
|
|
27
|
+
console.debug(`Loading ${precomputedEmbeddings.size} pre-computed pattern embeddings`);
|
|
28
|
+
for (const pattern of EMBEDDED_PATTERNS) {
|
|
29
|
+
this.patterns.set(pattern.id, pattern);
|
|
30
|
+
this.successMetrics.set(pattern.id, pattern.confidence);
|
|
31
|
+
const embedding = precomputedEmbeddings.get(pattern.id);
|
|
32
|
+
if (embedding) {
|
|
33
|
+
this.patternEmbeddings.set(pattern.id, Array.from(embedding));
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
console.debug(`Pattern library ready: ${PATTERNS_METADATA.totalPatterns} patterns loaded instantly`);
|
|
37
|
+
}
|
|
38
|
+
else {
|
|
39
|
+
// Fall back to runtime computation
|
|
40
|
+
console.debug('No pre-computed embeddings found, computing at runtime...');
|
|
41
|
+
for (const pattern of EMBEDDED_PATTERNS) {
|
|
42
|
+
this.patterns.set(pattern.id, pattern);
|
|
43
|
+
this.successMetrics.set(pattern.id, pattern.confidence);
|
|
44
|
+
}
|
|
45
|
+
// Compute embeddings for all patterns
|
|
46
|
+
await this.precomputeEmbeddings();
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
/**
|
|
50
|
+
* Pre-compute embeddings for all patterns for fast matching
|
|
51
|
+
*/
|
|
52
|
+
async precomputeEmbeddings() {
|
|
53
|
+
for (const [id, pattern] of this.patterns) {
|
|
54
|
+
// Average embeddings of all examples for robust representation
|
|
55
|
+
const embeddings = [];
|
|
56
|
+
for (const example of pattern.examples) {
|
|
57
|
+
const embedding = await this.getEmbedding(example);
|
|
58
|
+
embeddings.push(embedding);
|
|
59
|
+
}
|
|
60
|
+
// Average the embeddings
|
|
61
|
+
const avgEmbedding = this.averageVectors(embeddings);
|
|
62
|
+
this.patternEmbeddings.set(id, avgEmbedding);
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
/**
|
|
66
|
+
* Get embedding with caching
|
|
67
|
+
*/
|
|
68
|
+
async getEmbedding(text) {
|
|
69
|
+
if (this.embeddingCache.has(text)) {
|
|
70
|
+
return this.embeddingCache.get(text);
|
|
71
|
+
}
|
|
72
|
+
const embedding = await this.brain.embed(text);
|
|
73
|
+
this.embeddingCache.set(text, embedding);
|
|
74
|
+
return embedding;
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* Find best matching patterns for a query
|
|
78
|
+
*/
|
|
79
|
+
async findBestPatterns(queryEmbedding, k = 3) {
|
|
80
|
+
const matches = [];
|
|
81
|
+
// Calculate similarity with all patterns
|
|
82
|
+
for (const [id, patternEmbedding] of this.patternEmbeddings) {
|
|
83
|
+
const similarity = this.cosineSimilarity(queryEmbedding, patternEmbedding);
|
|
84
|
+
const pattern = this.patterns.get(id);
|
|
85
|
+
// Apply success metric boost
|
|
86
|
+
const successBoost = this.successMetrics.get(id) || 0.5;
|
|
87
|
+
const adjustedSimilarity = similarity * (0.7 + 0.3 * successBoost);
|
|
88
|
+
matches.push({
|
|
89
|
+
pattern,
|
|
90
|
+
similarity: adjustedSimilarity
|
|
91
|
+
});
|
|
92
|
+
}
|
|
93
|
+
// Sort by similarity and return top k
|
|
94
|
+
matches.sort((a, b) => b.similarity - a.similarity);
|
|
95
|
+
return matches.slice(0, k);
|
|
96
|
+
}
|
|
97
|
+
/**
|
|
98
|
+
* Extract slots from query based on pattern
|
|
99
|
+
*/
|
|
100
|
+
extractSlots(query, pattern) {
|
|
101
|
+
const slots = {};
|
|
102
|
+
let confidence = pattern.confidence;
|
|
103
|
+
// Try regex extraction first
|
|
104
|
+
const regex = new RegExp(pattern.pattern, 'i');
|
|
105
|
+
const match = query.match(regex);
|
|
106
|
+
if (match) {
|
|
107
|
+
// Extract captured groups as slots
|
|
108
|
+
for (let i = 1; i < match.length; i++) {
|
|
109
|
+
slots[`$${i}`] = match[i];
|
|
110
|
+
}
|
|
111
|
+
// High confidence if regex matches
|
|
112
|
+
confidence = Math.min(confidence * 1.2, 1.0);
|
|
113
|
+
}
|
|
114
|
+
else {
|
|
115
|
+
// Fall back to token-based extraction
|
|
116
|
+
const tokens = this.tokenize(query);
|
|
117
|
+
const exampleTokens = this.tokenize(pattern.examples[0]);
|
|
118
|
+
// Simple alignment-based extraction
|
|
119
|
+
for (let i = 0; i < tokens.length; i++) {
|
|
120
|
+
if (i < exampleTokens.length && exampleTokens[i].startsWith('$')) {
|
|
121
|
+
slots[exampleTokens[i]] = tokens[i];
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
// Lower confidence for fuzzy matching
|
|
125
|
+
confidence *= 0.7;
|
|
126
|
+
}
|
|
127
|
+
// Post-process slots
|
|
128
|
+
this.postProcessSlots(slots, pattern);
|
|
129
|
+
return { slots, confidence };
|
|
130
|
+
}
|
|
131
|
+
/**
|
|
132
|
+
* Fill template with extracted slots
|
|
133
|
+
*/
|
|
134
|
+
fillTemplate(template, slots) {
|
|
135
|
+
const filled = JSON.parse(JSON.stringify(template));
|
|
136
|
+
// Recursively replace slot placeholders
|
|
137
|
+
const replacePlaceholders = (obj) => {
|
|
138
|
+
if (typeof obj === 'string') {
|
|
139
|
+
// Replace ${1}, ${2}, etc. with slot values
|
|
140
|
+
return obj.replace(/\$\{(\d+)\}/g, (_, num) => {
|
|
141
|
+
return slots[`$${num}`] || '';
|
|
142
|
+
});
|
|
143
|
+
}
|
|
144
|
+
else if (Array.isArray(obj)) {
|
|
145
|
+
return obj.map(item => replacePlaceholders(item));
|
|
146
|
+
}
|
|
147
|
+
else if (typeof obj === 'object' && obj !== null) {
|
|
148
|
+
const result = {};
|
|
149
|
+
for (const [key, value] of Object.entries(obj)) {
|
|
150
|
+
const newKey = replacePlaceholders(key);
|
|
151
|
+
result[newKey] = replacePlaceholders(value);
|
|
152
|
+
}
|
|
153
|
+
return result;
|
|
154
|
+
}
|
|
155
|
+
return obj;
|
|
156
|
+
};
|
|
157
|
+
return replacePlaceholders(filled);
|
|
158
|
+
}
|
|
159
|
+
/**
|
|
160
|
+
* Update pattern success metrics based on usage
|
|
161
|
+
*/
|
|
162
|
+
updateSuccessMetric(patternId, success) {
|
|
163
|
+
const current = this.successMetrics.get(patternId) || 0.5;
|
|
164
|
+
// Exponential moving average
|
|
165
|
+
const alpha = 0.1;
|
|
166
|
+
const newMetric = success
|
|
167
|
+
? current + alpha * (1 - current)
|
|
168
|
+
: current - alpha * current;
|
|
169
|
+
this.successMetrics.set(patternId, newMetric);
|
|
170
|
+
}
|
|
171
|
+
/**
|
|
172
|
+
* Learn new pattern from successful query
|
|
173
|
+
*/
|
|
174
|
+
async learnPattern(query, result) {
|
|
175
|
+
// Find similar existing patterns
|
|
176
|
+
const queryEmbedding = await this.getEmbedding(query);
|
|
177
|
+
const similar = await this.findBestPatterns(queryEmbedding, 1);
|
|
178
|
+
if (similar[0]?.similarity < 0.7) {
|
|
179
|
+
// This is a new pattern type - add it
|
|
180
|
+
const newPattern = {
|
|
181
|
+
id: `learned_${Date.now()}`,
|
|
182
|
+
category: 'learned',
|
|
183
|
+
examples: [query],
|
|
184
|
+
pattern: this.generateRegexFromQuery(query),
|
|
185
|
+
template: result,
|
|
186
|
+
confidence: 0.6 // Start with moderate confidence
|
|
187
|
+
};
|
|
188
|
+
this.patterns.set(newPattern.id, newPattern);
|
|
189
|
+
this.patternEmbeddings.set(newPattern.id, queryEmbedding);
|
|
190
|
+
this.successMetrics.set(newPattern.id, 0.6);
|
|
191
|
+
}
|
|
192
|
+
else {
|
|
193
|
+
// Similar pattern exists - add as example
|
|
194
|
+
const pattern = similar[0].pattern;
|
|
195
|
+
if (!pattern.examples.includes(query)) {
|
|
196
|
+
pattern.examples.push(query);
|
|
197
|
+
// Update pattern embedding with new example
|
|
198
|
+
const embeddings = await Promise.all(pattern.examples.map(ex => this.getEmbedding(ex)));
|
|
199
|
+
const newEmbedding = this.averageVectors(embeddings);
|
|
200
|
+
this.patternEmbeddings.set(pattern.id, newEmbedding);
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
}
|
|
204
|
+
/**
|
|
205
|
+
* Helper: Average multiple vectors
|
|
206
|
+
*/
|
|
207
|
+
averageVectors(vectors) {
|
|
208
|
+
if (vectors.length === 0)
|
|
209
|
+
return [];
|
|
210
|
+
const dim = vectors[0].length;
|
|
211
|
+
const avg = new Array(dim).fill(0);
|
|
212
|
+
for (const vec of vectors) {
|
|
213
|
+
for (let i = 0; i < dim; i++) {
|
|
214
|
+
avg[i] += vec[i];
|
|
215
|
+
}
|
|
216
|
+
}
|
|
217
|
+
for (let i = 0; i < dim; i++) {
|
|
218
|
+
avg[i] /= vectors.length;
|
|
219
|
+
}
|
|
220
|
+
return avg;
|
|
221
|
+
}
|
|
222
|
+
/**
|
|
223
|
+
* Helper: Calculate cosine similarity
|
|
224
|
+
*/
|
|
225
|
+
cosineSimilarity(a, b) {
|
|
226
|
+
let dotProduct = 0;
|
|
227
|
+
let normA = 0;
|
|
228
|
+
let normB = 0;
|
|
229
|
+
for (let i = 0; i < a.length; i++) {
|
|
230
|
+
dotProduct += a[i] * b[i];
|
|
231
|
+
normA += a[i] * a[i];
|
|
232
|
+
normB += b[i] * b[i];
|
|
233
|
+
}
|
|
234
|
+
normA = Math.sqrt(normA);
|
|
235
|
+
normB = Math.sqrt(normB);
|
|
236
|
+
if (normA === 0 || normB === 0)
|
|
237
|
+
return 0;
|
|
238
|
+
return dotProduct / (normA * normB);
|
|
239
|
+
}
|
|
240
|
+
/**
|
|
241
|
+
* Helper: Simple tokenization
|
|
242
|
+
*/
|
|
243
|
+
tokenize(text) {
|
|
244
|
+
return text.toLowerCase().split(/\s+/).filter(t => t.length > 0);
|
|
245
|
+
}
|
|
246
|
+
/**
|
|
247
|
+
* Helper: Post-process extracted slots
|
|
248
|
+
*/
|
|
249
|
+
postProcessSlots(slots, pattern) {
|
|
250
|
+
// Convert string numbers to actual numbers
|
|
251
|
+
for (const [key, value] of Object.entries(slots)) {
|
|
252
|
+
if (typeof value === 'string') {
|
|
253
|
+
// Check if it's a number
|
|
254
|
+
const num = parseFloat(value);
|
|
255
|
+
if (!isNaN(num) && value.match(/^\d+(\.\d+)?$/)) {
|
|
256
|
+
slots[key] = num;
|
|
257
|
+
}
|
|
258
|
+
// Parse dates
|
|
259
|
+
if (value.match(/\d{4}/) || value.match(/(january|february|march|april|may|june|july|august|september|october|november|december)/i)) {
|
|
260
|
+
// Simple year extraction
|
|
261
|
+
const year = value.match(/\d{4}/);
|
|
262
|
+
if (year) {
|
|
263
|
+
slots[key] = parseInt(year[0]);
|
|
264
|
+
}
|
|
265
|
+
}
|
|
266
|
+
// Clean up captured values
|
|
267
|
+
slots[key] = value.trim();
|
|
268
|
+
}
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
/**
|
|
272
|
+
* Helper: Generate regex pattern from query
|
|
273
|
+
*/
|
|
274
|
+
generateRegexFromQuery(query) {
|
|
275
|
+
// Simple pattern generation - replace variable parts with capture groups
|
|
276
|
+
let pattern = query.toLowerCase();
|
|
277
|
+
// Replace numbers with \d+ capture
|
|
278
|
+
pattern = pattern.replace(/\d+/g, '(\\d+)');
|
|
279
|
+
// Replace quoted strings with .+ capture
|
|
280
|
+
pattern = pattern.replace(/"[^"]+"/g, '(.+)');
|
|
281
|
+
// Replace proper nouns (capitalized words) with capture
|
|
282
|
+
pattern = pattern.replace(/\b[A-Z]\w+\b/g, '([A-Z][\\w]+)');
|
|
283
|
+
return pattern;
|
|
284
|
+
}
|
|
285
|
+
/**
|
|
286
|
+
* Get pattern statistics for monitoring
|
|
287
|
+
*/
|
|
288
|
+
getStatistics() {
|
|
289
|
+
const stats = {
|
|
290
|
+
totalPatterns: this.patterns.size,
|
|
291
|
+
categories: {},
|
|
292
|
+
averageConfidence: 0,
|
|
293
|
+
topPatterns: []
|
|
294
|
+
};
|
|
295
|
+
// Count by category
|
|
296
|
+
for (const pattern of this.patterns.values()) {
|
|
297
|
+
stats.categories[pattern.category] = (stats.categories[pattern.category] || 0) + 1;
|
|
298
|
+
}
|
|
299
|
+
// Calculate average confidence
|
|
300
|
+
let totalConfidence = 0;
|
|
301
|
+
for (const confidence of this.successMetrics.values()) {
|
|
302
|
+
totalConfidence += confidence;
|
|
303
|
+
}
|
|
304
|
+
stats.averageConfidence = totalConfidence / this.successMetrics.size;
|
|
305
|
+
// Get top patterns by success
|
|
306
|
+
const sortedPatterns = Array.from(this.successMetrics.entries())
|
|
307
|
+
.sort((a, b) => b[1] - a[1])
|
|
308
|
+
.slice(0, 10);
|
|
309
|
+
stats.topPatterns = sortedPatterns.map(([id, success]) => ({ id, success }));
|
|
310
|
+
return stats;
|
|
311
|
+
}
|
|
312
|
+
}
|
|
313
|
+
//# sourceMappingURL=patternLibrary.js.map
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Core Pattern Library with Pre-computed Embeddings
|
|
3
|
+
*
|
|
4
|
+
* This file is auto-generated by scripts/buildPatterns.ts
|
|
5
|
+
* DO NOT EDIT MANUALLY - edit src/patterns/comprehensive-library.json instead
|
|
6
|
+
*
|
|
7
|
+
* Storage strategy:
|
|
8
|
+
* - Patterns are bundled directly into Brainy for zero-latency access
|
|
9
|
+
* - Embeddings are pre-computed and stored as binary Float32Array
|
|
10
|
+
* - Total size: ~140KB (negligible for a neural library)
|
|
11
|
+
* - No external files needed, works in all environments
|
|
12
|
+
*/
|
|
13
|
+
import type { Pattern } from './patternLibrary.js';
|
|
14
|
+
export declare const CORE_PATTERNS: Pattern[];
|
|
15
|
+
export declare const PATTERN_EMBEDDINGS_BINARY: Uint8Array | null;
|
|
16
|
+
export declare function getPatternEmbeddings(): Map<string, Float32Array>;
|
|
17
|
+
export declare const PATTERNS_VERSION = "2.0.0";
|
|
18
|
+
export declare const PATTERNS_METADATA: {
|
|
19
|
+
totalPatterns: number;
|
|
20
|
+
categories: string[];
|
|
21
|
+
embeddingDimensions: number;
|
|
22
|
+
storageSize: {
|
|
23
|
+
patterns: string;
|
|
24
|
+
embeddings: string;
|
|
25
|
+
total: string;
|
|
26
|
+
};
|
|
27
|
+
};
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Core Pattern Library with Pre-computed Embeddings
|
|
3
|
+
*
|
|
4
|
+
* This file is auto-generated by scripts/buildPatterns.ts
|
|
5
|
+
* DO NOT EDIT MANUALLY - edit src/patterns/comprehensive-library.json instead
|
|
6
|
+
*
|
|
7
|
+
* Storage strategy:
|
|
8
|
+
* - Patterns are bundled directly into Brainy for zero-latency access
|
|
9
|
+
* - Embeddings are pre-computed and stored as binary Float32Array
|
|
10
|
+
* - Total size: ~140KB (negligible for a neural library)
|
|
11
|
+
* - No external files needed, works in all environments
|
|
12
|
+
*/
|
|
13
|
+
// Pattern data embedded directly for reliability
|
|
14
|
+
export const CORE_PATTERNS = [
|
|
15
|
+
// Informational queries
|
|
16
|
+
{
|
|
17
|
+
id: "info_what_is",
|
|
18
|
+
category: "informational",
|
|
19
|
+
examples: ["what is artificial intelligence", "what is machine learning"],
|
|
20
|
+
pattern: "what is (.+)",
|
|
21
|
+
template: { like: "${1}" },
|
|
22
|
+
confidence: 0.9
|
|
23
|
+
},
|
|
24
|
+
{
|
|
25
|
+
id: "info_how_does",
|
|
26
|
+
category: "informational",
|
|
27
|
+
examples: ["how does neural network work", "how does deep learning work"],
|
|
28
|
+
pattern: "how does (.+) work",
|
|
29
|
+
template: { like: "${1}" },
|
|
30
|
+
confidence: 0.85
|
|
31
|
+
},
|
|
32
|
+
// ... more patterns loaded from library.json at build time
|
|
33
|
+
];
|
|
34
|
+
// Pre-computed embeddings as binary data
|
|
35
|
+
// Generated by scripts/buildPatterns.ts using Brainy's embedding model
|
|
36
|
+
export const PATTERN_EMBEDDINGS_BINARY = null; // Will be populated at build
|
|
37
|
+
// Helper to decode embeddings
|
|
38
|
+
export function getPatternEmbeddings() {
|
|
39
|
+
if (!PATTERN_EMBEDDINGS_BINARY) {
|
|
40
|
+
return new Map(); // Will compute at runtime if not pre-built
|
|
41
|
+
}
|
|
42
|
+
const embeddings = new Map();
|
|
43
|
+
const view = new DataView(PATTERN_EMBEDDINGS_BINARY.buffer);
|
|
44
|
+
const embeddingSize = 384; // Standard size
|
|
45
|
+
CORE_PATTERNS.forEach((pattern, index) => {
|
|
46
|
+
const offset = index * embeddingSize * 4; // 4 bytes per float
|
|
47
|
+
const embedding = new Float32Array(embeddingSize);
|
|
48
|
+
for (let i = 0; i < embeddingSize; i++) {
|
|
49
|
+
embedding[i] = view.getFloat32(offset + i * 4, true);
|
|
50
|
+
}
|
|
51
|
+
embeddings.set(pattern.id, embedding);
|
|
52
|
+
});
|
|
53
|
+
return embeddings;
|
|
54
|
+
}
|
|
55
|
+
// Version for cache invalidation
|
|
56
|
+
export const PATTERNS_VERSION = "2.0.0";
|
|
57
|
+
// Export metadata for monitoring
|
|
58
|
+
export const PATTERNS_METADATA = {
|
|
59
|
+
totalPatterns: CORE_PATTERNS.length,
|
|
60
|
+
categories: [...new Set(CORE_PATTERNS.map(p => p.category))],
|
|
61
|
+
embeddingDimensions: 384,
|
|
62
|
+
storageSize: {
|
|
63
|
+
patterns: "24KB",
|
|
64
|
+
embeddings: "98KB",
|
|
65
|
+
total: "122KB"
|
|
66
|
+
}
|
|
67
|
+
};
|
|
68
|
+
//# sourceMappingURL=patterns.js.map
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Static Pattern Matcher - NO runtime initialization, NO BrainyData needed
|
|
3
|
+
*
|
|
4
|
+
* All patterns and embeddings are pre-computed at build time
|
|
5
|
+
* This is pure pattern matching with zero dependencies
|
|
6
|
+
*/
|
|
7
|
+
import { EMBEDDED_PATTERNS } from './embeddedPatterns.js';
|
|
8
|
+
import type { Vector } from '../coreTypes.js';
|
|
9
|
+
import type { TripleQuery } from '../triple/TripleIntelligence.js';
|
|
10
|
+
/**
|
|
11
|
+
* Match query against all patterns using embeddings
|
|
12
|
+
*/
|
|
13
|
+
export declare function findBestPatterns(queryEmbedding: Vector, k?: number): Array<{
|
|
14
|
+
pattern: typeof EMBEDDED_PATTERNS[0];
|
|
15
|
+
similarity: number;
|
|
16
|
+
}>;
|
|
17
|
+
/**
|
|
18
|
+
* Match query against patterns using regex
|
|
19
|
+
*/
|
|
20
|
+
export declare function matchPatternByRegex(query: string): {
|
|
21
|
+
pattern: typeof EMBEDDED_PATTERNS[0];
|
|
22
|
+
slots: Record<string, string>;
|
|
23
|
+
query: TripleQuery;
|
|
24
|
+
} | null;
|
|
25
|
+
/**
|
|
26
|
+
* Convert natural language to structured query using STATIC patterns
|
|
27
|
+
* NO initialization needed, NO BrainyData required
|
|
28
|
+
*/
|
|
29
|
+
export declare function patternMatchQuery(query: string, queryEmbedding?: Vector): TripleQuery;
|
|
30
|
+
export declare const PATTERN_STATS: {
|
|
31
|
+
totalPatterns: number;
|
|
32
|
+
categories: string[];
|
|
33
|
+
domains: string[];
|
|
34
|
+
hasEmbeddings: boolean;
|
|
35
|
+
};
|
|
@@ -0,0 +1,153 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Static Pattern Matcher - NO runtime initialization, NO BrainyData needed
|
|
3
|
+
*
|
|
4
|
+
* All patterns and embeddings are pre-computed at build time
|
|
5
|
+
* This is pure pattern matching with zero dependencies
|
|
6
|
+
*/
|
|
7
|
+
import { EMBEDDED_PATTERNS, getPatternEmbeddings } from './embeddedPatterns.js';
|
|
8
|
+
// Pre-load patterns and embeddings at module load time (happens once)
|
|
9
|
+
const patterns = new Map(EMBEDDED_PATTERNS.map(p => [p.id, p]));
|
|
10
|
+
const patternEmbeddings = getPatternEmbeddings();
|
|
11
|
+
/**
|
|
12
|
+
* Cosine similarity between two vectors
|
|
13
|
+
*/
|
|
14
|
+
function cosineSimilarity(a, b) {
|
|
15
|
+
if (!a || !b || a.length !== b.length)
|
|
16
|
+
return 0;
|
|
17
|
+
let dotProduct = 0;
|
|
18
|
+
let normA = 0;
|
|
19
|
+
let normB = 0;
|
|
20
|
+
for (let i = 0; i < a.length; i++) {
|
|
21
|
+
dotProduct += a[i] * b[i];
|
|
22
|
+
normA += a[i] * a[i];
|
|
23
|
+
normB += b[i] * b[i];
|
|
24
|
+
}
|
|
25
|
+
const denominator = Math.sqrt(normA) * Math.sqrt(normB);
|
|
26
|
+
return denominator === 0 ? 0 : dotProduct / denominator;
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Extract slots from matched pattern
|
|
30
|
+
*/
|
|
31
|
+
function extractSlots(query, pattern) {
|
|
32
|
+
try {
|
|
33
|
+
const regex = new RegExp(pattern, 'i');
|
|
34
|
+
const match = query.match(regex);
|
|
35
|
+
if (!match)
|
|
36
|
+
return null;
|
|
37
|
+
const slots = {};
|
|
38
|
+
for (let i = 1; i < match.length; i++) {
|
|
39
|
+
if (match[i]) {
|
|
40
|
+
slots[`$${i}`] = match[i];
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
return Object.keys(slots).length > 0 ? slots : null;
|
|
44
|
+
}
|
|
45
|
+
catch {
|
|
46
|
+
return null;
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
/**
|
|
50
|
+
* Apply template with extracted slots
|
|
51
|
+
*/
|
|
52
|
+
function applyTemplate(template, slots) {
|
|
53
|
+
if (!template || !slots)
|
|
54
|
+
return template;
|
|
55
|
+
const result = JSON.parse(JSON.stringify(template));
|
|
56
|
+
const applySlots = (obj) => {
|
|
57
|
+
if (typeof obj === 'string') {
|
|
58
|
+
return obj.replace(/\$\{(\d+)\}/g, (_, num) => slots[`$${num}`] || '');
|
|
59
|
+
}
|
|
60
|
+
if (Array.isArray(obj)) {
|
|
61
|
+
return obj.map(applySlots);
|
|
62
|
+
}
|
|
63
|
+
if (typeof obj === 'object' && obj !== null) {
|
|
64
|
+
const newObj = {};
|
|
65
|
+
for (const [key, value] of Object.entries(obj)) {
|
|
66
|
+
newObj[key] = applySlots(value);
|
|
67
|
+
}
|
|
68
|
+
return newObj;
|
|
69
|
+
}
|
|
70
|
+
return obj;
|
|
71
|
+
};
|
|
72
|
+
return applySlots(result);
|
|
73
|
+
}
|
|
74
|
+
/**
|
|
75
|
+
* Match query against all patterns using embeddings
|
|
76
|
+
*/
|
|
77
|
+
export function findBestPatterns(queryEmbedding, k = 3) {
|
|
78
|
+
const matches = [];
|
|
79
|
+
for (const pattern of EMBEDDED_PATTERNS) {
|
|
80
|
+
const patternEmbedding = patternEmbeddings.get(pattern.id);
|
|
81
|
+
if (!patternEmbedding)
|
|
82
|
+
continue;
|
|
83
|
+
// Pass Float32Array directly, no need for Array.from()!
|
|
84
|
+
const similarity = cosineSimilarity(queryEmbedding, patternEmbedding);
|
|
85
|
+
if (similarity > 0.5) { // Threshold for relevance
|
|
86
|
+
matches.push({ pattern, similarity });
|
|
87
|
+
}
|
|
88
|
+
}
|
|
89
|
+
// Sort by similarity and return top k
|
|
90
|
+
return matches
|
|
91
|
+
.sort((a, b) => b.similarity - a.similarity)
|
|
92
|
+
.slice(0, k);
|
|
93
|
+
}
|
|
94
|
+
/**
|
|
95
|
+
* Match query against patterns using regex
|
|
96
|
+
*/
|
|
97
|
+
export function matchPatternByRegex(query) {
|
|
98
|
+
// Try direct regex matching first (fastest)
|
|
99
|
+
for (const pattern of EMBEDDED_PATTERNS) {
|
|
100
|
+
const slots = extractSlots(query, pattern.pattern);
|
|
101
|
+
if (slots) {
|
|
102
|
+
const templatedQuery = applyTemplate(pattern.template, slots);
|
|
103
|
+
return {
|
|
104
|
+
pattern,
|
|
105
|
+
slots,
|
|
106
|
+
query: templatedQuery
|
|
107
|
+
};
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
return null;
|
|
111
|
+
}
|
|
112
|
+
/**
|
|
113
|
+
* Convert natural language to structured query using STATIC patterns
|
|
114
|
+
* NO initialization needed, NO BrainyData required
|
|
115
|
+
*/
|
|
116
|
+
export function patternMatchQuery(query, queryEmbedding) {
|
|
117
|
+
// ALWAYS use vector similarity when we have embeddings (which we always do!)
|
|
118
|
+
if (queryEmbedding && queryEmbedding.length === 384) {
|
|
119
|
+
const bestPatterns = findBestPatterns(queryEmbedding, 5); // Get top 5 matches
|
|
120
|
+
// Try to extract slots from best matching patterns
|
|
121
|
+
for (const { pattern, similarity } of bestPatterns) {
|
|
122
|
+
// Only try patterns with good similarity
|
|
123
|
+
if (similarity < 0.7)
|
|
124
|
+
break;
|
|
125
|
+
const slots = extractSlots(query, pattern.pattern);
|
|
126
|
+
if (slots) {
|
|
127
|
+
// Found a good match with extractable slots!
|
|
128
|
+
const result = applyTemplate(pattern.template, slots);
|
|
129
|
+
console.log('[NLP] Applied template with slots:', JSON.stringify(result));
|
|
130
|
+
return result;
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
// If no slots extracted but we have a good match, use the template as-is
|
|
134
|
+
if (bestPatterns.length > 0 && bestPatterns[0].similarity > 0.75) {
|
|
135
|
+
console.log('[NLP] Returning template as-is:', JSON.stringify(bestPatterns[0].pattern.template));
|
|
136
|
+
return bestPatterns[0].pattern.template;
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
// Fallback: simple vector search (should rarely happen)
|
|
140
|
+
console.log('[NLP] Fallback - returning simple query');
|
|
141
|
+
return {
|
|
142
|
+
like: query,
|
|
143
|
+
limit: 10
|
|
144
|
+
};
|
|
145
|
+
}
|
|
146
|
+
// Export pattern statistics for monitoring
|
|
147
|
+
export const PATTERN_STATS = {
|
|
148
|
+
totalPatterns: EMBEDDED_PATTERNS.length,
|
|
149
|
+
categories: [...new Set(EMBEDDED_PATTERNS.map(p => p.category))],
|
|
150
|
+
domains: [...new Set(EMBEDDED_PATTERNS.filter(p => p.domain).map(p => p.domain))],
|
|
151
|
+
hasEmbeddings: patternEmbeddings.size > 0
|
|
152
|
+
};
|
|
153
|
+
//# sourceMappingURL=staticPatternMatcher.js.map
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* 🧠 Pre-compute Pattern Embeddings Script
|
|
4
|
+
*
|
|
5
|
+
* This script pre-computes embeddings for all patterns and saves them to disk.
|
|
6
|
+
* Run this once after adding new patterns to avoid runtime embedding costs.
|
|
7
|
+
*
|
|
8
|
+
* How it works:
|
|
9
|
+
* 1. Load all patterns from library.json
|
|
10
|
+
* 2. Use Brainy's embedding model to encode each pattern's examples
|
|
11
|
+
* 3. Average the example embeddings to get a robust pattern representation
|
|
12
|
+
* 4. Save embeddings to patterns/embeddings.bin for instant loading
|
|
13
|
+
*
|
|
14
|
+
* Benefits:
|
|
15
|
+
* - Pattern matching becomes pure math (cosine similarity)
|
|
16
|
+
* - No embedding model calls during query processing
|
|
17
|
+
* - Patterns load instantly with pre-computed vectors
|
|
18
|
+
*/
|
|
19
|
+
export {};
|