@mnemom/mnemom 0.7.2 → 0.9.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.
@@ -1,10 +1,10 @@
1
- import { configExists, loadConfig, requireAgent } from "../lib/config.js";
2
- import { getAgent, getIntegrity, getTraces } from "../lib/api.js";
1
+ import { getGatewayUrl } from "../lib/config.js";
2
+ import { resolveAgentId, getAgent, getIntegrity, getTraces } from "../lib/api.js";
3
+ import { isLoggedIn, getAuthInfo } from "../lib/auth.js";
3
4
  import { detectOpenClaw, detectProviders, getCurrentModel, getSmoltbotConfiguredProviders, PROVIDER_CONFIG_KEYS, } from "../lib/openclaw.js";
4
5
  import { formatModelName, detectProvider } from "../lib/models.js";
5
6
  import { refreshModelCache } from "../lib/model-cache.js";
6
7
  import { fmt } from "../lib/format.js";
7
- const GATEWAY_URL = "https://gateway.mnemom.ai";
8
8
  const DASHBOARD_URL = "https://mnemom.ai";
9
9
  const PROVIDER_LABELS = {
10
10
  anthropic: "Anthropic",
@@ -17,19 +17,20 @@ const AIP_SUPPORT = {
17
17
  gemini: "Full (thought parts)",
18
18
  };
19
19
  export async function statusCommand(agentName) {
20
- console.log(fmt.header("smoltbot status"));
20
+ console.log(fmt.header("mnemom status"));
21
21
  console.log();
22
22
  const checks = [];
23
- // 1. Check smoltbot config
24
- const configCheck = checkSmoltbotConfig();
25
- checks.push(configCheck);
26
- if (configCheck.status === "error") {
23
+ // 1. Check auth status
24
+ const authCheck = await checkAuthStatus();
25
+ checks.push(authCheck);
26
+ if (authCheck.status === "error") {
27
27
  printChecks(checks);
28
- console.log("\nRun `smoltbot init` to get started.\n");
28
+ console.log("\nRun `mnemom login` to authenticate.\n");
29
29
  process.exit(1);
30
30
  }
31
- const config = loadConfig();
32
- const agent = await requireAgent(agentName);
31
+ // Resolve agent ID from server
32
+ const agentId = await resolveAgentId(agentName);
33
+ const gatewayUrl = getGatewayUrl();
33
34
  // 2. Check OpenClaw configuration
34
35
  const openclawCheck = checkOpenClawConfig();
35
36
  checks.push(openclawCheck);
@@ -40,28 +41,19 @@ export async function statusCommand(agentName) {
40
41
  const modelCheck = checkCurrentModel();
41
42
  checks.push(modelCheck);
42
43
  // 5. Test gateway connectivity
43
- const gatewayCheck = await checkGatewayConnectivity();
44
+ const gatewayCheck = await checkGatewayConnectivity(gatewayUrl);
44
45
  checks.push(gatewayCheck);
45
46
  // 6. Test API connectivity
46
- const apiCheck = await checkApiConnectivity(agent.agentId);
47
+ const apiCheck = await checkApiConnectivity(agentId);
47
48
  checks.push(apiCheck);
48
49
  // Print all checks
49
50
  printChecks(checks);
50
51
  // Show configuration details
51
52
  console.log(fmt.section("Configuration"));
52
53
  console.log();
53
- console.log(fmt.label("Agent ID: ", agent.agentId));
54
- console.log(fmt.label("Gateway: ", config.gateway || GATEWAY_URL));
55
- console.log(fmt.label("Dashboard:", ` ${DASHBOARD_URL}/agents/${agent.agentId}`));
56
- if (config.mnemomApiKey) {
57
- console.log(`Mnemom Key: [CONFIGURED] (billing enabled)`);
58
- }
59
- else {
60
- console.log(`Mnemom Key: Not configured (free tier)`);
61
- }
62
- if (agent.openclawConfigured) {
63
- console.log(`Configured: ${agent.configuredAt || "yes"}`);
64
- }
54
+ console.log(fmt.label("Agent ID: ", agentId));
55
+ console.log(fmt.label("Gateway: ", gatewayUrl));
56
+ console.log(fmt.label("Dashboard:", ` ${DASHBOARD_URL}/agents/${agentId}`));
65
57
  // Show current model info
66
58
  const { fullPath, provider, modelId } = getCurrentModel();
67
59
  if (fullPath) {
@@ -76,7 +68,7 @@ export async function statusCommand(agentName) {
76
68
  console.log(" Status: Traced mode NOT ACTIVE");
77
69
  if (modelId) {
78
70
  const detectedProvider = detectProvider(modelId);
79
- const configKey = detectedProvider ? PROVIDER_CONFIG_KEYS[detectedProvider] : "smoltbot";
71
+ const configKey = detectedProvider ? PROVIDER_CONFIG_KEYS[detectedProvider] : "mnemom";
80
72
  console.log(`\n To enable: openclaw models set ${configKey}/${modelId}`);
81
73
  }
82
74
  }
@@ -85,7 +77,7 @@ export async function statusCommand(agentName) {
85
77
  showProviderSummary();
86
78
  // Show trace summary if available
87
79
  if (apiCheck.status === "ok") {
88
- await showTraceSummary(agent.agentId);
80
+ await showTraceSummary(agentId);
89
81
  }
90
82
  // Show overall status
91
83
  const hasErrors = checks.some((c) => c.status === "error");
@@ -105,29 +97,29 @@ export async function statusCommand(agentName) {
105
97
  // Refresh model cache in background (non-blocking)
106
98
  refreshModelCache().catch(() => { });
107
99
  }
108
- function checkSmoltbotConfig() {
109
- if (!configExists()) {
100
+ async function checkAuthStatus() {
101
+ const loggedIn = await isLoggedIn();
102
+ if (!loggedIn) {
110
103
  return {
111
- name: "Smoltbot Config",
104
+ name: "Authentication",
112
105
  status: "error",
113
- message: "Not initialized",
114
- details: "Run `smoltbot init` to configure",
106
+ message: "Not authenticated",
107
+ details: "Run `mnemom login` or set MNEMOM_API_KEY",
115
108
  };
116
109
  }
117
- const config = loadConfig();
118
- if (!config) {
110
+ const auth = getAuthInfo();
111
+ if (auth) {
119
112
  return {
120
- name: "Smoltbot Config",
121
- status: "error",
122
- message: "Config file corrupted",
123
- details: "Delete ~/.smoltbot/config.json and run `smoltbot init`",
113
+ name: "Authentication",
114
+ status: "ok",
115
+ message: `Logged in as ${auth.email}`,
124
116
  };
125
117
  }
126
- const defaultAgent = config.agents[config.defaultAgent];
118
+ // API key auth (no email available)
127
119
  return {
128
- name: "Smoltbot Config",
120
+ name: "Authentication",
129
121
  status: "ok",
130
- message: `Agent ID: ${defaultAgent?.agentId ?? "unknown"}`,
122
+ message: "Authenticated via API key",
131
123
  };
132
124
  }
133
125
  function checkOpenClawConfig() {
@@ -146,7 +138,7 @@ function checkOpenClawConfig() {
146
138
  name: "OpenClaw",
147
139
  status: "error",
148
140
  message: "OAuth auth (not supported)",
149
- details: "smoltbot requires API key authentication",
141
+ details: "mnemom requires API key authentication",
150
142
  };
151
143
  }
152
144
  // Check if any provider has a key (not just Anthropic)
@@ -170,14 +162,14 @@ function checkOpenClawConfig() {
170
162
  return {
171
163
  name: "OpenClaw",
172
164
  status: "warning",
173
- message: "smoltbot provider not configured",
174
- details: "Run `smoltbot init` to configure",
165
+ message: "mnemom provider not configured",
166
+ details: "Run `mnemom register <name>` to configure",
175
167
  };
176
168
  }
177
169
  return {
178
170
  name: "OpenClaw",
179
171
  status: "ok",
180
- message: "smoltbot provider configured",
172
+ message: "mnemom provider configured",
181
173
  };
182
174
  }
183
175
  function checkConfiguredProviders() {
@@ -201,7 +193,7 @@ function checkConfiguredProviders() {
201
193
  name: `${PROVIDER_LABELS[provider]}`,
202
194
  status: "warning",
203
195
  message: "API key found but not configured",
204
- details: "Run `smoltbot init` to configure",
196
+ details: "Run `mnemom register <name>` to configure",
205
197
  });
206
198
  }
207
199
  // Don't show providers without keys (too noisy)
@@ -215,7 +207,7 @@ function checkCurrentModel() {
215
207
  name: "Current Model",
216
208
  status: "warning",
217
209
  message: "No default model set",
218
- details: "Run `openclaw models set smoltbot/<model>`",
210
+ details: "Run `openclaw models set mnemom/<model>`",
219
211
  };
220
212
  }
221
213
  if (provider && (provider === "smoltbot" || provider.startsWith("smoltbot"))) {
@@ -229,7 +221,7 @@ function checkCurrentModel() {
229
221
  name: "Current Model",
230
222
  status: "warning",
231
223
  message: `${fullPath} (not traced)`,
232
- details: `Switch with: openclaw models set smoltbot/${modelId}`,
224
+ details: `Switch with: openclaw models set mnemom/${modelId}`,
233
225
  };
234
226
  }
235
227
  function showProviderSummary() {
@@ -248,9 +240,9 @@ function showProviderSummary() {
248
240
  console.log(` ${label}: ${configKey}/* (AIP: ${aip})`);
249
241
  }
250
242
  }
251
- async function checkGatewayConnectivity() {
243
+ async function checkGatewayConnectivity(gatewayUrl) {
252
244
  try {
253
- const response = await fetch(`${GATEWAY_URL}/health`, {
245
+ const response = await fetch(`${gatewayUrl}/health`, {
254
246
  signal: AbortSignal.timeout(5000),
255
247
  });
256
248
  if (response.ok) {
@@ -339,12 +331,14 @@ async function showTraceSummary(agentId) {
339
331
  console.log();
340
332
  if (integrityResult.status === "fulfilled") {
341
333
  const integrity = integrityResult.value;
342
- const score = (integrity.score * 100).toFixed(1);
334
+ // Field names per docs.mnemom.ai IntegrityScore: integrity_score
335
+ // (in [0,1]), verified_traces, violation_count.
336
+ const score = (integrity.integrity_score * 100).toFixed(1);
343
337
  console.log(`Integrity Score: ${score}%`);
344
338
  console.log(`Total Traces: ${integrity.total_traces}`);
345
- console.log(`Verified: ${integrity.verified}`);
346
- if (integrity.violations > 0) {
347
- console.log(`Violations: ${integrity.violations}`);
339
+ console.log(`Verified: ${integrity.verified_traces}`);
340
+ if (integrity.violation_count > 0) {
341
+ console.log(`Violations: ${integrity.violation_count}`);
348
342
  }
349
343
  }
350
344
  else {
package/dist/index.js CHANGED
@@ -1,42 +1,19 @@
1
1
  #!/usr/bin/env node
2
2
  import { program } from "commander";
3
- import { initCommand } from "./commands/init.js";
4
3
  import { statusCommand } from "./commands/status.js";
5
4
  import { integrityCommand } from "./commands/integrity.js";
6
5
  import { logsCommand } from "./commands/logs.js";
7
6
  import { licenseActivateCommand, licenseStatusCommand, licenseDeactivateCommand } from "./commands/license.js";
8
- import { cardShowCommand, cardPublishCommand, cardValidateCommand } from "./commands/card.js";
7
+ import { cardShowCommand, cardPublishCommand, cardValidateCommand, cardEditCommand, cardEvaluateCommand } from "./commands/card.js";
9
8
  import { policyInitCommand, policyValidateCommand, policyPublishCommand, policyListCommand, policyTestCommand, policyEvaluateCommand, } from "./commands/policy.js";
10
- import { registerCommand } from "./commands/register.js";
11
- import { agentsListCommand, agentsRemoveCommand, agentsAddCommand, agentsDefaultCommand, agentsRekeyCommand, agentsCheckBindingCommand } from "./commands/agents.js";
9
+ import { protectionShowCommand, protectionPublishCommand, protectionValidateCommand, protectionEditCommand } from "./commands/protection.js";
10
+ import { agentsListCommand } from "./commands/agents.js";
12
11
  import { loginCommand, logoutCommand, whoamiCommand } from "./commands/auth.js";
13
- import { makeMigrateConfigCommand } from "./commands/migrate-config.js";
14
12
  program
15
13
  .name("mnemom")
16
- .description("Transparent AI agent tracing - AAP compliant")
17
- .version("0.6.0")
18
- .option("--agent <name>", "Select agent by name");
19
- program
20
- .command("init")
21
- .description("Initialize smoltbot for traced mode (interactive, --openclaw, or --standalone)")
22
- .option("-y, --yes", "Skip confirmation prompts (accept defaults)")
23
- .option("-f, --force", "Force reconfiguration even if already configured")
24
- .option("--openclaw", "Configure using OpenClaw (requires OpenClaw installed)")
25
- .option("--standalone", "Configure standalone (prompt for API keys directly)")
26
- .action(async (options) => {
27
- try {
28
- await initCommand({
29
- yes: options.yes,
30
- force: options.force,
31
- openclaw: options.openclaw,
32
- standalone: options.standalone,
33
- });
34
- }
35
- catch (error) {
36
- console.error("Error:", error instanceof Error ? error.message : error);
37
- process.exit(1);
38
- }
39
- });
14
+ .description("Transparent AI agent tracing")
15
+ .version("0.8.0")
16
+ .option("--agent <name>", "Select agent by name (or set MNEMOM_AGENT)");
40
17
  program
41
18
  .command("status")
42
19
  .description("Show agent status and connection info")
@@ -117,12 +94,15 @@ license
117
94
  process.exit(1);
118
95
  }
119
96
  });
97
+ // ============================================================================
98
+ // Card commands (alignment card)
99
+ // ============================================================================
120
100
  const cardCmd = program
121
101
  .command("card")
122
102
  .description("Manage alignment card");
123
103
  cardCmd
124
104
  .command("show")
125
- .description("Display active alignment card")
105
+ .description("Display alignment card (YAML)")
126
106
  .action(async () => {
127
107
  try {
128
108
  const opts = program.opts();
@@ -134,13 +114,13 @@ cardCmd
134
114
  }
135
115
  });
136
116
  cardCmd
137
- .command("publish")
138
- .argument("<file>", "Path to card JSON file")
139
- .description("Publish alignment card from JSON file")
140
- .action(async (file) => {
117
+ .command("edit")
118
+ .description("Edit alignment card in $EDITOR")
119
+ .option("--idempotency-key <uuid>", "Reuse a specific Idempotency-Key (for retries; default: auto)")
120
+ .action(async (subOpts) => {
141
121
  try {
142
122
  const opts = program.opts();
143
- await cardPublishCommand(file, opts.agent);
123
+ await cardEditCommand(opts.agent, { idempotencyKey: subOpts.idempotencyKey });
144
124
  }
145
125
  catch (error) {
146
126
  console.error("Error:", error instanceof Error ? error.message : error);
@@ -148,198 +128,177 @@ cardCmd
148
128
  }
149
129
  });
150
130
  cardCmd
151
- .command("validate")
152
- .argument("<file>", "Path to card JSON file")
153
- .description("Validate card JSON locally")
154
- .action(async (file) => {
155
- try {
156
- await cardValidateCommand(file);
157
- }
158
- catch (error) {
159
- console.error("Error:", error instanceof Error ? error.message : error);
160
- process.exit(1);
161
- }
162
- });
163
- const policyCmd = program
164
- .command("policy")
165
- .description("Manage policy engine");
166
- policyCmd
167
- .command("init")
168
- .description("Scaffold a policy.json template")
169
- .action(async () => {
170
- try {
171
- await policyInitCommand();
172
- }
173
- catch (error) {
174
- console.error("Error:", error instanceof Error ? error.message : error);
175
- process.exit(1);
176
- }
177
- });
178
- policyCmd
179
- .command("validate")
180
- .argument("<file>", "Path to policy JSON file")
181
- .description("Validate policy locally")
182
- .action(async (file) => {
183
- try {
184
- await policyValidateCommand(file);
185
- }
186
- catch (error) {
187
- console.error("Error:", error instanceof Error ? error.message : error);
188
- process.exit(1);
189
- }
190
- });
191
- policyCmd
192
131
  .command("publish")
193
- .argument("<file>", "Path to policy JSON file")
194
- .description("Validate and publish policy to API")
195
- .action(async (file) => {
196
- try {
197
- const opts = program.opts();
198
- await policyPublishCommand(file, opts.agent);
199
- }
200
- catch (error) {
201
- console.error("Error:", error instanceof Error ? error.message : error);
202
- process.exit(1);
203
- }
204
- });
205
- policyCmd
206
- .command("list")
207
- .description("List active policy for current agent")
208
- .action(async () => {
132
+ .argument("<file>", "Path to alignment card file (YAML or JSON)")
133
+ .description("Publish alignment card")
134
+ .option("--idempotency-key <uuid>", "Reuse a specific Idempotency-Key (for retries; default: auto)")
135
+ .action(async (file, subOpts) => {
209
136
  try {
210
137
  const opts = program.opts();
211
- await policyListCommand(opts.agent);
138
+ await cardPublishCommand(file, opts.agent, { idempotencyKey: subOpts.idempotencyKey });
212
139
  }
213
140
  catch (error) {
214
141
  console.error("Error:", error instanceof Error ? error.message : error);
215
142
  process.exit(1);
216
143
  }
217
144
  });
218
- policyCmd
219
- .command("test")
220
- .argument("<file>", "Path to policy JSON file")
221
- .option("--against-traces", "Test against historical traces")
222
- .description("Dry-run policy against historical traces")
145
+ cardCmd
146
+ .command("validate")
147
+ .argument("<file>", "Path to alignment card file (YAML or JSON)")
148
+ .description("Validate alignment card locally")
223
149
  .action(async (file) => {
224
150
  try {
225
- const opts = program.opts();
226
- await policyTestCommand(file, opts.agent);
151
+ await cardValidateCommand(file);
227
152
  }
228
153
  catch (error) {
229
154
  console.error("Error:", error instanceof Error ? error.message : error);
230
155
  process.exit(1);
231
156
  }
232
157
  });
233
- policyCmd
158
+ cardCmd
234
159
  .command("evaluate")
235
- .argument("<file>", "Path to policy JSON file")
236
- .option("--card <file>", "Path to alignment card JSON file")
160
+ .argument("<file>", "Path to alignment card file (YAML or JSON)")
237
161
  .option("--tools <tools>", "Comma-separated list of tool names")
238
162
  .option("--tool-manifest <file>", "Path to tool manifest JSON file")
239
163
  .option("--strict", "Exit with code 1 on warnings (not just failures)")
240
- .description("Evaluate policy against tools locally (for CI/CD)")
164
+ .description("Evaluate card policy against tools locally (for CI/CD)")
241
165
  .action(async (file, options) => {
242
166
  try {
243
- await policyEvaluateCommand(file, options);
244
- }
245
- catch (error) {
246
- console.error("Error:", error instanceof Error ? error.message : error);
247
- process.exit(1);
248
- }
249
- });
250
- program
251
- .command("register <name>")
252
- .description("Register a new named agent")
253
- .option("--openclaw", "Configure using OpenClaw")
254
- .option("--standalone", "Configure standalone mode")
255
- .option("--set-default", "Set as default agent")
256
- .action(async (name, options) => {
257
- try {
258
- await registerCommand(name, {
259
- openclaw: options.openclaw,
260
- standalone: options.standalone,
261
- setDefault: options.setDefault,
262
- });
167
+ await cardEvaluateCommand(file, options);
263
168
  }
264
169
  catch (error) {
265
170
  console.error("Error:", error instanceof Error ? error.message : error);
266
171
  process.exit(1);
267
172
  }
268
173
  });
269
- const agentsCmd = program
270
- .command("agents")
271
- .description("List and manage registered agents");
272
- agentsCmd
174
+ // ============================================================================
175
+ // Protection card commands
176
+ // ============================================================================
177
+ const protectionCmd = program
178
+ .command("protection")
179
+ .description("Manage protection card");
180
+ protectionCmd
181
+ .command("show")
182
+ .description("Display protection card (YAML)")
273
183
  .action(async () => {
274
184
  try {
275
- await agentsListCommand();
185
+ const opts = program.opts();
186
+ await protectionShowCommand(opts.agent);
276
187
  }
277
188
  catch (error) {
278
189
  console.error("Error:", error instanceof Error ? error.message : error);
279
190
  process.exit(1);
280
191
  }
281
192
  });
282
- agentsCmd
283
- .command("remove <name>")
284
- .description("Remove a registered agent")
285
- .action(async (name) => {
193
+ protectionCmd
194
+ .command("edit")
195
+ .description("Edit protection card in $EDITOR")
196
+ .option("--idempotency-key <uuid>", "Reuse a specific Idempotency-Key (for retries; default: auto)")
197
+ .action(async (subOpts) => {
286
198
  try {
287
- await agentsRemoveCommand(name);
199
+ const opts = program.opts();
200
+ await protectionEditCommand(opts.agent, { idempotencyKey: subOpts.idempotencyKey });
288
201
  }
289
202
  catch (error) {
290
203
  console.error("Error:", error instanceof Error ? error.message : error);
291
204
  process.exit(1);
292
205
  }
293
206
  });
294
- agentsCmd
295
- .command("add <name-or-id>")
296
- .description("Register an existing API agent in local config")
297
- .option("--alias <alias>", "Local alias name (default: agent's API name)")
298
- .action(async (nameOrId, options) => {
207
+ protectionCmd
208
+ .command("publish")
209
+ .argument("<file>", "Path to protection card file (YAML or JSON)")
210
+ .description("Publish protection card")
211
+ .option("--idempotency-key <uuid>", "Reuse a specific Idempotency-Key (for retries; default: auto)")
212
+ .action(async (file, subOpts) => {
299
213
  try {
300
- await agentsAddCommand(nameOrId, options.alias);
214
+ const opts = program.opts();
215
+ await protectionPublishCommand(file, opts.agent, { idempotencyKey: subOpts.idempotencyKey });
301
216
  }
302
217
  catch (error) {
303
218
  console.error("Error:", error instanceof Error ? error.message : error);
304
219
  process.exit(1);
305
220
  }
306
221
  });
307
- agentsCmd
308
- .command("default <name>")
309
- .description("Set the default agent")
310
- .action(async (name) => {
222
+ protectionCmd
223
+ .command("validate")
224
+ .argument("<file>", "Path to protection card file (YAML or JSON)")
225
+ .description("Validate protection card locally")
226
+ .action(async (file) => {
311
227
  try {
312
- await agentsDefaultCommand(name);
228
+ await protectionValidateCommand(file);
313
229
  }
314
230
  catch (error) {
315
231
  console.error("Error:", error instanceof Error ? error.message : error);
316
232
  process.exit(1);
317
233
  }
318
234
  });
319
- agentsCmd
320
- .command("rekey [name]")
321
- .description("Re-bind an agent to a new provider API key (key hashed locally, never transmitted)")
322
- .action(async (name) => {
323
- try {
324
- await agentsRekeyCommand(name);
325
- }
326
- catch (error) {
327
- console.error("Error:", error instanceof Error ? error.message : error);
328
- process.exit(1);
329
- }
235
+ // ============================================================================
236
+ // Policy commands (removed — stubs with migration guidance)
237
+ // ============================================================================
238
+ const policyCmd = program
239
+ .command("policy")
240
+ .description("(removed) Policy is now part of the alignment card");
241
+ policyCmd
242
+ .command("init")
243
+ .description("(removed) Use `mnemom card validate`")
244
+ .action(async () => { await policyInitCommand(); });
245
+ policyCmd
246
+ .command("validate")
247
+ .argument("<file>", "Path to policy file")
248
+ .description("(removed) Use `mnemom card validate`")
249
+ .action(async (file) => { await policyValidateCommand(file); });
250
+ policyCmd
251
+ .command("publish")
252
+ .argument("<file>", "Path to policy file")
253
+ .description("(removed) Use `mnemom card publish`")
254
+ .action(async (file) => {
255
+ const opts = program.opts();
256
+ await policyPublishCommand(file, opts.agent);
257
+ });
258
+ policyCmd
259
+ .command("list")
260
+ .description("(removed) Use `mnemom card show`")
261
+ .action(async () => {
262
+ const opts = program.opts();
263
+ await policyListCommand(opts.agent);
330
264
  });
331
- agentsCmd
332
- .command("check-binding [name]")
333
- .description("Verify that a provider API key is bound to an agent (key hashed locally, never transmitted)")
334
- .action(async (name) => {
265
+ policyCmd
266
+ .command("test")
267
+ .argument("<file>", "Path to policy file")
268
+ .description("(removed) Use `mnemom card evaluate`")
269
+ .action(async (file) => {
270
+ const opts = program.opts();
271
+ await policyTestCommand(file, opts.agent);
272
+ });
273
+ policyCmd
274
+ .command("evaluate")
275
+ .argument("<file>", "Path to policy file")
276
+ .option("--card <file>", "Path to card file")
277
+ .option("--tools <tools>", "Comma-separated list of tool names")
278
+ .option("--tool-manifest <file>", "Path to tool manifest JSON file")
279
+ .option("--strict", "Exit with code 1 on warnings")
280
+ .description("(removed) Use `mnemom card evaluate`")
281
+ .action(async (file, options) => {
282
+ await policyEvaluateCommand(file, options);
283
+ });
284
+ // ============================================================================
285
+ // Agent management
286
+ // ============================================================================
287
+ program
288
+ .command("agents")
289
+ .description("List agents in your account")
290
+ .action(async () => {
335
291
  try {
336
- await agentsCheckBindingCommand(name);
292
+ await agentsListCommand();
337
293
  }
338
294
  catch (error) {
339
295
  console.error("Error:", error instanceof Error ? error.message : error);
340
296
  process.exit(1);
341
297
  }
342
298
  });
299
+ // ============================================================================
300
+ // Auth
301
+ // ============================================================================
343
302
  program
344
303
  .command("login")
345
304
  .description("Authenticate with your Mnemom account")
@@ -377,5 +336,4 @@ program
377
336
  process.exit(1);
378
337
  }
379
338
  });
380
- program.addCommand(makeMigrateConfigCommand());
381
339
  program.parse();