Spaces:
Paused
Paused
File size: 3,342 Bytes
34367da | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 | /**
* ProjectMemory - In-memory project lifecycle tracking
*
* Uses in-memory storage for development.
* In production, events are also sent to Neo4j via EventBus.
*/
import { eventBus } from '../../mcp/EventBus.js';
export interface LifecycleEvent {
id?: number;
eventType: 'build' | 'test' | 'deploy' | 'feature' | 'other';
status: 'success' | 'failure' | 'in_progress';
details: any;
createdAt?: string;
}
export interface ProjectFeature {
id?: number;
name: string;
description: string;
status: 'planned' | 'in_progress' | 'completed' | 'deprecated';
createdAt?: string;
updatedAt?: string;
}
class ProjectMemoryService {
private events: LifecycleEvent[] = [];
private features: Map<string, ProjectFeature> = new Map();
private eventIdCounter = 1;
private featureIdCounter = 1;
constructor() {
this.setupEventListeners();
console.log('📚 ProjectMemory initialized (in-memory mode)');
}
private setupEventListeners() {
// Listen for system alerts and log them as 'other' events
eventBus.onEvent('system.alert', (event) => {
this.logLifecycleEvent({
eventType: 'other',
status: 'failure', // Alerts are usually bad
details: { source: 'system.alert', payload: event.payload }
});
});
}
public logLifecycleEvent(event: LifecycleEvent): void {
const now = new Date().toISOString();
const newEvent: LifecycleEvent = {
...event,
id: this.eventIdCounter++,
createdAt: now
};
this.events.unshift(newEvent); // Add to front for newest-first ordering
// Keep only last 1000 events in memory
if (this.events.length > 1000) {
this.events = this.events.slice(0, 1000);
}
console.log(`[ProjectMemory] Logged event: ${event.eventType} - ${event.status}`);
}
public getLifecycleEvents(limit = 50): LifecycleEvent[] {
return this.events.slice(0, limit);
}
public addFeature(feature: ProjectFeature): void {
const now = new Date().toISOString();
const newFeature: ProjectFeature = {
...feature,
id: this.featureIdCounter++,
createdAt: now,
updatedAt: now
};
this.features.set(feature.name, newFeature);
console.log(`[ProjectMemory] Added feature: ${feature.name}`);
}
public getFeatures(): ProjectFeature[] {
return Array.from(this.features.values())
.sort((a, b) => (b.updatedAt || '').localeCompare(a.updatedAt || ''));
}
public updateFeatureStatus(name: string, status: ProjectFeature['status']): void {
const existing = this.features.get(name);
if (existing) {
existing.status = status;
existing.updatedAt = new Date().toISOString();
} else {
this.addFeature({
name,
description: name,
status
});
}
console.log(`[ProjectMemory] Updated feature ${name} to ${status}`);
}
}
export const projectMemory = new ProjectMemoryService();
|