@openclawcity/become 1.0.1 → 1.0.3

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/README.md CHANGED
@@ -10,7 +10,7 @@ Install become. It sits between your agent and its LLM. When your agent talks to
10
10
 
11
11
  [![npm version](https://img.shields.io/npm/v/@openclawcity/become?style=flat&labelColor=555&color=22d3ee)](https://www.npmjs.com/package/@openclawcity/become)
12
12
  [![License: MIT](https://img.shields.io/badge/license-MIT-green?style=flat&labelColor=555)](LICENSE)
13
- [![Tests](https://img.shields.io/badge/tests-492_passing-22d3ee?style=flat&labelColor=555)]()
13
+ [![Tests](https://img.shields.io/badge/tests-492_passing-22d3ee?style=flat&labelColor=555)](https://github.com/openclawcity/become)
14
14
 
15
15
  </div>
16
16
 
@@ -127,7 +127,7 @@ Open `http://localhost:30002` when the proxy is running.
127
127
  | **On/off switch** | `become off` — your agent bypasses the proxy completely. |
128
128
  | **Local only** | Everything stored in `~/.become/` on your machine. |
129
129
  | **No data sent** | become never phones home. Only talks to the LLM you configured. |
130
- | **Open source** | MIT license. 482 tests. |
130
+ | **Open source** | MIT license. 492 tests. |
131
131
 
132
132
  ---
133
133
 
@@ -195,6 +195,28 @@ Yes. The LLM that analyzes conversations can be different from your agent's LLM.
195
195
 
196
196
  ---
197
197
 
198
+ ## Update, downgrade, uninstall
199
+
200
+ ```bash
201
+ # Update to latest version
202
+ npm update -g @openclawcity/become
203
+
204
+ # Check which version you have
205
+ become --version
206
+
207
+ # Uninstall completely (removes CLI, keeps your learned skills)
208
+ npm uninstall -g @openclawcity/become
209
+
210
+ # Uninstall and remove all data (skills, config, trust, everything)
211
+ npm uninstall -g @openclawcity/become && rm -rf ~/.become
212
+
213
+ # If become was ON when you uninstall, restore your agent first
214
+ become off # restores original agent config
215
+ npm uninstall -g @openclawcity/become
216
+ ```
217
+
218
+ ---
219
+
198
220
  ## Also included (library mode)
199
221
 
200
222
  become also exports a TypeScript library for programmatic use:
@@ -215,7 +237,7 @@ Plus: skill scoring (Dreyfus stages), peer review protocol, teaching protocol, l
215
237
 
216
238
  ```bash
217
239
  git clone https://github.com/openclawcity/become.git
218
- cd become && npm install && npm test # 482 tests
240
+ cd become && npm install && npm test # 492 tests
219
241
  ```
220
242
 
221
243
  ---
package/dist/cli.cjs CHANGED
@@ -92,6 +92,157 @@ var LLM_DEFAULTS = {
92
92
  openrouter: { base_url: "https://openrouter.ai/api" }
93
93
  };
94
94
 
95
+ // src/cli/adapter/openclaw.ts
96
+ var import_node_fs2 = require("fs");
97
+ var import_node_path2 = require("path");
98
+ var import_node_os2 = require("os");
99
+ var import_node_child_process = require("child_process");
100
+ var OPENCLAW_CONFIG = (0, import_node_path2.join)((0, import_node_os2.homedir)(), ".openclaw", "openclaw.json");
101
+ var BACKUP_PATH = (0, import_node_path2.join)((0, import_node_os2.homedir)(), ".become", "state", "original_openclaw.json");
102
+ var ORIGINAL_MODEL_PATH = (0, import_node_path2.join)((0, import_node_os2.homedir)(), ".become", "state", "original_model.txt");
103
+ var PATCHED_AGENT_PATH = (0, import_node_path2.join)((0, import_node_os2.homedir)(), ".become", "state", "patched_agent.txt");
104
+ function patchOpenClaw(config, agentId) {
105
+ if (!(0, import_node_fs2.existsSync)(OPENCLAW_CONFIG)) {
106
+ throw new Error(`OpenClaw config not found at ${OPENCLAW_CONFIG}`);
107
+ }
108
+ const raw = (0, import_node_fs2.readFileSync)(OPENCLAW_CONFIG, "utf-8");
109
+ const clawConfig = parseOpenClawConfig(raw);
110
+ if (clawConfig.models?.providers?.become) {
111
+ console.log("become is already connected. Run `become off` first to disconnect.");
112
+ return;
113
+ }
114
+ (0, import_node_fs2.mkdirSync)((0, import_node_path2.join)((0, import_node_os2.homedir)(), ".become", "state"), { recursive: true });
115
+ (0, import_node_fs2.writeFileSync)(BACKUP_PATH, raw, "utf-8");
116
+ const agents = clawConfig.agents?.list ?? [];
117
+ let originalModel;
118
+ let patchedAgentId;
119
+ if (agents.length > 0 && agentId) {
120
+ const agent = agents.find((a) => a.id === agentId);
121
+ if (!agent) {
122
+ throw new Error(`Agent "${agentId}" not found in agents.list. Available: ${agents.map((a) => a.id).join(", ")}`);
123
+ }
124
+ originalModel = agent.model ?? clawConfig.agents?.defaults?.model?.primary ?? "";
125
+ patchedAgentId = agentId;
126
+ const modelId2 = stripProvider(originalModel);
127
+ if (!modelId2) {
128
+ throw new Error("No model configured for this agent. Set a model in openclaw.json first.");
129
+ }
130
+ agent.model = `become/${modelId2}`;
131
+ } else {
132
+ originalModel = clawConfig.agents?.defaults?.model?.primary ?? "";
133
+ patchedAgentId = "_defaults";
134
+ const modelId2 = stripProvider(originalModel);
135
+ if (!modelId2) {
136
+ throw new Error("No default model configured. Set agents.defaults.model.primary in openclaw.json first.");
137
+ }
138
+ if (!clawConfig.agents) clawConfig.agents = {};
139
+ if (!clawConfig.agents.defaults) clawConfig.agents.defaults = {};
140
+ if (!clawConfig.agents.defaults.model) clawConfig.agents.defaults.model = {};
141
+ clawConfig.agents.defaults.model.primary = `become/${modelId2}`;
142
+ }
143
+ (0, import_node_fs2.writeFileSync)(ORIGINAL_MODEL_PATH, originalModel, "utf-8");
144
+ (0, import_node_fs2.writeFileSync)(PATCHED_AGENT_PATH, patchedAgentId, "utf-8");
145
+ const modelId = stripProvider(originalModel);
146
+ if (!clawConfig.models) clawConfig.models = {};
147
+ if (!clawConfig.models.providers) clawConfig.models.providers = {};
148
+ clawConfig.models.providers.become = {
149
+ api: config.llm_provider === "openai" || config.llm_provider === "openrouter" ? "openai-completions" : "anthropic-messages",
150
+ baseUrl: `http://127.0.0.1:${config.proxy_port}`,
151
+ apiKey: config.llm_api_key,
152
+ models: [
153
+ { id: modelId, name: `${modelId} via become` }
154
+ ]
155
+ };
156
+ (0, import_node_fs2.writeFileSync)(OPENCLAW_CONFIG, JSON.stringify(clawConfig, null, 2), "utf-8");
157
+ try {
158
+ (0, import_node_child_process.execSync)("openclaw gateway restart", { stdio: "pipe", timeout: 15e3 });
159
+ } catch {
160
+ console.log("Warning: Could not restart OpenClaw gateway. Restart it manually: openclaw gateway restart");
161
+ }
162
+ }
163
+ function restoreOpenClaw() {
164
+ if (!(0, import_node_fs2.existsSync)(OPENCLAW_CONFIG)) {
165
+ throw new Error(`OpenClaw config not found at ${OPENCLAW_CONFIG}`);
166
+ }
167
+ if ((0, import_node_fs2.existsSync)(BACKUP_PATH)) {
168
+ const backup = (0, import_node_fs2.readFileSync)(BACKUP_PATH, "utf-8");
169
+ const backupConfig = parseOpenClawConfig(backup);
170
+ if (!backupConfig.models?.providers?.become) {
171
+ (0, import_node_fs2.writeFileSync)(OPENCLAW_CONFIG, backup, "utf-8");
172
+ restartGateway();
173
+ return;
174
+ }
175
+ }
176
+ const raw = (0, import_node_fs2.readFileSync)(OPENCLAW_CONFIG, "utf-8");
177
+ const config = parseOpenClawConfig(raw);
178
+ const patchedAgentId = readStateFile(PATCHED_AGENT_PATH);
179
+ const originalModel = readStateFile(ORIGINAL_MODEL_PATH);
180
+ if (originalModel) {
181
+ const agents = config.agents?.list ?? [];
182
+ if (patchedAgentId && patchedAgentId !== "_defaults") {
183
+ const agent = agents.find((a) => a.id === patchedAgentId);
184
+ if (agent) {
185
+ agent.model = originalModel;
186
+ }
187
+ } else {
188
+ if (config.agents?.defaults?.model) {
189
+ config.agents.defaults.model.primary = originalModel;
190
+ }
191
+ }
192
+ }
193
+ if (config.models?.providers?.become) {
194
+ delete config.models.providers.become;
195
+ }
196
+ for (const provider of Object.values(config.models?.providers ?? {})) {
197
+ if (provider && typeof provider === "object" && "_originalModel" in provider) {
198
+ delete provider._originalModel;
199
+ }
200
+ }
201
+ (0, import_node_fs2.writeFileSync)(OPENCLAW_CONFIG, JSON.stringify(config, null, 2), "utf-8");
202
+ restartGateway();
203
+ }
204
+ function listOpenClawAgents() {
205
+ if (!(0, import_node_fs2.existsSync)(OPENCLAW_CONFIG)) return [];
206
+ try {
207
+ const config = parseOpenClawConfig((0, import_node_fs2.readFileSync)(OPENCLAW_CONFIG, "utf-8"));
208
+ const agents = config.agents?.list ?? [];
209
+ const defaultModel = unbecome(config.agents?.defaults?.model?.primary ?? "unknown");
210
+ if (agents.length === 0) {
211
+ return [{ id: "_defaults", model: defaultModel }];
212
+ }
213
+ return agents.map((a) => ({
214
+ id: a.id,
215
+ model: unbecome(a.model ?? defaultModel)
216
+ }));
217
+ } catch {
218
+ return [];
219
+ }
220
+ }
221
+ function stripProvider(model) {
222
+ return model.includes("/") ? model.split("/").slice(1).join("/") : model;
223
+ }
224
+ function unbecome(model) {
225
+ return model.startsWith("become/") ? model.replace("become/", "") : model;
226
+ }
227
+ function parseOpenClawConfig(raw) {
228
+ const stripped = raw.replace(/\/\/.*$/gm, "").replace(/\/\*[\s\S]*?\*\//g, "").replace(/,\s*([\]}])/g, "$1");
229
+ return JSON.parse(stripped);
230
+ }
231
+ function readStateFile(path) {
232
+ try {
233
+ return (0, import_node_fs2.existsSync)(path) ? (0, import_node_fs2.readFileSync)(path, "utf-8").trim() : "";
234
+ } catch {
235
+ return "";
236
+ }
237
+ }
238
+ function restartGateway() {
239
+ try {
240
+ (0, import_node_child_process.execSync)("openclaw gateway restart", { stdio: "pipe", timeout: 15e3 });
241
+ } catch {
242
+ console.log("Warning: Could not restart OpenClaw gateway. Restart it manually: openclaw gateway restart");
243
+ }
244
+ }
245
+
95
246
  // src/cli/setup.ts
96
247
  var AGENT_TYPES = ["openclaw", "ironclaw", "nanoclaw", "generic"];
97
248
  var LLM_PROVIDERS = ["anthropic", "openai", "ollama", "openrouter", "custom"];
@@ -107,7 +258,25 @@ async function runSetup() {
107
258
  const agentChoice = await ask(rl, "> ");
108
259
  const agentIdx = parseInt(agentChoice, 10) - 1;
109
260
  const agent_type = AGENT_TYPES[agentIdx] ?? "openclaw";
110
- console.log("\nWhich LLM provider?");
261
+ let openclaw_agent_id;
262
+ if (agent_type === "openclaw") {
263
+ const agents = listOpenClawAgents();
264
+ if (agents.length > 1) {
265
+ console.log("\nWhich OpenClaw agent should learn from other agents?");
266
+ agents.forEach((a, i) => console.log(` ${i + 1}. ${a.id} (${a.model})`));
267
+ const agentPick = await ask(rl, "> ");
268
+ const pickIdx = parseInt(agentPick, 10) - 1;
269
+ const picked = agents[pickIdx];
270
+ if (picked && picked.id !== "_defaults") {
271
+ openclaw_agent_id = picked.id;
272
+ }
273
+ } else if (agents.length === 1 && agents[0].id !== "_defaults") {
274
+ openclaw_agent_id = agents[0].id;
275
+ console.log(`
276
+ OpenClaw agent: ${openclaw_agent_id} (${agents[0].model})`);
277
+ }
278
+ }
279
+ console.log("\nWhich LLM provider does your agent use?");
111
280
  LLM_PROVIDERS.forEach((p, i) => console.log(` ${i + 1}. ${p}`));
112
281
  const llmChoice = await ask(rl, "> ");
113
282
  const llmIdx = parseInt(llmChoice, 10) - 1;
@@ -129,6 +298,7 @@ Proxy port (default 30001): `);
129
298
  const dashboard_port = parseInt(dashInput, 10) || 30002;
130
299
  const config = {
131
300
  agent_type,
301
+ openclaw_agent_id,
132
302
  llm_provider,
133
303
  llm_base_url,
134
304
  llm_api_key: llm_api_key.trim(),
@@ -152,20 +322,20 @@ Proxy port (default 30001): `);
152
322
  var import_node_http = require("http");
153
323
 
154
324
  // src/skills/store.ts
155
- var import_node_fs2 = require("fs");
156
- var import_node_path2 = require("path");
325
+ var import_node_fs3 = require("fs");
326
+ var import_node_path3 = require("path");
157
327
  var import_node_crypto = require("crypto");
158
328
  var FileSkillStore = class {
159
329
  skillsDir;
160
330
  pendingDir;
161
331
  rejectedDir;
162
332
  constructor(config) {
163
- this.skillsDir = (0, import_node_path2.join)(config.baseDir, "skills");
164
- this.pendingDir = (0, import_node_path2.join)(config.baseDir, "pending");
165
- this.rejectedDir = (0, import_node_path2.join)(config.baseDir, "rejected");
166
- (0, import_node_fs2.mkdirSync)(this.skillsDir, { recursive: true });
167
- (0, import_node_fs2.mkdirSync)(this.pendingDir, { recursive: true });
168
- (0, import_node_fs2.mkdirSync)(this.rejectedDir, { recursive: true });
333
+ this.skillsDir = (0, import_node_path3.join)(config.baseDir, "skills");
334
+ this.pendingDir = (0, import_node_path3.join)(config.baseDir, "pending");
335
+ this.rejectedDir = (0, import_node_path3.join)(config.baseDir, "rejected");
336
+ (0, import_node_fs3.mkdirSync)(this.skillsDir, { recursive: true });
337
+ (0, import_node_fs3.mkdirSync)(this.pendingDir, { recursive: true });
338
+ (0, import_node_fs3.mkdirSync)(this.rejectedDir, { recursive: true });
169
339
  }
170
340
  // ── Read ────────────────────────────────────────────────────────────────
171
341
  listApproved() {
@@ -179,7 +349,7 @@ var FileSkillStore = class {
179
349
  }
180
350
  getApproved(id) {
181
351
  this.validateId(id);
182
- return this.readFile((0, import_node_path2.join)(this.skillsDir, `${id}.md`));
352
+ return this.readFile((0, import_node_path3.join)(this.skillsDir, `${id}.md`));
183
353
  }
184
354
  // ── Write ───────────────────────────────────────────────────────────────
185
355
  savePending(lesson) {
@@ -190,43 +360,43 @@ var FileSkillStore = class {
190
360
  }
191
361
  const id = this.generateId(lesson.name);
192
362
  const file = { ...lesson, id, approved_at: void 0 };
193
- this.writeFile((0, import_node_path2.join)(this.pendingDir, `${id}.md`), file);
363
+ this.writeFile((0, import_node_path3.join)(this.pendingDir, `${id}.md`), file);
194
364
  return file;
195
365
  }
196
366
  approve(id) {
197
367
  this.validateId(id);
198
- const src = (0, import_node_path2.join)(this.pendingDir, `${id}.md`);
199
- if (!(0, import_node_fs2.existsSync)(src)) return false;
368
+ const src = (0, import_node_path3.join)(this.pendingDir, `${id}.md`);
369
+ if (!(0, import_node_fs3.existsSync)(src)) return false;
200
370
  const skill = this.readFile(src);
201
371
  if (!skill) return false;
202
372
  skill.approved_at = (/* @__PURE__ */ new Date()).toISOString();
203
- const dest = (0, import_node_path2.join)(this.skillsDir, `${id}.md`);
373
+ const dest = (0, import_node_path3.join)(this.skillsDir, `${id}.md`);
204
374
  this.writeFile(dest, skill);
205
- (0, import_node_fs2.unlinkSync)(src);
375
+ (0, import_node_fs3.unlinkSync)(src);
206
376
  return true;
207
377
  }
208
378
  reject(id) {
209
379
  this.validateId(id);
210
- const src = (0, import_node_path2.join)(this.pendingDir, `${id}.md`);
211
- if (!(0, import_node_fs2.existsSync)(src)) return false;
212
- const dest = (0, import_node_path2.join)(this.rejectedDir, `${id}.md`);
213
- (0, import_node_fs2.renameSync)(src, dest);
380
+ const src = (0, import_node_path3.join)(this.pendingDir, `${id}.md`);
381
+ if (!(0, import_node_fs3.existsSync)(src)) return false;
382
+ const dest = (0, import_node_path3.join)(this.rejectedDir, `${id}.md`);
383
+ (0, import_node_fs3.renameSync)(src, dest);
214
384
  return true;
215
385
  }
216
386
  disable(id) {
217
387
  this.validateId(id);
218
- const src = (0, import_node_path2.join)(this.skillsDir, `${id}.md`);
219
- if (!(0, import_node_fs2.existsSync)(src)) return false;
220
- const dest = (0, import_node_path2.join)(this.rejectedDir, `${id}.md`);
221
- (0, import_node_fs2.renameSync)(src, dest);
388
+ const src = (0, import_node_path3.join)(this.skillsDir, `${id}.md`);
389
+ if (!(0, import_node_fs3.existsSync)(src)) return false;
390
+ const dest = (0, import_node_path3.join)(this.rejectedDir, `${id}.md`);
391
+ (0, import_node_fs3.renameSync)(src, dest);
222
392
  return true;
223
393
  }
224
394
  remove(id) {
225
395
  this.validateId(id);
226
396
  for (const dir of [this.skillsDir, this.pendingDir, this.rejectedDir]) {
227
- const path = (0, import_node_path2.join)(dir, `${id}.md`);
228
- if ((0, import_node_fs2.existsSync)(path)) {
229
- (0, import_node_fs2.unlinkSync)(path);
397
+ const path = (0, import_node_path3.join)(dir, `${id}.md`);
398
+ if ((0, import_node_fs3.existsSync)(path)) {
399
+ (0, import_node_fs3.unlinkSync)(path);
230
400
  return true;
231
401
  }
232
402
  }
@@ -244,27 +414,27 @@ var FileSkillStore = class {
244
414
  }
245
415
  }
246
416
  readDir(dir) {
247
- if (!(0, import_node_fs2.existsSync)(dir)) return [];
248
- const files = (0, import_node_fs2.readdirSync)(dir).filter((f) => f.endsWith(".md"));
417
+ if (!(0, import_node_fs3.existsSync)(dir)) return [];
418
+ const files = (0, import_node_fs3.readdirSync)(dir).filter((f) => f.endsWith(".md"));
249
419
  const skills = [];
250
420
  for (const f of files) {
251
- const skill = this.readFile((0, import_node_path2.join)(dir, f));
421
+ const skill = this.readFile((0, import_node_path3.join)(dir, f));
252
422
  if (skill) skills.push(skill);
253
423
  }
254
424
  return skills.sort((a, b) => b.created_at.localeCompare(a.created_at));
255
425
  }
256
426
  readFile(path) {
257
- if (!(0, import_node_fs2.existsSync)(path)) return null;
427
+ if (!(0, import_node_fs3.existsSync)(path)) return null;
258
428
  try {
259
- const content = (0, import_node_fs2.readFileSync)(path, "utf-8");
260
- return this.parseSkillFile(content, (0, import_node_path2.basename)(path, ".md"));
429
+ const content = (0, import_node_fs3.readFileSync)(path, "utf-8");
430
+ return this.parseSkillFile(content, (0, import_node_path3.basename)(path, ".md"));
261
431
  } catch {
262
432
  return null;
263
433
  }
264
434
  }
265
435
  writeFile(path, skill) {
266
436
  const content = this.formatSkillFile(skill);
267
- (0, import_node_fs2.writeFileSync)(path, content, "utf-8");
437
+ (0, import_node_fs3.writeFileSync)(path, content, "utf-8");
268
438
  }
269
439
  parseSkillFile(content, id) {
270
440
  const match = content.match(/^---\s*\n([\s\S]*?)\n---\s*\n([\s\S]*)$/);
@@ -313,8 +483,8 @@ var FileSkillStore = class {
313
483
  };
314
484
 
315
485
  // src/skills/trust.ts
316
- var import_node_fs3 = require("fs");
317
- var import_node_path3 = require("path");
486
+ var import_node_fs4 = require("fs");
487
+ var import_node_path4 = require("path");
318
488
  var DEFAULT_TRUST = {
319
489
  trusted: [],
320
490
  blocked: [],
@@ -331,9 +501,9 @@ var TrustManager = class {
331
501
  config;
332
502
  dailyCounts;
333
503
  constructor(baseDir) {
334
- this.trustPath = (0, import_node_path3.join)(baseDir, "trust.json");
335
- this.statsPath = (0, import_node_path3.join)(baseDir, "state", "daily_counts.json");
336
- (0, import_node_fs3.mkdirSync)((0, import_node_path3.join)(baseDir, "state"), { recursive: true });
504
+ this.trustPath = (0, import_node_path4.join)(baseDir, "trust.json");
505
+ this.statsPath = (0, import_node_path4.join)(baseDir, "state", "daily_counts.json");
506
+ (0, import_node_fs4.mkdirSync)((0, import_node_path4.join)(baseDir, "state"), { recursive: true });
337
507
  this.config = this.loadTrust();
338
508
  this.dailyCounts = this.loadDailyCounts();
339
509
  }
@@ -376,9 +546,9 @@ var TrustManager = class {
376
546
  }
377
547
  // ── Private ─────────────────────────────────────────────────────────────
378
548
  loadTrust() {
379
- if (!(0, import_node_fs3.existsSync)(this.trustPath)) return { ...DEFAULT_TRUST, trusted: [], blocked: [] };
549
+ if (!(0, import_node_fs4.existsSync)(this.trustPath)) return { ...DEFAULT_TRUST, trusted: [], blocked: [] };
380
550
  try {
381
- const raw = JSON.parse((0, import_node_fs3.readFileSync)(this.trustPath, "utf-8"));
551
+ const raw = JSON.parse((0, import_node_fs4.readFileSync)(this.trustPath, "utf-8"));
382
552
  return {
383
553
  trusted: Array.isArray(raw.trusted) ? raw.trusted.filter((a) => typeof a === "string") : [],
384
554
  blocked: Array.isArray(raw.blocked) ? raw.blocked.filter((a) => typeof a === "string") : [],
@@ -389,14 +559,14 @@ var TrustManager = class {
389
559
  }
390
560
  }
391
561
  saveTrust() {
392
- (0, import_node_fs3.mkdirSync)((0, import_node_path3.dirname)(this.trustPath), { recursive: true });
393
- (0, import_node_fs3.writeFileSync)(this.trustPath, JSON.stringify(this.config, null, 2), "utf-8");
562
+ (0, import_node_fs4.mkdirSync)((0, import_node_path4.dirname)(this.trustPath), { recursive: true });
563
+ (0, import_node_fs4.writeFileSync)(this.trustPath, JSON.stringify(this.config, null, 2), "utf-8");
394
564
  }
395
565
  loadDailyCounts() {
396
566
  const today = (/* @__PURE__ */ new Date()).toISOString().slice(0, 10);
397
- if (!(0, import_node_fs3.existsSync)(this.statsPath)) return { date: today, total: 0, perAgent: {} };
567
+ if (!(0, import_node_fs4.existsSync)(this.statsPath)) return { date: today, total: 0, perAgent: {} };
398
568
  try {
399
- const data = JSON.parse((0, import_node_fs3.readFileSync)(this.statsPath, "utf-8"));
569
+ const data = JSON.parse((0, import_node_fs4.readFileSync)(this.statsPath, "utf-8"));
400
570
  if (data.date !== today) return { date: today, total: 0, perAgent: {} };
401
571
  return data;
402
572
  } catch {
@@ -404,7 +574,7 @@ var TrustManager = class {
404
574
  }
405
575
  }
406
576
  saveDailyCounts() {
407
- (0, import_node_fs3.writeFileSync)(this.statsPath, JSON.stringify(this.dailyCounts, null, 2), "utf-8");
577
+ (0, import_node_fs4.writeFileSync)(this.statsPath, JSON.stringify(this.dailyCounts, null, 2), "utf-8");
408
578
  }
409
579
  refreshDailyCountsIfNewDay() {
410
580
  const today = (/* @__PURE__ */ new Date()).toISOString().slice(0, 10);
@@ -1251,54 +1421,6 @@ function readBody2(req) {
1251
1421
  });
1252
1422
  }
1253
1423
 
1254
- // src/cli/adapter/openclaw.ts
1255
- var import_node_fs4 = require("fs");
1256
- var import_node_path4 = require("path");
1257
- var import_node_os2 = require("os");
1258
- var import_node_child_process = require("child_process");
1259
- var OPENCLAW_CONFIG = (0, import_node_path4.join)((0, import_node_os2.homedir)(), ".openclaw", "openclaw.json");
1260
- var BACKUP_PATH = (0, import_node_path4.join)((0, import_node_os2.homedir)(), ".become", "state", "original_openclaw.json");
1261
- function patchOpenClaw(config) {
1262
- if (!(0, import_node_fs4.existsSync)(OPENCLAW_CONFIG)) {
1263
- throw new Error(`OpenClaw config not found at ${OPENCLAW_CONFIG}`);
1264
- }
1265
- const raw = (0, import_node_fs4.readFileSync)(OPENCLAW_CONFIG, "utf-8");
1266
- const clawConfig = JSON.parse(raw);
1267
- (0, import_node_fs4.mkdirSync)((0, import_node_path4.join)((0, import_node_os2.homedir)(), ".become", "state"), { recursive: true });
1268
- (0, import_node_fs4.writeFileSync)(BACKUP_PATH, raw, "utf-8");
1269
- if (!clawConfig.models) clawConfig.models = {};
1270
- if (!clawConfig.models.providers) clawConfig.models.providers = {};
1271
- clawConfig.models.providers.become = {
1272
- api: "anthropic-messages",
1273
- baseUrl: `http://127.0.0.1:${config.proxy_port}`,
1274
- apiKey: config.llm_api_key
1275
- };
1276
- if (clawConfig.agents?.defaults?.model?.primary) {
1277
- const original = clawConfig.agents.defaults.model.primary;
1278
- clawConfig.models.providers.become._originalModel = original;
1279
- const modelId = original.includes("/") ? original.split("/").slice(1).join("/") : original;
1280
- clawConfig.agents.defaults.model.primary = `become/${modelId}`;
1281
- }
1282
- (0, import_node_fs4.writeFileSync)(OPENCLAW_CONFIG, JSON.stringify(clawConfig, null, 2), "utf-8");
1283
- try {
1284
- (0, import_node_child_process.execSync)("openclaw gateway restart", { stdio: "pipe", timeout: 15e3 });
1285
- } catch {
1286
- console.log("Warning: Could not restart OpenClaw gateway. Restart it manually: openclaw gateway restart");
1287
- }
1288
- }
1289
- function restoreOpenClaw() {
1290
- if (!(0, import_node_fs4.existsSync)(BACKUP_PATH)) {
1291
- throw new Error("No backup found. Was become ever turned on?");
1292
- }
1293
- const backup = (0, import_node_fs4.readFileSync)(BACKUP_PATH, "utf-8");
1294
- (0, import_node_fs4.writeFileSync)(OPENCLAW_CONFIG, backup, "utf-8");
1295
- try {
1296
- (0, import_node_child_process.execSync)("openclaw gateway restart", { stdio: "pipe", timeout: 15e3 });
1297
- } catch {
1298
- console.log("Warning: Could not restart OpenClaw gateway. Restart it manually: openclaw gateway restart");
1299
- }
1300
- }
1301
-
1302
1424
  // src/cli/adapter/ironclaw.ts
1303
1425
  var import_node_fs5 = require("fs");
1304
1426
  var import_node_path5 = require("path");
@@ -1482,7 +1604,7 @@ Patching ${config.agent_type} config...`);
1482
1604
  console.log(` baseUrl: ${config.llm_base_url} \u2192 localhost:${config.proxy_port}`);
1483
1605
  switch (config.agent_type) {
1484
1606
  case "openclaw":
1485
- patchOpenClaw(config);
1607
+ patchOpenClaw(config, config.openclaw_agent_id);
1486
1608
  break;
1487
1609
  case "ironclaw":
1488
1610
  patchIronClaw(config);