@stackmemoryai/stackmemory 0.5.0 → 0.5.2
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/dist/cli/commands/config.js +81 -0
- package/dist/cli/commands/config.js.map +2 -2
- package/dist/cli/commands/decision.js +262 -0
- package/dist/cli/commands/decision.js.map +7 -0
- package/dist/cli/commands/handoff.js +87 -24
- package/dist/cli/commands/handoff.js.map +3 -3
- package/dist/cli/commands/service.js +684 -0
- package/dist/cli/commands/service.js.map +7 -0
- package/dist/cli/commands/sweep.js +311 -0
- package/dist/cli/commands/sweep.js.map +7 -0
- package/dist/cli/index.js +98 -4
- package/dist/cli/index.js.map +2 -2
- package/dist/cli/streamlined-cli.js +144 -0
- package/dist/cli/streamlined-cli.js.map +7 -0
- package/dist/core/config/storage-config.js +111 -0
- package/dist/core/config/storage-config.js.map +7 -0
- package/dist/core/events/event-bus.js +110 -0
- package/dist/core/events/event-bus.js.map +7 -0
- package/dist/core/plugins/plugin-interface.js +87 -0
- package/dist/core/plugins/plugin-interface.js.map +7 -0
- package/dist/core/session/enhanced-handoff.js +654 -0
- package/dist/core/session/enhanced-handoff.js.map +7 -0
- package/dist/core/storage/simplified-storage.js +328 -0
- package/dist/core/storage/simplified-storage.js.map +7 -0
- package/dist/daemon/session-daemon.js +308 -0
- package/dist/daemon/session-daemon.js.map +7 -0
- package/dist/plugins/linear/index.js +166 -0
- package/dist/plugins/linear/index.js.map +7 -0
- package/dist/plugins/loader.js +57 -0
- package/dist/plugins/loader.js.map +7 -0
- package/dist/plugins/plugin-interface.js +67 -0
- package/dist/plugins/plugin-interface.js.map +7 -0
- package/dist/plugins/ralph/simple-ralph-plugin.js +305 -0
- package/dist/plugins/ralph/simple-ralph-plugin.js.map +7 -0
- package/dist/plugins/ralph/use-cases/code-generator.js +151 -0
- package/dist/plugins/ralph/use-cases/code-generator.js.map +7 -0
- package/dist/plugins/ralph/use-cases/test-generator.js +201 -0
- package/dist/plugins/ralph/use-cases/test-generator.js.map +7 -0
- package/dist/skills/repo-ingestion-skill.js +54 -10
- package/dist/skills/repo-ingestion-skill.js.map +2 -2
- package/package.json +4 -8
- package/scripts/archive/check-all-duplicates.ts +2 -2
- package/scripts/archive/merge-linear-duplicates.ts +6 -4
- package/scripts/install-claude-hooks-auto.js +72 -15
- package/scripts/measure-handoff-impact.mjs +395 -0
- package/scripts/measure-handoff-impact.ts +450 -0
- package/templates/claude-hooks/on-startup.js +200 -19
- package/templates/services/com.stackmemory.guardian.plist +59 -0
- package/templates/services/stackmemory-guardian.service +41 -0
- package/scripts/testing/results/real-performance-results.json +0 -90
- package/scripts/testing/test-tier-migration.js +0 -100
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
class BasePlugin {
|
|
2
|
+
dependencies;
|
|
3
|
+
context;
|
|
4
|
+
status = { state: "uninitialized" };
|
|
5
|
+
metrics = {
|
|
6
|
+
eventsEmitted: 0,
|
|
7
|
+
eventsReceived: 0,
|
|
8
|
+
errors: 0
|
|
9
|
+
};
|
|
10
|
+
startTime;
|
|
11
|
+
async initialize(context) {
|
|
12
|
+
this.context = context;
|
|
13
|
+
this.status = { state: "initialized" };
|
|
14
|
+
await this.onInitialize();
|
|
15
|
+
}
|
|
16
|
+
async start() {
|
|
17
|
+
this.status = { state: "starting" };
|
|
18
|
+
this.startTime = Date.now();
|
|
19
|
+
await this.onStart();
|
|
20
|
+
this.status = { state: "running", lastActivity: Date.now() };
|
|
21
|
+
}
|
|
22
|
+
async stop() {
|
|
23
|
+
this.status = { state: "stopping" };
|
|
24
|
+
await this.onStop();
|
|
25
|
+
this.status = { state: "stopped" };
|
|
26
|
+
}
|
|
27
|
+
async shutdown() {
|
|
28
|
+
if (this.status.state === "running") {
|
|
29
|
+
await this.stop();
|
|
30
|
+
}
|
|
31
|
+
await this.onShutdown();
|
|
32
|
+
this.status = { state: "uninitialized" };
|
|
33
|
+
}
|
|
34
|
+
getStatus() {
|
|
35
|
+
return { ...this.status };
|
|
36
|
+
}
|
|
37
|
+
getMetrics() {
|
|
38
|
+
return {
|
|
39
|
+
...this.metrics,
|
|
40
|
+
startTime: this.startTime,
|
|
41
|
+
uptime: this.startTime ? Date.now() - this.startTime : 0
|
|
42
|
+
};
|
|
43
|
+
}
|
|
44
|
+
validateConfig(config) {
|
|
45
|
+
const errors = [];
|
|
46
|
+
const warnings = [];
|
|
47
|
+
if (config.name !== this.name) {
|
|
48
|
+
errors.push(`Config name '${config.name}' doesn't match plugin name '${this.name}'`);
|
|
49
|
+
}
|
|
50
|
+
const customValidation = this.onValidateConfig(config);
|
|
51
|
+
if (customValidation.errors) errors.push(...customValidation.errors);
|
|
52
|
+
if (customValidation.warnings) warnings.push(...customValidation.warnings);
|
|
53
|
+
return {
|
|
54
|
+
valid: errors.length === 0,
|
|
55
|
+
errors: errors.length > 0 ? errors : void 0,
|
|
56
|
+
warnings: warnings.length > 0 ? warnings : void 0
|
|
57
|
+
};
|
|
58
|
+
}
|
|
59
|
+
emit(eventType, data) {
|
|
60
|
+
if (!this.context) throw new Error("Plugin not initialized");
|
|
61
|
+
this.context.eventBus.emit({
|
|
62
|
+
type: eventType,
|
|
63
|
+
source: this.name,
|
|
64
|
+
data
|
|
65
|
+
});
|
|
66
|
+
this.metrics.eventsEmitted++;
|
|
67
|
+
this.status.lastActivity = Date.now();
|
|
68
|
+
}
|
|
69
|
+
on(eventType, handler) {
|
|
70
|
+
if (!this.context) throw new Error("Plugin not initialized");
|
|
71
|
+
this.context.eventBus.on(eventType, async (event) => {
|
|
72
|
+
this.metrics.eventsReceived++;
|
|
73
|
+
this.status.lastActivity = Date.now();
|
|
74
|
+
try {
|
|
75
|
+
await handler(event);
|
|
76
|
+
} catch (error) {
|
|
77
|
+
this.metrics.errors++;
|
|
78
|
+
this.status.error = error;
|
|
79
|
+
console.error(`Plugin ${this.name} error handling ${eventType}:`, error);
|
|
80
|
+
}
|
|
81
|
+
});
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
export {
|
|
85
|
+
BasePlugin
|
|
86
|
+
};
|
|
87
|
+
//# sourceMappingURL=plugin-interface.js.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../src/core/plugins/plugin-interface.ts"],
|
|
4
|
+
"sourcesContent": ["/**\n * Plugin Interface - Defines contract for all StackMemory plugins\n * Enables modular architecture with clear boundaries\n */\n\nimport { EventBus } from '../events/event-bus.js';\n\nexport interface PluginConfig {\n name: string;\n version: string;\n enabled: boolean;\n options?: Record<string, any>;\n}\n\nexport interface PluginContext {\n eventBus: EventBus;\n config: PluginConfig;\n dataDir: string;\n getRepository<T>(name: string): T;\n registerRepository(name: string, repository: any): void;\n}\n\nexport interface Plugin {\n readonly name: string;\n readonly version: string;\n readonly description: string;\n readonly dependencies?: string[];\n\n initialize(context: PluginContext): Promise<void>;\n start(): Promise<void>;\n stop(): Promise<void>;\n shutdown(): Promise<void>;\n \n getStatus(): PluginStatus;\n getMetrics(): PluginMetrics;\n validateConfig(config: PluginConfig): ValidationResult;\n}\n\nexport interface PluginStatus {\n state: 'uninitialized' | 'initialized' | 'starting' | 'running' | 'stopping' | 'stopped' | 'error';\n message?: string;\n lastActivity?: number;\n error?: Error;\n}\n\nexport interface PluginMetrics {\n startTime?: number;\n uptime?: number;\n eventsEmitted: number;\n eventsReceived: number;\n errors: number;\n custom?: Record<string, number>;\n}\n\nexport interface ValidationResult {\n valid: boolean;\n errors?: string[];\n warnings?: string[];\n}\n\nexport abstract class BasePlugin implements Plugin {\n abstract readonly name: string;\n abstract readonly version: string;\n abstract readonly description: string;\n readonly dependencies?: string[];\n\n protected context?: PluginContext;\n protected status: PluginStatus = { state: 'uninitialized' };\n protected metrics: PluginMetrics = {\n eventsEmitted: 0,\n eventsReceived: 0,\n errors: 0\n };\n protected startTime?: number;\n\n async initialize(context: PluginContext): Promise<void> {\n this.context = context;\n this.status = { state: 'initialized' };\n await this.onInitialize();\n }\n\n async start(): Promise<void> {\n this.status = { state: 'starting' };\n this.startTime = Date.now();\n await this.onStart();\n this.status = { state: 'running', lastActivity: Date.now() };\n }\n\n async stop(): Promise<void> {\n this.status = { state: 'stopping' };\n await this.onStop();\n this.status = { state: 'stopped' };\n }\n\n async shutdown(): Promise<void> {\n if (this.status.state === 'running') {\n await this.stop();\n }\n await this.onShutdown();\n this.status = { state: 'uninitialized' };\n }\n\n getStatus(): PluginStatus {\n return { ...this.status };\n }\n\n getMetrics(): PluginMetrics {\n return {\n ...this.metrics,\n startTime: this.startTime,\n uptime: this.startTime ? Date.now() - this.startTime : 0\n };\n }\n\n validateConfig(config: PluginConfig): ValidationResult {\n const errors: string[] = [];\n const warnings: string[] = [];\n\n if (config.name !== this.name) {\n errors.push(`Config name '${config.name}' doesn't match plugin name '${this.name}'`);\n }\n\n const customValidation = this.onValidateConfig(config);\n if (customValidation.errors) errors.push(...customValidation.errors);\n if (customValidation.warnings) warnings.push(...customValidation.warnings);\n\n return {\n valid: errors.length === 0,\n errors: errors.length > 0 ? errors : undefined,\n warnings: warnings.length > 0 ? warnings : undefined\n };\n }\n\n protected emit(eventType: string, data: Record<string, any>): void {\n if (!this.context) throw new Error('Plugin not initialized');\n \n this.context.eventBus.emit({\n type: eventType,\n source: this.name,\n data\n });\n this.metrics.eventsEmitted++;\n this.status.lastActivity = Date.now();\n }\n\n protected on(eventType: string, handler: (event: any) => void | Promise<void>): void {\n if (!this.context) throw new Error('Plugin not initialized');\n \n this.context.eventBus.on(eventType, async (event) => {\n this.metrics.eventsReceived++;\n this.status.lastActivity = Date.now();\n try {\n await handler(event);\n } catch (error) {\n this.metrics.errors++;\n this.status.error = error as Error;\n console.error(`Plugin ${this.name} error handling ${eventType}:`, error);\n }\n });\n }\n\n // Hooks for subclasses\n protected abstract onInitialize(): Promise<void>;\n protected abstract onStart(): Promise<void>;\n protected abstract onStop(): Promise<void>;\n protected abstract onShutdown(): Promise<void>;\n protected abstract onValidateConfig(config: PluginConfig): ValidationResult;\n}"],
|
|
5
|
+
"mappings": "AA4DO,MAAe,WAA6B;AAAA,EAIxC;AAAA,EAEC;AAAA,EACA,SAAuB,EAAE,OAAO,gBAAgB;AAAA,EAChD,UAAyB;AAAA,IACjC,eAAe;AAAA,IACf,gBAAgB;AAAA,IAChB,QAAQ;AAAA,EACV;AAAA,EACU;AAAA,EAEV,MAAM,WAAW,SAAuC;AACtD,SAAK,UAAU;AACf,SAAK,SAAS,EAAE,OAAO,cAAc;AACrC,UAAM,KAAK,aAAa;AAAA,EAC1B;AAAA,EAEA,MAAM,QAAuB;AAC3B,SAAK,SAAS,EAAE,OAAO,WAAW;AAClC,SAAK,YAAY,KAAK,IAAI;AAC1B,UAAM,KAAK,QAAQ;AACnB,SAAK,SAAS,EAAE,OAAO,WAAW,cAAc,KAAK,IAAI,EAAE;AAAA,EAC7D;AAAA,EAEA,MAAM,OAAsB;AAC1B,SAAK,SAAS,EAAE,OAAO,WAAW;AAClC,UAAM,KAAK,OAAO;AAClB,SAAK,SAAS,EAAE,OAAO,UAAU;AAAA,EACnC;AAAA,EAEA,MAAM,WAA0B;AAC9B,QAAI,KAAK,OAAO,UAAU,WAAW;AACnC,YAAM,KAAK,KAAK;AAAA,IAClB;AACA,UAAM,KAAK,WAAW;AACtB,SAAK,SAAS,EAAE,OAAO,gBAAgB;AAAA,EACzC;AAAA,EAEA,YAA0B;AACxB,WAAO,EAAE,GAAG,KAAK,OAAO;AAAA,EAC1B;AAAA,EAEA,aAA4B;AAC1B,WAAO;AAAA,MACL,GAAG,KAAK;AAAA,MACR,WAAW,KAAK;AAAA,MAChB,QAAQ,KAAK,YAAY,KAAK,IAAI,IAAI,KAAK,YAAY;AAAA,IACzD;AAAA,EACF;AAAA,EAEA,eAAe,QAAwC;AACrD,UAAM,SAAmB,CAAC;AAC1B,UAAM,WAAqB,CAAC;AAE5B,QAAI,OAAO,SAAS,KAAK,MAAM;AAC7B,aAAO,KAAK,gBAAgB,OAAO,IAAI,gCAAgC,KAAK,IAAI,GAAG;AAAA,IACrF;AAEA,UAAM,mBAAmB,KAAK,iBAAiB,MAAM;AACrD,QAAI,iBAAiB,OAAQ,QAAO,KAAK,GAAG,iBAAiB,MAAM;AACnE,QAAI,iBAAiB,SAAU,UAAS,KAAK,GAAG,iBAAiB,QAAQ;AAEzE,WAAO;AAAA,MACL,OAAO,OAAO,WAAW;AAAA,MACzB,QAAQ,OAAO,SAAS,IAAI,SAAS;AAAA,MACrC,UAAU,SAAS,SAAS,IAAI,WAAW;AAAA,IAC7C;AAAA,EACF;AAAA,EAEU,KAAK,WAAmB,MAAiC;AACjE,QAAI,CAAC,KAAK,QAAS,OAAM,IAAI,MAAM,wBAAwB;AAE3D,SAAK,QAAQ,SAAS,KAAK;AAAA,MACzB,MAAM;AAAA,MACN,QAAQ,KAAK;AAAA,MACb;AAAA,IACF,CAAC;AACD,SAAK,QAAQ;AACb,SAAK,OAAO,eAAe,KAAK,IAAI;AAAA,EACtC;AAAA,EAEU,GAAG,WAAmB,SAAqD;AACnF,QAAI,CAAC,KAAK,QAAS,OAAM,IAAI,MAAM,wBAAwB;AAE3D,SAAK,QAAQ,SAAS,GAAG,WAAW,OAAO,UAAU;AACnD,WAAK,QAAQ;AACb,WAAK,OAAO,eAAe,KAAK,IAAI;AACpC,UAAI;AACF,cAAM,QAAQ,KAAK;AAAA,MACrB,SAAS,OAAO;AACd,aAAK,QAAQ;AACb,aAAK,OAAO,QAAQ;AACpB,gBAAQ,MAAM,UAAU,KAAK,IAAI,mBAAmB,SAAS,KAAK,KAAK;AAAA,MACzE;AAAA,IACF,CAAC;AAAA,EACH;AAQF;",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|