@askexenow/exe-os 0.9.7 → 0.9.9

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.
Files changed (101) hide show
  1. package/dist/bin/backfill-conversations.js +953 -105
  2. package/dist/bin/backfill-responses.js +952 -104
  3. package/dist/bin/backfill-vectors.js +956 -108
  4. package/dist/bin/cleanup-stale-review-tasks.js +802 -58
  5. package/dist/bin/cli.js +2292 -1070
  6. package/dist/bin/exe-agent-config.js +157 -101
  7. package/dist/bin/exe-agent.js +55 -29
  8. package/dist/bin/exe-assign.js +940 -92
  9. package/dist/bin/exe-boot.js +1424 -442
  10. package/dist/bin/exe-call.js +240 -141
  11. package/dist/bin/exe-cloud.js +198 -70
  12. package/dist/bin/exe-dispatch.js +951 -192
  13. package/dist/bin/exe-doctor.js +791 -51
  14. package/dist/bin/exe-export-behaviors.js +790 -42
  15. package/dist/bin/exe-forget.js +771 -31
  16. package/dist/bin/exe-gateway.js +1592 -521
  17. package/dist/bin/exe-heartbeat.js +850 -109
  18. package/dist/bin/exe-kill.js +783 -35
  19. package/dist/bin/exe-launch-agent.js +1030 -107
  20. package/dist/bin/exe-link.js +916 -110
  21. package/dist/bin/exe-new-employee.js +526 -217
  22. package/dist/bin/exe-pending-messages.js +1046 -62
  23. package/dist/bin/exe-pending-notifications.js +1318 -111
  24. package/dist/bin/exe-pending-reviews.js +1040 -72
  25. package/dist/bin/exe-rename.js +772 -59
  26. package/dist/bin/exe-review.js +772 -32
  27. package/dist/bin/exe-search.js +982 -128
  28. package/dist/bin/exe-session-cleanup.js +1180 -306
  29. package/dist/bin/exe-settings.js +185 -105
  30. package/dist/bin/exe-start-codex.js +886 -132
  31. package/dist/bin/exe-start-opencode.js +873 -119
  32. package/dist/bin/exe-status.js +803 -59
  33. package/dist/bin/exe-team.js +772 -32
  34. package/dist/bin/git-sweep.js +1046 -223
  35. package/dist/bin/graph-backfill.js +779 -31
  36. package/dist/bin/graph-export.js +785 -37
  37. package/dist/bin/install.js +632 -200
  38. package/dist/bin/scan-tasks.js +1055 -232
  39. package/dist/bin/setup.js +1419 -320
  40. package/dist/bin/shard-migrate.js +783 -35
  41. package/dist/bin/update.js +138 -49
  42. package/dist/bin/wiki-sync.js +782 -34
  43. package/dist/gateway/index.js +1444 -449
  44. package/dist/hooks/bug-report-worker.js +1141 -269
  45. package/dist/hooks/codex-stop-task-finalizer.js +4678 -0
  46. package/dist/hooks/commit-complete.js +1044 -221
  47. package/dist/hooks/error-recall.js +989 -135
  48. package/dist/hooks/exe-heartbeat-hook.js +99 -75
  49. package/dist/hooks/ingest-worker.js +4176 -3226
  50. package/dist/hooks/ingest.js +920 -168
  51. package/dist/hooks/instructions-loaded.js +874 -70
  52. package/dist/hooks/notification.js +860 -56
  53. package/dist/hooks/post-compact.js +881 -73
  54. package/dist/hooks/pre-compact.js +1050 -227
  55. package/dist/hooks/pre-tool-use.js +1084 -159
  56. package/dist/hooks/prompt-ingest-worker.js +1089 -164
  57. package/dist/hooks/prompt-submit.js +1469 -515
  58. package/dist/hooks/response-ingest-worker.js +1104 -179
  59. package/dist/hooks/session-end.js +1085 -251
  60. package/dist/hooks/session-start.js +1241 -231
  61. package/dist/hooks/stop.js +935 -109
  62. package/dist/hooks/subagent-stop.js +881 -73
  63. package/dist/hooks/summary-worker.js +1323 -307
  64. package/dist/index.js +1449 -452
  65. package/dist/lib/agent-config.js +28 -6
  66. package/dist/lib/cloud-sync.js +909 -115
  67. package/dist/lib/config.js +30 -10
  68. package/dist/lib/consolidation.js +42 -9
  69. package/dist/lib/database.js +739 -33
  70. package/dist/lib/db-daemon-client.js +73 -19
  71. package/dist/lib/db.js +2359 -0
  72. package/dist/lib/device-registry.js +760 -47
  73. package/dist/lib/embedder.js +201 -73
  74. package/dist/lib/employee-templates.js +30 -4
  75. package/dist/lib/employees.js +290 -86
  76. package/dist/lib/exe-daemon-client.js +187 -83
  77. package/dist/lib/exe-daemon.js +1696 -616
  78. package/dist/lib/hybrid-search.js +982 -128
  79. package/dist/lib/identity.js +43 -13
  80. package/dist/lib/license.js +133 -48
  81. package/dist/lib/messaging.js +167 -80
  82. package/dist/lib/reminders.js +35 -5
  83. package/dist/lib/schedules.js +772 -32
  84. package/dist/lib/skill-learning.js +54 -7
  85. package/dist/lib/store.js +779 -31
  86. package/dist/lib/task-router.js +94 -73
  87. package/dist/lib/tasks.js +298 -225
  88. package/dist/lib/tmux-routing.js +246 -172
  89. package/dist/lib/token-spend.js +52 -14
  90. package/dist/mcp/server.js +2893 -850
  91. package/dist/mcp/tools/complete-reminder.js +35 -5
  92. package/dist/mcp/tools/create-reminder.js +35 -5
  93. package/dist/mcp/tools/create-task.js +507 -323
  94. package/dist/mcp/tools/deactivate-behavior.js +40 -10
  95. package/dist/mcp/tools/list-reminders.js +35 -5
  96. package/dist/mcp/tools/list-tasks.js +277 -104
  97. package/dist/mcp/tools/send-message.js +129 -56
  98. package/dist/mcp/tools/update-task.js +1864 -188
  99. package/dist/runtime/index.js +1083 -259
  100. package/dist/tui/App.js +1501 -434
  101. package/package.json +3 -2
@@ -3,9 +3,18 @@ var __esm = (fn, res) => function __init() {
3
3
  return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
4
4
  };
5
5
 
6
+ // src/lib/secure-files.ts
7
+ import { chmodSync, existsSync, mkdirSync } from "fs";
8
+ import { chmod, mkdir } from "fs/promises";
9
+ var init_secure_files = __esm({
10
+ "src/lib/secure-files.ts"() {
11
+ "use strict";
12
+ }
13
+ });
14
+
6
15
  // src/lib/config.ts
7
- import { readFile, writeFile, mkdir, chmod } from "fs/promises";
8
- import { readFileSync, existsSync, renameSync } from "fs";
16
+ import { readFile, writeFile } from "fs/promises";
17
+ import { readFileSync, existsSync as existsSync2, renameSync } from "fs";
9
18
  import path from "path";
10
19
  import os from "os";
11
20
  function resolveDataDir() {
@@ -13,7 +22,7 @@ function resolveDataDir() {
13
22
  if (process.env.EXE_MEM_DIR) return process.env.EXE_MEM_DIR;
14
23
  const newDir = path.join(os.homedir(), ".exe-os");
15
24
  const legacyDir = path.join(os.homedir(), ".exe-mem");
16
- if (!existsSync(newDir) && existsSync(legacyDir)) {
25
+ if (!existsSync2(newDir) && existsSync2(legacyDir)) {
17
26
  try {
18
27
  renameSync(legacyDir, newDir);
19
28
  process.stderr.write(`[exe-os] Migrated data directory: ~/.exe-mem \u2192 ~/.exe-os
@@ -28,6 +37,7 @@ var EXE_AI_DIR, DB_PATH, MODELS_DIR, CONFIG_PATH, LEGACY_LANCE_PATH, CURRENT_CON
28
37
  var init_config = __esm({
29
38
  "src/lib/config.ts"() {
30
39
  "use strict";
40
+ init_secure_files();
31
41
  EXE_AI_DIR = resolveDataDir();
32
42
  DB_PATH = path.join(EXE_AI_DIR, "memories.db");
33
43
  MODELS_DIR = path.join(EXE_AI_DIR, "models");
@@ -98,8 +108,8 @@ var init_config = __esm({
98
108
  import { readdir } from "fs/promises";
99
109
  import { createReadStream } from "fs";
100
110
  import { createInterface } from "readline";
101
- import path3 from "path";
102
- import os3 from "os";
111
+ import path4 from "path";
112
+ import os4 from "os";
103
113
 
104
114
  // src/lib/database.ts
105
115
  import { createClient } from "@libsql/client";
@@ -107,19 +117,39 @@ import { createClient } from "@libsql/client";
107
117
  // src/lib/employees.ts
108
118
  init_config();
109
119
  import { readFile as readFile2, writeFile as writeFile2, mkdir as mkdir2 } from "fs/promises";
110
- import { existsSync as existsSync2, symlinkSync, readlinkSync, readFileSync as readFileSync2, renameSync as renameSync2, unlinkSync, writeFileSync } from "fs";
120
+ import { existsSync as existsSync3, symlinkSync, readlinkSync, readFileSync as readFileSync2, renameSync as renameSync2, unlinkSync, writeFileSync } from "fs";
111
121
  import { execSync } from "child_process";
112
122
  import path2 from "path";
113
123
  import os2 from "os";
114
124
  var EMPLOYEES_PATH = path2.join(EXE_AI_DIR, "exe-employees.json");
125
+ var IDENTITY_DIR = path2.join(EXE_AI_DIR, "identity");
126
+
127
+ // src/lib/database-adapter.ts
128
+ import os3 from "os";
129
+ import path3 from "path";
130
+ import { createRequire } from "module";
131
+ import { pathToFileURL } from "url";
132
+ var BOOLEAN_COLUMNS_BY_TABLE = {
133
+ memories: /* @__PURE__ */ new Set(["has_error", "draft"]),
134
+ behaviors: /* @__PURE__ */ new Set(["active"]),
135
+ notifications: /* @__PURE__ */ new Set(["read"]),
136
+ users: /* @__PURE__ */ new Set(["has_personal_memory"])
137
+ };
138
+ var BOOLEAN_COLUMN_NAMES = new Set(
139
+ Object.values(BOOLEAN_COLUMNS_BY_TABLE).flatMap((cols) => [...cols])
140
+ );
115
141
 
116
142
  // src/lib/database.ts
117
143
  var _resilientClient = null;
118
144
  var _daemonClient = null;
145
+ var _adapterClient = null;
119
146
  function getClient() {
120
- if (!_resilientClient) {
147
+ if (!_adapterClient) {
121
148
  throw new Error("Database client not initialized. Call initDatabase() first.");
122
149
  }
150
+ if (process.env.DATABASE_URL) {
151
+ return _adapterClient;
152
+ }
123
153
  if (process.env.EXE_IS_DAEMON === "1") {
124
154
  return _resilientClient;
125
155
  }
@@ -155,6 +185,8 @@ var MODEL_PRICING = {
155
185
  "claude-3-haiku": { input: 0.25 / 1e6, output: 1.25 / 1e6, cacheRead: 0.03 / 1e6, cacheWrite: 0.3 / 1e6 }
156
186
  };
157
187
  var DEFAULT_PRICING = MODEL_PRICING["claude-sonnet-4"];
188
+ var CACHE_TTL_MS = 5 * 60 * 1e3;
189
+ var _spendCache = /* @__PURE__ */ new Map();
158
190
  function getPricing(model) {
159
191
  if (MODEL_PRICING[model]) return MODEL_PRICING[model];
160
192
  const stripped = model.replace(/-\d{8}$/, "");
@@ -166,29 +198,33 @@ function getPricing(model) {
166
198
  return DEFAULT_PRICING;
167
199
  }
168
200
  async function getAgentSpend(period = "7d") {
201
+ const cached = _spendCache.get(period);
202
+ if (cached && Date.now() < cached.expires) {
203
+ return cached.result;
204
+ }
169
205
  const cutoff = periodToCutoff(period);
170
206
  const client = getClient();
171
- const result = await client.execute({
207
+ const dbResult = await client.execute({
172
208
  sql: `SELECT session_uuid, agent_id FROM session_agent_map WHERE started_at >= ?`,
173
209
  args: [cutoff]
174
210
  });
175
- if (result.rows.length === 0) return [];
211
+ if (dbResult.rows.length === 0) return [];
176
212
  const sessionAgent = /* @__PURE__ */ new Map();
177
- for (const row of result.rows) {
213
+ for (const row of dbResult.rows) {
178
214
  sessionAgent.set(row.session_uuid, row.agent_id);
179
215
  }
180
- const claudeDir = path3.join(os3.homedir(), ".claude", "projects");
216
+ const claudeDir = path4.join(os4.homedir(), ".claude", "projects");
181
217
  let projectDirs = [];
182
218
  try {
183
219
  const entries = await readdir(claudeDir);
184
- projectDirs = entries.map((e) => path3.join(claudeDir, e));
220
+ projectDirs = entries.map((e) => path4.join(claudeDir, e));
185
221
  } catch {
186
222
  return [];
187
223
  }
188
224
  const agentTotals = /* @__PURE__ */ new Map();
189
225
  for (const [sessionUuid, agentId] of sessionAgent) {
190
226
  for (const dir of projectDirs) {
191
- const jsonlPath = path3.join(dir, `${sessionUuid}.jsonl`);
227
+ const jsonlPath = path4.join(dir, `${sessionUuid}.jsonl`);
192
228
  try {
193
229
  const usage = await extractSessionUsage(jsonlPath);
194
230
  if (usage.input === 0 && usage.output === 0) continue;
@@ -212,7 +248,7 @@ async function getAgentSpend(period = "7d") {
212
248
  }
213
249
  }
214
250
  }
215
- return Array.from(agentTotals.entries()).map(([agentId, t]) => ({
251
+ const result = Array.from(agentTotals.entries()).map(([agentId, t]) => ({
216
252
  agentId,
217
253
  inputTokens: t.input,
218
254
  outputTokens: t.output,
@@ -222,6 +258,8 @@ async function getAgentSpend(period = "7d") {
222
258
  sessions: t.sessions.size,
223
259
  period
224
260
  })).sort((a, b) => b.costUSD - a.costUSD);
261
+ _spendCache.set(period, { result, expires: Date.now() + CACHE_TTL_MS });
262
+ return result;
225
263
  }
226
264
  async function extractSessionUsage(jsonlPath) {
227
265
  let input = 0;