@slorenzot/memento-cli 0.2.0 → 0.3.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/dist/CLI.d.ts ADDED
@@ -0,0 +1,12 @@
1
+ export declare class CLI {
2
+ private program;
3
+ private memory;
4
+ private activeSessionId;
5
+ private projectId;
6
+ constructor();
7
+ private setupCommands;
8
+ private getOrCreateSessionId;
9
+ run(argv?: string[]): Promise<void>;
10
+ close(): void;
11
+ }
12
+ //# sourceMappingURL=CLI.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"CLI.d.ts","sourceRoot":"","sources":["../src/CLI.ts"],"names":[],"mappings":"AAKA,qBAAa,GAAG;IACd,OAAO,CAAC,OAAO,CAAU;IACzB,OAAO,CAAC,MAAM,CAAe;IAC7B,OAAO,CAAC,eAAe,CAAuB;IAC9C,OAAO,CAAC,SAAS,CAAS;;IAY1B,OAAO,CAAC,aAAa;YAsJP,oBAAoB;IAa5B,GAAG,CAAC,IAAI,GAAE,MAAM,EAAiB;IAIvC,KAAK;CAGN"}
package/dist/CLI.js ADDED
@@ -0,0 +1,178 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.CLI = void 0;
4
+ const commander_1 = require("commander");
5
+ const memento_core_1 = require("@slorenzot/memento-core");
6
+ // @ts-ignore
7
+ class CLI {
8
+ program;
9
+ memory;
10
+ activeSessionId = null;
11
+ projectId;
12
+ constructor() {
13
+ const config = (0, memento_core_1.loadConfig)();
14
+ const dbPath = (0, memento_core_1.resolveDbPath)(config);
15
+ this.projectId = (0, memento_core_1.getProjectId)(config);
16
+ this.program = new commander_1.Command();
17
+ this.memory = new memento_core_1.MemoryEngine(dbPath);
18
+ this.setupCommands();
19
+ }
20
+ setupCommands() {
21
+ this.program
22
+ .name('memento')
23
+ .description('Persistent memory system for AI coding agents')
24
+ .version('0.1.0');
25
+ this.program
26
+ .command('setup [agent]')
27
+ .description('Setup configuration for an AI agent')
28
+ .action((agent) => {
29
+ console.log(`Setup for agent: ${agent || 'default'}`);
30
+ console.log('Configuration saved to ~/.memento/config.json');
31
+ });
32
+ this.program
33
+ .command('serve [port]')
34
+ .description('Start API server')
35
+ .option('-d, --db <path>', 'Database path', './data/memento.db')
36
+ .action((port, options) => {
37
+ console.log(`Starting API server on port ${port || 3000}`);
38
+ console.log(`Database: ${options.db}`);
39
+ console.log('Note: API server not implemented in CLI mode');
40
+ });
41
+ this.program
42
+ .command('mcp')
43
+ .description('Start MCP server')
44
+ .option('-d, --db <path>', 'Database path', './data/memento.db')
45
+ .action((options) => {
46
+ console.log(`Starting MCP server`);
47
+ console.log(`Database: ${options.db}`);
48
+ console.log('Note: MCP server not implemented in CLI mode');
49
+ });
50
+ this.program
51
+ .command('search <query>')
52
+ .description('Search observations')
53
+ .option('-t, --type <type>', 'Filter by type')
54
+ .option('-p, --project <project>', 'Filter by project')
55
+ .option('--limit <number>', 'Limit results')
56
+ .action(async (query, options) => {
57
+ const result = await this.memory.search({
58
+ query,
59
+ type: options.type,
60
+ projectId: options.project,
61
+ limit: options.limit ? parseInt(options.limit) : undefined,
62
+ });
63
+ console.log(`Found ${result.total} observations:`);
64
+ result.observations.forEach((obs) => {
65
+ console.log(` [${obs.type}] ${obs.title}`);
66
+ console.log(` ${obs.content.substring(0, 100)}...`);
67
+ });
68
+ });
69
+ this.program
70
+ .command('save <title> <content>')
71
+ .description('Save an observation')
72
+ .option('-t, --type <type>', 'Observation type', 'note')
73
+ .option('-k, --topic <topic>', 'Topic key')
74
+ .option('-p, --project <project>', 'Project ID', this.projectId)
75
+ .action(async (title, content, options) => {
76
+ const sessionId = await this.getOrCreateSessionId(options.project);
77
+ const observation = await this.memory.createObservation({
78
+ sessionId,
79
+ title,
80
+ content,
81
+ type: options.type,
82
+ topicKey: options.topic || null,
83
+ projectId: options.project,
84
+ metadata: {},
85
+ });
86
+ console.log(`Saved observation: ${observation.uuid}`);
87
+ });
88
+ this.program
89
+ .command('get <id>')
90
+ .description('Get observation by ID')
91
+ .action(async (id) => {
92
+ const observation = await this.memory.getObservation(parseInt(id));
93
+ if (!observation) {
94
+ console.error('Observation not found');
95
+ return;
96
+ }
97
+ console.log(`[${observation.type}] ${observation.title}`);
98
+ console.log(observation.content);
99
+ console.log(`Topic: ${observation.topicKey || 'none'}`);
100
+ console.log(`Created: ${observation.createdAt.toISOString()}`);
101
+ });
102
+ this.program
103
+ .command('update <id>')
104
+ .description('Update observation')
105
+ .option('-t, --title <title>', 'New title')
106
+ .option('-c, --content <content>', 'New content')
107
+ .option('-k, --topic <topic>', 'New topic key')
108
+ .action(async (id, options) => {
109
+ const updates = {};
110
+ if (options.title)
111
+ updates.title = options.title;
112
+ if (options.content)
113
+ updates.content = options.content;
114
+ if (options.topic)
115
+ updates.topicKey = options.topic;
116
+ const observation = await this.memory.updateObservation(parseInt(id), updates);
117
+ console.log(`Updated observation: ${observation.uuid}`);
118
+ });
119
+ this.program
120
+ .command('delete <id>')
121
+ .description('Delete observation')
122
+ .action(async (id) => {
123
+ await this.memory.deleteObservation(parseInt(id));
124
+ console.log(`Deleted observation ${id}`);
125
+ });
126
+ this.program
127
+ .command('timeline [project]')
128
+ .description('Show timeline of observations')
129
+ .option('-l, --limit <number>', 'Limit results', '20')
130
+ .action(async (project, options) => {
131
+ const result = await this.memory.search({
132
+ projectId: project,
133
+ limit: parseInt(options.limit),
134
+ });
135
+ console.log(`Timeline (${result.total} observations):`);
136
+ result.observations.forEach((obs) => {
137
+ const date = obs.createdAt.toLocaleDateString();
138
+ console.log(` ${date} [${obs.type}] ${obs.title}`);
139
+ });
140
+ });
141
+ this.program
142
+ .command('stats')
143
+ .description('Show statistics')
144
+ .action(async () => {
145
+ const result = await this.memory.search({});
146
+ const byType = result.observations.reduce((acc, obs) => {
147
+ acc[obs.type] = (acc[obs.type] || 0) + 1;
148
+ return acc;
149
+ }, {});
150
+ console.log('Statistics:');
151
+ console.log(` Total observations: ${result.total}`);
152
+ console.log(' By type:');
153
+ Object.entries(byType).forEach(([type, count]) => {
154
+ console.log(` ${type}: ${count}`);
155
+ });
156
+ });
157
+ }
158
+ async getOrCreateSessionId(projectId) {
159
+ if (this.activeSessionId) {
160
+ return this.activeSessionId;
161
+ }
162
+ const session = await this.memory.createSession({
163
+ projectId,
164
+ endedAt: null,
165
+ metadata: {},
166
+ });
167
+ this.activeSessionId = session.id;
168
+ return session.id;
169
+ }
170
+ async run(argv = process.argv) {
171
+ await this.program.parseAsync(argv);
172
+ }
173
+ close() {
174
+ this.memory.close();
175
+ }
176
+ }
177
+ exports.CLI = CLI;
178
+ //# sourceMappingURL=CLI.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"CLI.js","sourceRoot":"","sources":["../src/CLI.ts"],"names":[],"mappings":"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"}
package/dist/index.js CHANGED
@@ -3,7 +3,9 @@
3
3
  Object.defineProperty(exports, "__esModule", { value: true });
4
4
  const commander_1 = require("commander");
5
5
  const memento_core_1 = require("@slorenzot/memento-core");
6
- const dbPath = process.env.MEMENTO_DB_PATH || "./data/memento.db";
6
+ const config = (0, memento_core_1.loadConfig)();
7
+ const dbPath = (0, memento_core_1.resolveDbPath)(config);
8
+ const projectId = (0, memento_core_1.getProjectId)(config);
7
9
  const memory = new memento_core_1.MemoryEngine(dbPath);
8
10
  let activeSessionId = null;
9
11
  async function getOrCreateSessionId(projectId) {
@@ -14,42 +16,68 @@ async function getOrCreateSessionId(projectId) {
14
16
  return session.id;
15
17
  }
16
18
  const program = new commander_1.Command();
17
- program.name("memento").description("Persistent memory system for AI coding agents").version("0.2.0");
18
- program.command("search <query>").description("Search observations")
19
- .option("-t, --type <type>", "Filter by type")
20
- .option("-p, --project <project>", "Filter by project")
21
- .option("--limit <number>", "Limit results")
19
+ program
20
+ .name('memento')
21
+ .description('Persistent memory system for AI coding agents')
22
+ .version('0.2.0');
23
+ program
24
+ .command('search <query>')
25
+ .description('Search observations')
26
+ .option('-t, --type <type>', 'Filter by type')
27
+ .option('-p, --project <project>', 'Filter by project')
28
+ .option('--limit <number>', 'Limit results')
22
29
  .action(async (query, options) => {
23
- const result = await memory.search({ query, type: options.type, projectId: options.project, limit: options.limit ? parseInt(options.limit) : undefined });
30
+ const result = await memory.search({
31
+ query,
32
+ type: options.type,
33
+ projectId: options.project,
34
+ limit: options.limit ? parseInt(options.limit) : undefined,
35
+ });
24
36
  console.log(`Found ${result.total} observations:`);
25
- result.observations.forEach((obs) => { console.log(` [${obs.type}] ${obs.title}\n ${obs.content.substring(0, 100)}...`); });
37
+ result.observations.forEach((obs) => {
38
+ console.log(` [${obs.type}] ${obs.title}\n ${obs.content.substring(0, 100)}...`);
39
+ });
26
40
  memory.close();
27
41
  });
28
- program.command("save <title> <content>").description("Save an observation")
29
- .option("-t, --type <type>", "Observation type", "note")
30
- .option("-k, --topic <topic>", "Topic key")
31
- .option("-p, --project <project>", "Project ID", "default")
42
+ program
43
+ .command('save <title> <content>')
44
+ .description('Save an observation')
45
+ .option('-t, --type <type>', 'Observation type', 'note')
46
+ .option('-k, --topic <topic>', 'Topic key')
47
+ .option('-p, --project <project>', 'Project ID', projectId)
32
48
  .action(async (title, content, options) => {
33
49
  const sessionId = await getOrCreateSessionId(options.project);
34
- const observation = await memory.createObservation({ sessionId, title, content, type: options.type, topicKey: options.topic || null, projectId: options.project, metadata: {} });
50
+ const observation = await memory.createObservation({
51
+ sessionId,
52
+ title,
53
+ content,
54
+ type: options.type,
55
+ topicKey: options.topic || null,
56
+ projectId: options.project,
57
+ metadata: {},
58
+ });
35
59
  console.log(`Saved observation: ${observation.uuid}`);
36
60
  memory.close();
37
61
  });
38
- program.command("get <id>").description("Get observation by ID")
62
+ program
63
+ .command('get <id>')
64
+ .description('Get observation by ID')
39
65
  .action(async (id) => {
40
66
  const observation = await memory.getObservation(parseInt(id));
41
67
  if (!observation) {
42
- console.error("Observation not found");
68
+ console.error('Observation not found');
43
69
  memory.close();
44
70
  return;
45
71
  }
46
- console.log(`[${observation.type}] ${observation.title}\n${observation.content}\nTopic: ${observation.topicKey || "none"}\nCreated: ${observation.createdAt.toISOString()}`);
72
+ console.log(`[${observation.type}] ${observation.title}\n${observation.content}\nTopic: ${observation.topicKey || 'none'}\nCreated: ${observation.createdAt.toISOString()}`);
47
73
  memory.close();
48
74
  });
49
- program.command("update <id>").description("Update observation")
50
- .option("-t, --title <title>", "New title")
51
- .option("-c, --content <content>", "New content")
52
- .option("-k, --topic <topic>", "New topic key")
75
+ program
76
+ .command('update <id>')
77
+ .description('Update observation')
78
+ .option('-t, --title <title>', 'New title')
79
+ .option('-c, --content <content>', 'New content')
80
+ .option('-k, --topic <topic>', 'New topic key')
53
81
  .action(async (id, options) => {
54
82
  const updates = {};
55
83
  if (options.title)
@@ -62,27 +90,39 @@ program.command("update <id>").description("Update observation")
62
90
  console.log(`Updated observation: ${observation.uuid}`);
63
91
  memory.close();
64
92
  });
65
- program.command("delete <id>").description("Delete observation")
93
+ program
94
+ .command('delete <id>')
95
+ .description('Delete observation')
66
96
  .action(async (id) => {
67
97
  await memory.deleteObservation(parseInt(id));
68
98
  console.log(`Deleted observation ${id}`);
69
99
  memory.close();
70
100
  });
71
- program.command("timeline [project]").description("Show timeline")
72
- .option("-l, --limit <number>", "Limit results", "20")
101
+ program
102
+ .command('timeline [project]')
103
+ .description('Show timeline')
104
+ .option('-l, --limit <number>', 'Limit results', '20')
73
105
  .action(async (project, options) => {
74
106
  const result = await memory.search({ projectId: project, limit: parseInt(options.limit) });
75
107
  console.log(`Timeline (${result.total} observations):`);
76
- result.observations.forEach((obs) => { console.log(` ${obs.createdAt.toLocaleDateString()} [${obs.type}] ${obs.title}`); });
108
+ result.observations.forEach((obs) => {
109
+ console.log(` ${obs.createdAt.toLocaleDateString()} [${obs.type}] ${obs.title}`);
110
+ });
77
111
  memory.close();
78
112
  });
79
- program.command("stats").description("Show statistics")
113
+ program
114
+ .command('stats')
115
+ .description('Show statistics')
80
116
  .action(async () => {
81
117
  const result = await memory.search({});
82
118
  const byType = {};
83
- result.observations.forEach((obs) => { byType[obs.type] = (byType[obs.type] || 0) + 1; });
119
+ result.observations.forEach((obs) => {
120
+ byType[obs.type] = (byType[obs.type] || 0) + 1;
121
+ });
84
122
  console.log(`Statistics:\n Total observations: ${result.total}\n By type:`);
85
- Object.entries(byType).forEach(([type, count]) => { console.log(` ${type}: ${count}`); });
123
+ Object.entries(byType).forEach(([type, count]) => {
124
+ console.log(` ${type}: ${count}`);
125
+ });
86
126
  memory.close();
87
127
  });
88
128
  program.parseAsync(process.argv);
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@slorenzot/memento-cli",
3
- "version": "0.2.0",
3
+ "version": "0.3.0",
4
4
  "description": "CLI interface for Memento memory system",
5
5
  "keywords": [
6
6
  "memento",
@@ -21,7 +21,7 @@
21
21
  "prepare": "npm run build"
22
22
  },
23
23
  "dependencies": {
24
- "@slorenzot/memento-core": "file:../../../tmp/core-build/slorenzot-memento-core-0.2.0.tgz",
24
+ "@slorenzot/memento-core": "^0.6.0",
25
25
  "commander": "^12.0.0"
26
26
  },
27
27
  "devDependencies": {
@@ -0,0 +1,60 @@
1
+ import { describe, it, expect, beforeEach, afterEach } from 'bun:test';
2
+ import { CLI } from './CLI';
3
+
4
+ describe('CLI', () => {
5
+ let cli: CLI;
6
+ let testDbPath: string;
7
+
8
+ beforeEach(() => {
9
+ testDbPath = `/tmp/test-cli-${Date.now()}.db`;
10
+ cli = new CLI(testDbPath);
11
+ });
12
+
13
+ afterEach(() => {
14
+ cli.close();
15
+ });
16
+
17
+ it('should initialize without errors', () => {
18
+ expect(cli).toBeDefined();
19
+ });
20
+
21
+ describe('Commands', () => {
22
+ it('should have all required commands', () => {
23
+ const commands = cli['program'].commands;
24
+
25
+ const commandNames = commands.map((c) => c.name());
26
+ expect(commandNames).toContain('setup');
27
+ expect(commandNames).toContain('serve');
28
+ expect(commandNames).toContain('mcp');
29
+ expect(commandNames).toContain('search');
30
+ expect(commandNames).toContain('save');
31
+ expect(commandNames).toContain('get');
32
+ expect(commandNames).toContain('update');
33
+ expect(commandNames).toContain('delete');
34
+ expect(commandNames).toContain('timeline');
35
+ expect(commandNames).toContain('stats');
36
+ });
37
+
38
+ it('should have proper descriptions', () => {
39
+ const commands = cli['program'].commands;
40
+
41
+ const setupCommand = commands.find((c) => c.name() === 'setup');
42
+ expect(setupCommand).toBeDefined();
43
+ expect(setupCommand?.description()).toContain('Setup');
44
+
45
+ const searchCommand = commands.find((c) => c.name() === 'search');
46
+ expect(searchCommand).toBeDefined();
47
+ expect(searchCommand?.description()).toContain('Search');
48
+ });
49
+ });
50
+
51
+ describe('Session Management', () => {
52
+ it('should create and track active session', async () => {
53
+ const sessionId = await cli['getOrCreateSessionId']('test-project');
54
+ expect(sessionId).toBeDefined();
55
+
56
+ const sameSessionId = await cli['getOrCreateSessionId']('test-project');
57
+ expect(sameSessionId).toBe(sessionId);
58
+ });
59
+ });
60
+ });
package/src/CLI.ts ADDED
@@ -0,0 +1,192 @@
1
+ import { Command } from 'commander';
2
+ import { MemoryEngine, loadConfig, resolveDbPath, getProjectId } from '@slorenzot/memento-core';
3
+ import type { Observation } from '@slorenzot/memento-core';
4
+
5
+ // @ts-ignore
6
+ export class CLI {
7
+ private program: Command;
8
+ private memory: MemoryEngine;
9
+ private activeSessionId: number | null = null;
10
+ private projectId: string;
11
+
12
+ constructor() {
13
+ const config = loadConfig();
14
+ const dbPath = resolveDbPath(config);
15
+ this.projectId = getProjectId(config);
16
+
17
+ this.program = new Command();
18
+ this.memory = new MemoryEngine(dbPath);
19
+ this.setupCommands();
20
+ }
21
+
22
+ private setupCommands() {
23
+ this.program
24
+ .name('memento')
25
+ .description('Persistent memory system for AI coding agents')
26
+ .version('0.1.0');
27
+
28
+ this.program
29
+ .command('setup [agent]')
30
+ .description('Setup configuration for an AI agent')
31
+ .action((agent) => {
32
+ console.log(`Setup for agent: ${agent || 'default'}`);
33
+ console.log('Configuration saved to ~/.memento/config.json');
34
+ });
35
+
36
+ this.program
37
+ .command('serve [port]')
38
+ .description('Start API server')
39
+ .option('-d, --db <path>', 'Database path', './data/memento.db')
40
+ .action((port, options) => {
41
+ console.log(`Starting API server on port ${port || 3000}`);
42
+ console.log(`Database: ${options.db}`);
43
+ console.log('Note: API server not implemented in CLI mode');
44
+ });
45
+
46
+ this.program
47
+ .command('mcp')
48
+ .description('Start MCP server')
49
+ .option('-d, --db <path>', 'Database path', './data/memento.db')
50
+ .action((options) => {
51
+ console.log(`Starting MCP server`);
52
+ console.log(`Database: ${options.db}`);
53
+ console.log('Note: MCP server not implemented in CLI mode');
54
+ });
55
+
56
+ this.program
57
+ .command('search <query>')
58
+ .description('Search observations')
59
+ .option('-t, --type <type>', 'Filter by type')
60
+ .option('-p, --project <project>', 'Filter by project')
61
+ .option('--limit <number>', 'Limit results')
62
+ .action(async (query, options) => {
63
+ const result = await this.memory.search({
64
+ query,
65
+ type: options.type as Observation['type'] | undefined,
66
+ projectId: options.project as string | undefined,
67
+ limit: options.limit ? parseInt(options.limit as string) : undefined,
68
+ });
69
+ console.log(`Found ${result.total} observations:`);
70
+ result.observations.forEach((obs) => {
71
+ console.log(` [${obs.type}] ${obs.title}`);
72
+ console.log(` ${obs.content.substring(0, 100)}...`);
73
+ });
74
+ });
75
+
76
+ this.program
77
+ .command('save <title> <content>')
78
+ .description('Save an observation')
79
+ .option('-t, --type <type>', 'Observation type', 'note')
80
+ .option('-k, --topic <topic>', 'Topic key')
81
+ .option('-p, --project <project>', 'Project ID', this.projectId)
82
+ .action(async (title, content, options) => {
83
+ const sessionId = await this.getOrCreateSessionId(options.project as string);
84
+ const observation = await this.memory.createObservation({
85
+ sessionId,
86
+ title,
87
+ content,
88
+ type: options.type as Observation['type'],
89
+ topicKey: options.topic || null,
90
+ projectId: options.project as string,
91
+ metadata: {},
92
+ });
93
+ console.log(`Saved observation: ${observation.uuid}`);
94
+ });
95
+
96
+ this.program
97
+ .command('get <id>')
98
+ .description('Get observation by ID')
99
+ .action(async (id) => {
100
+ const observation = await this.memory.getObservation(parseInt(id));
101
+ if (!observation) {
102
+ console.error('Observation not found');
103
+ return;
104
+ }
105
+ console.log(`[${observation.type}] ${observation.title}`);
106
+ console.log(observation.content);
107
+ console.log(`Topic: ${observation.topicKey || 'none'}`);
108
+ console.log(`Created: ${observation.createdAt.toISOString()}`);
109
+ });
110
+
111
+ this.program
112
+ .command('update <id>')
113
+ .description('Update observation')
114
+ .option('-t, --title <title>', 'New title')
115
+ .option('-c, --content <content>', 'New content')
116
+ .option('-k, --topic <topic>', 'New topic key')
117
+ .action(async (id, options) => {
118
+ const updates: Partial<Observation> = {};
119
+ if (options.title) updates.title = options.title;
120
+ if (options.content) updates.content = options.content;
121
+ if (options.topic) updates.topicKey = options.topic;
122
+
123
+ const observation = await this.memory.updateObservation(parseInt(id), updates);
124
+ console.log(`Updated observation: ${observation.uuid}`);
125
+ });
126
+
127
+ this.program
128
+ .command('delete <id>')
129
+ .description('Delete observation')
130
+ .action(async (id) => {
131
+ await this.memory.deleteObservation(parseInt(id));
132
+ console.log(`Deleted observation ${id}`);
133
+ });
134
+
135
+ this.program
136
+ .command('timeline [project]')
137
+ .description('Show timeline of observations')
138
+ .option('-l, --limit <number>', 'Limit results', '20')
139
+ .action(async (project, options) => {
140
+ const result = await this.memory.search({
141
+ projectId: project,
142
+ limit: parseInt(options.limit as string),
143
+ });
144
+ console.log(`Timeline (${result.total} observations):`);
145
+ result.observations.forEach((obs) => {
146
+ const date = obs.createdAt.toLocaleDateString();
147
+ console.log(` ${date} [${obs.type}] ${obs.title}`);
148
+ });
149
+ });
150
+
151
+ this.program
152
+ .command('stats')
153
+ .description('Show statistics')
154
+ .action(async () => {
155
+ const result = await this.memory.search({});
156
+ const byType = result.observations.reduce(
157
+ (acc, obs) => {
158
+ acc[obs.type] = (acc[obs.type] || 0) + 1;
159
+ return acc;
160
+ },
161
+ {} as Record<string, number>
162
+ );
163
+ console.log('Statistics:');
164
+ console.log(` Total observations: ${result.total}`);
165
+ console.log(' By type:');
166
+ Object.entries(byType).forEach(([type, count]) => {
167
+ console.log(` ${type}: ${count}`);
168
+ });
169
+ });
170
+ }
171
+
172
+ private async getOrCreateSessionId(projectId: string): Promise<number> {
173
+ if (this.activeSessionId) {
174
+ return this.activeSessionId;
175
+ }
176
+ const session = await this.memory.createSession({
177
+ projectId,
178
+ endedAt: null,
179
+ metadata: {},
180
+ });
181
+ this.activeSessionId = session.id;
182
+ return session.id;
183
+ }
184
+
185
+ async run(argv: string[] = process.argv) {
186
+ await this.program.parseAsync(argv);
187
+ }
188
+
189
+ close() {
190
+ this.memory.close();
191
+ }
192
+ }
package/src/index.ts CHANGED
@@ -1,10 +1,12 @@
1
1
  #!/usr/bin/env node
2
2
 
3
- import { Command } from "commander";
4
- import { MemoryEngine } from "@slorenzot/memento-core";
5
- import type { Observation } from "@slorenzot/memento-core";
3
+ import { Command } from 'commander';
4
+ import { MemoryEngine, loadConfig, resolveDbPath, getProjectId } from '@slorenzot/memento-core';
5
+ import type { Observation } from '@slorenzot/memento-core';
6
6
 
7
- const dbPath = process.env.MEMENTO_DB_PATH || "./data/memento.db";
7
+ const config = loadConfig();
8
+ const dbPath = resolveDbPath(config);
9
+ const projectId = getProjectId(config);
8
10
  const memory = new MemoryEngine(dbPath);
9
11
  let activeSessionId: number | null = null;
10
12
 
@@ -16,42 +18,74 @@ async function getOrCreateSessionId(projectId: string): Promise<number> {
16
18
  }
17
19
 
18
20
  const program = new Command();
19
- program.name("memento").description("Persistent memory system for AI coding agents").version("0.2.0");
21
+ program
22
+ .name('memento')
23
+ .description('Persistent memory system for AI coding agents')
24
+ .version('0.2.0');
20
25
 
21
- program.command("search <query>").description("Search observations")
22
- .option("-t, --type <type>", "Filter by type")
23
- .option("-p, --project <project>", "Filter by project")
24
- .option("--limit <number>", "Limit results")
26
+ program
27
+ .command('search <query>')
28
+ .description('Search observations')
29
+ .option('-t, --type <type>', 'Filter by type')
30
+ .option('-p, --project <project>', 'Filter by project')
31
+ .option('--limit <number>', 'Limit results')
25
32
  .action(async (query: string, options: any) => {
26
- const result = await memory.search({ query, type: options.type, projectId: options.project, limit: options.limit ? parseInt(options.limit) : undefined });
33
+ const result = await memory.search({
34
+ query,
35
+ type: options.type,
36
+ projectId: options.project,
37
+ limit: options.limit ? parseInt(options.limit) : undefined,
38
+ });
27
39
  console.log(`Found ${result.total} observations:`);
28
- result.observations.forEach((obs: Observation) => { console.log(` [${obs.type}] ${obs.title}\n ${obs.content.substring(0, 100)}...`); });
40
+ result.observations.forEach((obs: Observation) => {
41
+ console.log(` [${obs.type}] ${obs.title}\n ${obs.content.substring(0, 100)}...`);
42
+ });
29
43
  memory.close();
30
44
  });
31
45
 
32
- program.command("save <title> <content>").description("Save an observation")
33
- .option("-t, --type <type>", "Observation type", "note")
34
- .option("-k, --topic <topic>", "Topic key")
35
- .option("-p, --project <project>", "Project ID", "default")
46
+ program
47
+ .command('save <title> <content>')
48
+ .description('Save an observation')
49
+ .option('-t, --type <type>', 'Observation type', 'note')
50
+ .option('-k, --topic <topic>', 'Topic key')
51
+ .option('-p, --project <project>', 'Project ID', projectId)
36
52
  .action(async (title: string, content: string, options: any) => {
37
53
  const sessionId = await getOrCreateSessionId(options.project);
38
- const observation = await memory.createObservation({ sessionId, title, content, type: options.type, topicKey: options.topic || null, projectId: options.project, metadata: {} });
54
+ const observation = await memory.createObservation({
55
+ sessionId,
56
+ title,
57
+ content,
58
+ type: options.type,
59
+ topicKey: options.topic || null,
60
+ projectId: options.project,
61
+ metadata: {},
62
+ });
39
63
  console.log(`Saved observation: ${observation.uuid}`);
40
64
  memory.close();
41
65
  });
42
66
 
43
- program.command("get <id>").description("Get observation by ID")
67
+ program
68
+ .command('get <id>')
69
+ .description('Get observation by ID')
44
70
  .action(async (id: string) => {
45
71
  const observation = await memory.getObservation(parseInt(id));
46
- if (!observation) { console.error("Observation not found"); memory.close(); return; }
47
- console.log(`[${observation.type}] ${observation.title}\n${observation.content}\nTopic: ${observation.topicKey || "none"}\nCreated: ${observation.createdAt.toISOString()}`);
72
+ if (!observation) {
73
+ console.error('Observation not found');
74
+ memory.close();
75
+ return;
76
+ }
77
+ console.log(
78
+ `[${observation.type}] ${observation.title}\n${observation.content}\nTopic: ${observation.topicKey || 'none'}\nCreated: ${observation.createdAt.toISOString()}`
79
+ );
48
80
  memory.close();
49
81
  });
50
82
 
51
- program.command("update <id>").description("Update observation")
52
- .option("-t, --title <title>", "New title")
53
- .option("-c, --content <content>", "New content")
54
- .option("-k, --topic <topic>", "New topic key")
83
+ program
84
+ .command('update <id>')
85
+ .description('Update observation')
86
+ .option('-t, --title <title>', 'New title')
87
+ .option('-c, --content <content>', 'New content')
88
+ .option('-k, --topic <topic>', 'New topic key')
55
89
  .action(async (id: string, options: any) => {
56
90
  const updates: any = {};
57
91
  if (options.title) updates.title = options.title;
@@ -62,29 +96,41 @@ program.command("update <id>").description("Update observation")
62
96
  memory.close();
63
97
  });
64
98
 
65
- program.command("delete <id>").description("Delete observation")
99
+ program
100
+ .command('delete <id>')
101
+ .description('Delete observation')
66
102
  .action(async (id: string) => {
67
103
  await memory.deleteObservation(parseInt(id));
68
104
  console.log(`Deleted observation ${id}`);
69
105
  memory.close();
70
106
  });
71
107
 
72
- program.command("timeline [project]").description("Show timeline")
73
- .option("-l, --limit <number>", "Limit results", "20")
108
+ program
109
+ .command('timeline [project]')
110
+ .description('Show timeline')
111
+ .option('-l, --limit <number>', 'Limit results', '20')
74
112
  .action(async (project: string, options: any) => {
75
113
  const result = await memory.search({ projectId: project, limit: parseInt(options.limit) });
76
114
  console.log(`Timeline (${result.total} observations):`);
77
- result.observations.forEach((obs: Observation) => { console.log(` ${obs.createdAt.toLocaleDateString()} [${obs.type}] ${obs.title}`); });
115
+ result.observations.forEach((obs: Observation) => {
116
+ console.log(` ${obs.createdAt.toLocaleDateString()} [${obs.type}] ${obs.title}`);
117
+ });
78
118
  memory.close();
79
119
  });
80
120
 
81
- program.command("stats").description("Show statistics")
121
+ program
122
+ .command('stats')
123
+ .description('Show statistics')
82
124
  .action(async () => {
83
125
  const result = await memory.search({});
84
126
  const byType: Record<string, number> = {};
85
- result.observations.forEach((obs: Observation) => { byType[obs.type] = (byType[obs.type] || 0) + 1; });
127
+ result.observations.forEach((obs: Observation) => {
128
+ byType[obs.type] = (byType[obs.type] || 0) + 1;
129
+ });
86
130
  console.log(`Statistics:\n Total observations: ${result.total}\n By type:`);
87
- Object.entries(byType).forEach(([type, count]) => { console.log(` ${type}: ${count}`); });
131
+ Object.entries(byType).forEach(([type, count]) => {
132
+ console.log(` ${type}: ${count}`);
133
+ });
88
134
  memory.close();
89
135
  });
90
136
 
package/data/memento.db DELETED
Binary file
Binary file
Binary file
Binary file