chore: recovery checkpoint - v3.0 API successfully recovered
CRITICAL CHECKPOINT - DO NOT PUSH TO GITHUB Recovery Status: - Successfully recovered brainy.ts from compiled JavaScript - All core v3.0 API methods functional (add, get, update, delete, relate, find, etc.) - Neural subsystem intact (562KB embedded patterns, NLP working) - Augmentation pipeline operational (20+ augmentations) - HNSW clustering system complete - Triple Intelligence compiled (needs constructor fix) - Test suite validates functionality Changes preserved: - 898 files with changes from last 3 days - 144,475 insertions - All augmentation improvements - All test coverage enhancements - Complete v3.0 feature set This is a LOCAL checkpoint only - contains recovered work after corruption incident. Created backup in .backups/brainy-full-20250910-151314.tar.gz Branch: recovery-checkpoint-20250910-151433 Date: Wed Sep 10 03:18:04 PM PDT 2025
This commit is contained in:
parent
f65455fb22
commit
8ff382ca3b
895 changed files with 143654 additions and 28268 deletions
|
|
@ -0,0 +1,265 @@
|
|||
/**
|
||||
* Distributed Cache Synchronization
|
||||
* Provides cache coherence across multiple Brainy instances
|
||||
*/
|
||||
import { EventEmitter } from 'events';
|
||||
/**
|
||||
* Distributed Cache Synchronizer
|
||||
*/
|
||||
export class CacheSync extends EventEmitter {
|
||||
constructor(config) {
|
||||
super();
|
||||
this.localCache = new Map();
|
||||
this.versionVector = new Map();
|
||||
this.syncQueue = [];
|
||||
this.isRunning = false;
|
||||
this.nodeId = config.nodeId;
|
||||
this.syncInterval = config.syncInterval || 1000;
|
||||
this.maxSyncBatchSize = config.maxSyncBatchSize || 100;
|
||||
}
|
||||
/**
|
||||
* Start cache synchronization
|
||||
*/
|
||||
start() {
|
||||
if (this.isRunning)
|
||||
return;
|
||||
this.isRunning = true;
|
||||
this.startSyncTimer();
|
||||
this.emit('started', { nodeId: this.nodeId });
|
||||
}
|
||||
/**
|
||||
* Stop cache synchronization
|
||||
*/
|
||||
stop() {
|
||||
if (!this.isRunning)
|
||||
return;
|
||||
this.isRunning = false;
|
||||
if (this.syncTimer) {
|
||||
clearInterval(this.syncTimer);
|
||||
this.syncTimer = undefined;
|
||||
}
|
||||
this.emit('stopped', { nodeId: this.nodeId });
|
||||
}
|
||||
/**
|
||||
* Get a value from cache
|
||||
*/
|
||||
get(key) {
|
||||
const entry = this.localCache.get(key);
|
||||
if (!entry)
|
||||
return undefined;
|
||||
// Check TTL
|
||||
if (entry.ttl && Date.now() - entry.timestamp > entry.ttl) {
|
||||
this.localCache.delete(key);
|
||||
return undefined;
|
||||
}
|
||||
return entry.value;
|
||||
}
|
||||
/**
|
||||
* Set a value in cache and propagate
|
||||
*/
|
||||
set(key, value, ttl) {
|
||||
const version = this.incrementVersion(key);
|
||||
const entry = {
|
||||
key,
|
||||
value,
|
||||
version,
|
||||
timestamp: Date.now(),
|
||||
ttl,
|
||||
nodeId: this.nodeId
|
||||
};
|
||||
this.localCache.set(key, entry);
|
||||
// Queue for sync
|
||||
this.queueSync('update', [entry]);
|
||||
}
|
||||
/**
|
||||
* Delete a value from cache and propagate
|
||||
*/
|
||||
delete(key) {
|
||||
const existed = this.localCache.has(key);
|
||||
if (existed) {
|
||||
const version = this.incrementVersion(key);
|
||||
this.localCache.delete(key);
|
||||
// Queue deletion for sync
|
||||
this.queueSync('delete', [{
|
||||
key,
|
||||
value: null,
|
||||
version,
|
||||
timestamp: Date.now(),
|
||||
nodeId: this.nodeId
|
||||
}]);
|
||||
}
|
||||
return existed;
|
||||
}
|
||||
/**
|
||||
* Invalidate a cache entry across all nodes
|
||||
*/
|
||||
invalidate(key) {
|
||||
const version = this.incrementVersion(key);
|
||||
this.localCache.delete(key);
|
||||
// Queue invalidation
|
||||
this.queueSync('invalidate', [{
|
||||
key,
|
||||
value: null,
|
||||
version,
|
||||
timestamp: Date.now(),
|
||||
nodeId: this.nodeId
|
||||
}]);
|
||||
}
|
||||
/**
|
||||
* Clear all cache entries
|
||||
*/
|
||||
clear() {
|
||||
const entries = [];
|
||||
for (const key of this.localCache.keys()) {
|
||||
const version = this.incrementVersion(key);
|
||||
entries.push({
|
||||
key,
|
||||
value: null,
|
||||
version,
|
||||
timestamp: Date.now(),
|
||||
nodeId: this.nodeId
|
||||
});
|
||||
}
|
||||
this.localCache.clear();
|
||||
if (entries.length > 0) {
|
||||
this.queueSync('delete', entries);
|
||||
}
|
||||
}
|
||||
/**
|
||||
* Handle incoming sync message from another node
|
||||
*/
|
||||
handleSyncMessage(message) {
|
||||
if (message.source === this.nodeId)
|
||||
return; // Ignore own messages
|
||||
for (const entry of message.entries) {
|
||||
this.handleRemoteEntry(message.type, entry);
|
||||
}
|
||||
this.emit('synced', {
|
||||
type: message.type,
|
||||
entries: message.entries.length,
|
||||
source: message.source
|
||||
});
|
||||
}
|
||||
/**
|
||||
* Handle a remote cache entry
|
||||
*/
|
||||
handleRemoteEntry(type, entry) {
|
||||
const localEntry = this.localCache.get(entry.key);
|
||||
const localVersion = this.versionVector.get(entry.key) || 0;
|
||||
// Version vector check - only accept if remote version is newer
|
||||
if (entry.version <= localVersion) {
|
||||
return; // Our version is newer or same, ignore
|
||||
}
|
||||
// Update version vector
|
||||
this.versionVector.set(entry.key, entry.version);
|
||||
switch (type) {
|
||||
case 'update':
|
||||
case 'batch':
|
||||
// Update local cache with remote value
|
||||
this.localCache.set(entry.key, entry);
|
||||
break;
|
||||
case 'delete':
|
||||
case 'invalidate':
|
||||
// Remove from local cache
|
||||
this.localCache.delete(entry.key);
|
||||
break;
|
||||
}
|
||||
}
|
||||
/**
|
||||
* Queue a sync message
|
||||
*/
|
||||
queueSync(type, entries) {
|
||||
const message = {
|
||||
type,
|
||||
entries,
|
||||
source: this.nodeId,
|
||||
timestamp: Date.now()
|
||||
};
|
||||
this.syncQueue.push(message);
|
||||
// If queue is getting large, sync immediately
|
||||
if (this.syncQueue.length >= this.maxSyncBatchSize) {
|
||||
this.performSync();
|
||||
}
|
||||
}
|
||||
/**
|
||||
* Start sync timer
|
||||
*/
|
||||
startSyncTimer() {
|
||||
this.syncTimer = setInterval(() => {
|
||||
this.performSync();
|
||||
}, this.syncInterval);
|
||||
}
|
||||
/**
|
||||
* Perform sync operation
|
||||
*/
|
||||
performSync() {
|
||||
if (this.syncQueue.length === 0)
|
||||
return;
|
||||
// Batch multiple messages if possible
|
||||
const messages = this.syncQueue.splice(0, this.maxSyncBatchSize);
|
||||
if (messages.length === 1) {
|
||||
// Single message
|
||||
this.emit('sync', messages[0]);
|
||||
}
|
||||
else {
|
||||
// Batch multiple messages
|
||||
const batchedEntries = [];
|
||||
for (const msg of messages) {
|
||||
batchedEntries.push(...msg.entries);
|
||||
}
|
||||
const batchMessage = {
|
||||
type: 'batch',
|
||||
entries: batchedEntries,
|
||||
source: this.nodeId,
|
||||
timestamp: Date.now()
|
||||
};
|
||||
this.emit('sync', batchMessage);
|
||||
}
|
||||
}
|
||||
/**
|
||||
* Increment version for a key
|
||||
*/
|
||||
incrementVersion(key) {
|
||||
const current = this.versionVector.get(key) || 0;
|
||||
const next = current + 1;
|
||||
this.versionVector.set(key, next);
|
||||
return next;
|
||||
}
|
||||
/**
|
||||
* Get cache statistics
|
||||
*/
|
||||
getStats() {
|
||||
// Estimate memory usage (rough approximation)
|
||||
let memoryUsage = 0;
|
||||
for (const entry of this.localCache.values()) {
|
||||
memoryUsage += JSON.stringify(entry).length;
|
||||
}
|
||||
return {
|
||||
entries: this.localCache.size,
|
||||
pendingSync: this.syncQueue.length,
|
||||
versionedKeys: this.versionVector.size,
|
||||
memoryUsage
|
||||
};
|
||||
}
|
||||
/**
|
||||
* Get cache entries for debugging
|
||||
*/
|
||||
getEntries() {
|
||||
return Array.from(this.localCache.values());
|
||||
}
|
||||
/**
|
||||
* Merge cache state from another node (for recovery)
|
||||
*/
|
||||
mergeState(entries) {
|
||||
for (const entry of entries) {
|
||||
this.handleRemoteEntry('update', entry);
|
||||
}
|
||||
}
|
||||
}
|
||||
/**
|
||||
* Create a cache sync instance
|
||||
*/
|
||||
export function createCacheSync(config) {
|
||||
return new CacheSync(config);
|
||||
}
|
||||
//# sourceMappingURL=cacheSync.js.map
|
||||
Loading…
Add table
Add a link
Reference in a new issue