@askexenow/exe-os 0.9.77 → 0.9.78
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/bin/agentic-ontology-backfill.js +2 -2
- package/dist/bin/agentic-reflection-backfill.js +2 -2
- package/dist/bin/agentic-semantic-label.js +2 -2
- package/dist/bin/backfill-conversations.js +2 -2
- package/dist/bin/backfill-responses.js +2 -2
- package/dist/bin/backfill-vectors.js +2 -2
- package/dist/bin/bulk-sync-postgres.js +2 -2
- package/dist/bin/cleanup-stale-review-tasks.js +2 -2
- package/dist/bin/cli.js +759 -524
- package/dist/bin/customer-readiness.js +19 -0
- package/dist/bin/exe-agent.js +2 -2
- package/dist/bin/exe-assign.js +2 -2
- package/dist/bin/exe-boot.js +2 -2
- package/dist/bin/exe-call.js +2 -2
- package/dist/bin/exe-cloud.js +2 -2
- package/dist/bin/exe-dispatch.js +2 -2
- package/dist/bin/exe-doctor.js +2 -2
- package/dist/bin/exe-export-behaviors.js +2 -2
- package/dist/bin/exe-forget.js +2 -2
- package/dist/bin/exe-gateway.js +158 -16
- package/dist/bin/exe-heartbeat.js +2 -2
- package/dist/bin/exe-kill.js +2 -2
- package/dist/bin/exe-launch-agent.js +2 -2
- package/dist/bin/exe-new-employee.js +2 -2
- package/dist/bin/exe-pending-messages.js +2 -2
- package/dist/bin/exe-pending-notifications.js +2 -2
- package/dist/bin/exe-pending-reviews.js +2 -2
- package/dist/bin/exe-rename.js +2 -2
- package/dist/bin/exe-review.js +2 -2
- package/dist/bin/exe-search.js +2 -2
- package/dist/bin/exe-session-cleanup.js +2 -2
- package/dist/bin/exe-start-codex.js +2 -2
- package/dist/bin/exe-start-opencode.js +2 -2
- package/dist/bin/exe-status.js +2 -2
- package/dist/bin/exe-support.js +461 -0
- package/dist/bin/exe-team.js +2 -2
- package/dist/bin/git-sweep.js +2 -2
- package/dist/bin/graph-backfill.js +2 -2
- package/dist/bin/graph-export.js +2 -2
- package/dist/bin/intercom-check.js +2 -2
- package/dist/bin/scan-tasks.js +2 -2
- package/dist/bin/setup.js +3 -2
- package/dist/bin/shard-migrate.js +2 -2
- package/dist/bin/update.js +9 -0
- package/dist/gateway/index.js +2 -2
- package/dist/hooks/bug-report-worker.js +2 -2
- package/dist/hooks/codex-stop-task-finalizer.js +2 -2
- package/dist/hooks/commit-complete.js +2 -2
- package/dist/hooks/error-recall.js +2 -2
- package/dist/hooks/ingest.js +2 -2
- package/dist/hooks/instructions-loaded.js +2 -2
- package/dist/hooks/notification.js +2 -2
- package/dist/hooks/post-compact.js +2 -2
- package/dist/hooks/post-tool-combined.js +2 -2
- package/dist/hooks/pre-compact.js +2 -2
- package/dist/hooks/pre-tool-use.js +2 -2
- package/dist/hooks/prompt-submit.js +2 -2
- package/dist/hooks/session-end.js +2 -2
- package/dist/hooks/session-start.js +2 -2
- package/dist/hooks/stop.js +2 -2
- package/dist/hooks/subagent-stop.js +2 -2
- package/dist/hooks/summary-worker.js +2 -2
- package/dist/index.js +2 -2
- package/dist/lib/employee-templates.js +2 -2
- package/dist/lib/exe-daemon.js +28 -16
- package/dist/lib/hybrid-search.js +2 -2
- package/dist/lib/schedules.js +2 -2
- package/dist/lib/store.js +2 -2
- package/dist/mcp/server.js +27 -15
- package/dist/runtime/index.js +2 -2
- package/dist/tui/App.js +2 -2
- package/package.json +1 -1
package/dist/bin/cli.js
CHANGED
|
@@ -2619,8 +2619,8 @@ function deriveMachineKey() {
|
|
|
2619
2619
|
}
|
|
2620
2620
|
function readMachineId() {
|
|
2621
2621
|
try {
|
|
2622
|
-
const { readFileSync:
|
|
2623
|
-
return
|
|
2622
|
+
const { readFileSync: readFileSync37 } = __require("fs");
|
|
2623
|
+
return readFileSync37("/etc/machine-id", "utf-8").trim();
|
|
2624
2624
|
} catch {
|
|
2625
2625
|
return "";
|
|
2626
2626
|
}
|
|
@@ -8667,7 +8667,7 @@ var init_platform_procedures = __esm({
|
|
|
8667
8667
|
title: "Customer patch triage \u2014 upstream bug vs customization",
|
|
8668
8668
|
domain: "support",
|
|
8669
8669
|
priority: "p0",
|
|
8670
|
-
content: "When an agent encounters a suspected Exe OS bug, update breakage, MCP/tool failure, installer issue, memory/orchestration defect, or customer-local patch need, it MUST use create_bug_report. Do this before or alongside any local workaround so the report reaches AskExe support directly via the customer's license. Do NOT ask the founder for permission to file a required bug report. If create_bug_report is deferred/lazy-loaded, load it and call it. If it is unavailable in the live MCP surface, report 'create_bug_report unavailable in this session' and save a local report in exe/output \u2014 never claim the tool does not exist unless the live MCP surface was checked. Classify first: upstream_bug = reproducible exe-os/platform defect; customer_customization = identity, behavior, procedure, config, branding, workflow preference that belongs in customer-owned layers; emergency_hotfix = temporary local patch. For upstream bugs/emergency hotfixes include version, repro steps, expected/actual, files changed, workaround, and local diff summary. Avoid permanent platform-code patches unless founder approves; if a hotfix is unavoidable, document it in the bug report and re-check after npm update."
|
|
8670
|
+
content: "When an agent encounters a suspected Exe OS bug, update breakage, MCP/tool failure, installer issue, memory/orchestration defect, or customer-local patch need, it MUST use create_bug_report. Do this before or alongside any local workaround so the report reaches AskExe support directly via the customer's license. Do NOT ask the founder for permission to file a required bug report. If create_bug_report is deferred/lazy-loaded, load it and call it. If it is unavailable in the live MCP surface, report 'create_bug_report unavailable in this session' and save a local report in exe/output \u2014 never claim the tool does not exist unless the live MCP surface was checked. If upstream delivery fails, run `exe-os support test` and include its result in the local report so AskExe can distinguish customer setup, license provisioning, and server intake issues. Classify first: upstream_bug = reproducible exe-os/platform defect; customer_customization = identity, behavior, procedure, config, branding, workflow preference that belongs in customer-owned layers; emergency_hotfix = temporary local patch. For upstream bugs/emergency hotfixes include version, repro steps, expected/actual, files changed, workaround, and local diff summary. Avoid permanent platform-code patches unless founder approves; if a hotfix is unavoidable, document it in the bug report and re-check after npm update."
|
|
8671
8671
|
},
|
|
8672
8672
|
// --- Operations ---
|
|
8673
8673
|
{
|
|
@@ -8749,7 +8749,7 @@ var init_platform_procedures = __esm({
|
|
|
8749
8749
|
title: "MCP tools \u2014 identity, behavior, and decisions",
|
|
8750
8750
|
domain: "tool-use",
|
|
8751
8751
|
priority: "p1",
|
|
8752
|
-
content: "get_identity: read an agent's exe.md (Layer 1 identity). update_identity: write an agent's exe.md. Identity > behavior \u2014 use for permanent rules. store_behavior: record a correction or pattern for an agent (Layer 2 expertise). list_behaviors: view an agent's active behaviors. deactivate_behavior: soft-delete a stale or conflicting behavior. store_decision: record an ADR (architectural decision record). get_decision: retrieve a past decision by query. create_bug_report: customer-facing bug/support intake; use whenever an Exe OS bug or emergency hotfix is encountered so the report reaches AskExe directly. Customers only get report access; internal list/get/triage support tools are AskExe-only."
|
|
8752
|
+
content: "get_identity: read an agent's exe.md (Layer 1 identity). update_identity: write an agent's exe.md. Identity > behavior \u2014 use for permanent rules. store_behavior: record a correction or pattern for an agent (Layer 2 expertise). list_behaviors: view an agent's active behaviors. deactivate_behavior: soft-delete a stale or conflicting behavior. store_decision: record an ADR (architectural decision record). get_decision: retrieve a past decision by query. create_bug_report: customer-facing bug/support intake; use whenever an Exe OS bug or emergency hotfix is encountered so the report reaches AskExe directly. Customers only get report access; internal list/get/triage support tools are AskExe-only. If a customer-side agent cannot send upstream, run `exe-os support test` from the terminal to verify local file write, license auth, support endpoint health, and upstream POST."
|
|
8753
8753
|
},
|
|
8754
8754
|
{
|
|
8755
8755
|
title: "MCP tools \u2014 communication and messaging",
|
|
@@ -10945,12 +10945,234 @@ var init_exe_key = __esm({
|
|
|
10945
10945
|
}
|
|
10946
10946
|
});
|
|
10947
10947
|
|
|
10948
|
+
// src/bin/exe-support.ts
|
|
10949
|
+
var exe_support_exports = {};
|
|
10950
|
+
__export(exe_support_exports, {
|
|
10951
|
+
main: () => main4
|
|
10952
|
+
});
|
|
10953
|
+
import { mkdirSync as mkdirSync13, readFileSync as readFileSync14, unlinkSync as unlinkSync7, writeFileSync as writeFileSync13 } from "fs";
|
|
10954
|
+
import path20 from "path";
|
|
10955
|
+
import { randomUUID as randomUUID4 } from "crypto";
|
|
10956
|
+
async function main4(argv = process.argv.slice(2)) {
|
|
10957
|
+
const command = argv[0] && !argv[0].startsWith("--") ? argv[0] : "test";
|
|
10958
|
+
const json = argv.includes("--json");
|
|
10959
|
+
const project = getArg(argv, "--project") ?? "support-smoke";
|
|
10960
|
+
if (command === "health") {
|
|
10961
|
+
const result = await runHealth();
|
|
10962
|
+
output(result, json);
|
|
10963
|
+
process.exitCode = result.some((row) => !row.ok) ? 1 : 0;
|
|
10964
|
+
return;
|
|
10965
|
+
}
|
|
10966
|
+
if (command === "test") {
|
|
10967
|
+
const result = await runTest(project);
|
|
10968
|
+
output(result, json);
|
|
10969
|
+
process.exitCode = result.some((row) => !row.ok) ? 1 : 0;
|
|
10970
|
+
return;
|
|
10971
|
+
}
|
|
10972
|
+
console.error("Usage: exe-os support health|test [--project <name>] [--json]");
|
|
10973
|
+
process.exitCode = 1;
|
|
10974
|
+
}
|
|
10975
|
+
async function runHealth() {
|
|
10976
|
+
const checks = [];
|
|
10977
|
+
const endpoints = await resolveEndpoints();
|
|
10978
|
+
checks.push(checkLocalWrite());
|
|
10979
|
+
checks.push({
|
|
10980
|
+
check: "license_key_present",
|
|
10981
|
+
ok: Boolean(loadLicense()),
|
|
10982
|
+
detail: loadLicense() ? "license.key found" : "missing ~/.exe-os/license.key; run exe-os setup or exe-os cloud setup"
|
|
10983
|
+
});
|
|
10984
|
+
checks.push({
|
|
10985
|
+
check: "license_token_cached",
|
|
10986
|
+
ok: Boolean(readCachedLicenseToken()),
|
|
10987
|
+
detail: readCachedLicenseToken() ? "cached license token found" : "no cached token yet; support can still use license.key"
|
|
10988
|
+
});
|
|
10989
|
+
try {
|
|
10990
|
+
const res = await fetch(endpoints.healthEndpoint, { method: "GET", signal: AbortSignal.timeout(1e4) });
|
|
10991
|
+
const body = await safeJson2(res);
|
|
10992
|
+
checks.push({
|
|
10993
|
+
check: "support_health_endpoint",
|
|
10994
|
+
ok: res.ok && body?.status !== "down",
|
|
10995
|
+
detail: `${res.status} ${body?.status ?? res.statusText}`
|
|
10996
|
+
});
|
|
10997
|
+
for (const remote of body?.checks ?? []) {
|
|
10998
|
+
checks.push({
|
|
10999
|
+
check: `server_${remote.name ?? "unknown"}`,
|
|
11000
|
+
ok: remote.ok === true,
|
|
11001
|
+
detail: remote.detail ?? (remote.ok ? "ok" : "failed")
|
|
11002
|
+
});
|
|
11003
|
+
}
|
|
11004
|
+
} catch (err) {
|
|
11005
|
+
checks.push({
|
|
11006
|
+
check: "support_health_endpoint",
|
|
11007
|
+
ok: false,
|
|
11008
|
+
detail: err instanceof Error ? err.message : String(err)
|
|
11009
|
+
});
|
|
11010
|
+
}
|
|
11011
|
+
return checks;
|
|
11012
|
+
}
|
|
11013
|
+
async function runTest(project) {
|
|
11014
|
+
const checks = await runHealth();
|
|
11015
|
+
const endpoints = await resolveEndpoints();
|
|
11016
|
+
const licenseKey = loadLicense();
|
|
11017
|
+
const licenseToken = readCachedLicenseToken();
|
|
11018
|
+
const id = randomUUID4();
|
|
11019
|
+
const version = readPackageVersion();
|
|
11020
|
+
const reportPath = writeLocalTestReport(id, project, version);
|
|
11021
|
+
checks.push({ check: "local_report_file", ok: true, detail: reportPath });
|
|
11022
|
+
if (!licenseKey && !licenseToken) {
|
|
11023
|
+
checks.push({ check: "upstream_post", ok: false, detail: "missing license key/token" });
|
|
11024
|
+
return checks;
|
|
11025
|
+
}
|
|
11026
|
+
const payload = {
|
|
11027
|
+
id,
|
|
11028
|
+
title: `TEST \u2014 ${project} support intake (${version})`,
|
|
11029
|
+
classification: "unclear",
|
|
11030
|
+
severity: "p3",
|
|
11031
|
+
summary: "Synthetic exe-os support intake smoke test. Safe to close.",
|
|
11032
|
+
customer_impact: "No customer impact; diagnostic only.",
|
|
11033
|
+
reproduction_steps: ["Run exe-os support test"],
|
|
11034
|
+
expected: "The report reaches AskExe support intake and can be triaged.",
|
|
11035
|
+
actual: "Smoke test submitted by exe-os support test.",
|
|
11036
|
+
package_version: `@askexenow/exe-os@${version}`,
|
|
11037
|
+
project_name: project,
|
|
11038
|
+
agent_id: "support-test",
|
|
11039
|
+
agent_role: "diagnostic",
|
|
11040
|
+
report_path: reportPath,
|
|
11041
|
+
markdown: readFileSync14(reportPath, "utf8")
|
|
11042
|
+
};
|
|
11043
|
+
try {
|
|
11044
|
+
const headers = { "content-type": "application/json" };
|
|
11045
|
+
if (licenseKey) headers["x-exe-license-key"] = licenseKey;
|
|
11046
|
+
if (licenseToken) headers["x-exe-license-token"] = licenseToken;
|
|
11047
|
+
const res = await fetch(endpoints.bugEndpoint, {
|
|
11048
|
+
method: "POST",
|
|
11049
|
+
headers,
|
|
11050
|
+
body: JSON.stringify(payload),
|
|
11051
|
+
signal: AbortSignal.timeout(15e3)
|
|
11052
|
+
});
|
|
11053
|
+
const data = await safeJson2(res);
|
|
11054
|
+
checks.push({
|
|
11055
|
+
check: "upstream_post",
|
|
11056
|
+
ok: res.ok,
|
|
11057
|
+
detail: res.ok ? `sent id=${String(data?.id ?? id)}` : `${res.status} ${JSON.stringify(data)}`
|
|
11058
|
+
});
|
|
11059
|
+
if (res.ok) {
|
|
11060
|
+
checks.push(await maybeCloseAdmin(String(data?.id ?? id), endpoints.adminEndpoint, version));
|
|
11061
|
+
}
|
|
11062
|
+
} catch (err) {
|
|
11063
|
+
checks.push({ check: "upstream_post", ok: false, detail: err instanceof Error ? err.message : String(err) });
|
|
11064
|
+
}
|
|
11065
|
+
return checks;
|
|
11066
|
+
}
|
|
11067
|
+
async function resolveEndpoints() {
|
|
11068
|
+
const config = await loadConfig();
|
|
11069
|
+
const bugEndpoint = process.env.EXE_SUPPORT_BUG_REPORT_ENDPOINT ?? config.support?.bugReportEndpoint ?? DEFAULT_BUG_ENDPOINT;
|
|
11070
|
+
const healthEndpoint = process.env.EXE_SUPPORT_HEALTH_ENDPOINT ?? bugEndpoint.replace(/\/bug-reports\/?$/, "/health");
|
|
11071
|
+
const adminEndpoint = process.env.ASKEXE_SUPPORT_ADMIN_ENDPOINT ?? process.env.EXE_SUPPORT_ADMIN_ENDPOINT ?? DEFAULT_ADMIN_ENDPOINT;
|
|
11072
|
+
return { bugEndpoint, healthEndpoint, adminEndpoint };
|
|
11073
|
+
}
|
|
11074
|
+
function checkLocalWrite() {
|
|
11075
|
+
const dir = path20.join(EXE_AI_DIR, "bug-reports");
|
|
11076
|
+
const testPath = path20.join(dir, ".support-write-test");
|
|
11077
|
+
try {
|
|
11078
|
+
mkdirSync13(dir, { recursive: true, mode: 448 });
|
|
11079
|
+
writeFileSync13(testPath, "ok\n", { mode: 384 });
|
|
11080
|
+
unlinkSync7(testPath);
|
|
11081
|
+
return { check: "local_bug_report_dir_writable", ok: true, detail: dir };
|
|
11082
|
+
} catch (err) {
|
|
11083
|
+
return { check: "local_bug_report_dir_writable", ok: false, detail: err instanceof Error ? err.message : String(err) };
|
|
11084
|
+
}
|
|
11085
|
+
}
|
|
11086
|
+
function writeLocalTestReport(id, project, version) {
|
|
11087
|
+
const dir = path20.join(EXE_AI_DIR, "bug-reports");
|
|
11088
|
+
mkdirSync13(dir, { recursive: true, mode: 448 });
|
|
11089
|
+
const date = (/* @__PURE__ */ new Date()).toISOString().slice(0, 10);
|
|
11090
|
+
const filePath = path20.join(dir, `${date}-support-intake-test-${id.slice(0, 8)}.md`);
|
|
11091
|
+
writeFileSync13(filePath, `# TEST \u2014 ${project} support intake
|
|
11092
|
+
|
|
11093
|
+
Report ID: ${id}
|
|
11094
|
+
Package: @askexenow/exe-os@${version}
|
|
11095
|
+
|
|
11096
|
+
Synthetic smoke test from \`exe-os support test\`. Safe to close.
|
|
11097
|
+
`, { mode: 384 });
|
|
11098
|
+
return filePath;
|
|
11099
|
+
}
|
|
11100
|
+
async function maybeCloseAdmin(id, adminEndpoint, version) {
|
|
11101
|
+
const token = process.env.ASKEXE_SUPPORT_ADMIN_TOKEN ?? process.env.EXE_SUPPORT_ADMIN_TOKEN;
|
|
11102
|
+
if (!token) {
|
|
11103
|
+
return { check: "askexe_admin_autoclose", ok: true, detail: "skipped; admin token is AskExe-only" };
|
|
11104
|
+
}
|
|
11105
|
+
try {
|
|
11106
|
+
const res = await fetch(`${adminEndpoint}/${encodeURIComponent(id)}`, {
|
|
11107
|
+
method: "PATCH",
|
|
11108
|
+
headers: { authorization: `Bearer ${token}`, "content-type": "application/json" },
|
|
11109
|
+
body: JSON.stringify({
|
|
11110
|
+
status: "closed",
|
|
11111
|
+
triage_notes: "Auto-closed synthetic support smoke test.",
|
|
11112
|
+
fixed_version: version
|
|
11113
|
+
}),
|
|
11114
|
+
signal: AbortSignal.timeout(1e4)
|
|
11115
|
+
});
|
|
11116
|
+
return { check: "askexe_admin_autoclose", ok: res.ok, detail: res.ok ? "closed" : `${res.status} ${await res.text()}` };
|
|
11117
|
+
} catch (err) {
|
|
11118
|
+
return { check: "askexe_admin_autoclose", ok: false, detail: err instanceof Error ? err.message : String(err) };
|
|
11119
|
+
}
|
|
11120
|
+
}
|
|
11121
|
+
function readPackageVersion() {
|
|
11122
|
+
let dir = path20.dirname(new URL(import.meta.url).pathname);
|
|
11123
|
+
for (let i = 0; i < 6; i++) {
|
|
11124
|
+
const pkg = path20.join(dir, "package.json");
|
|
11125
|
+
try {
|
|
11126
|
+
const parsed = JSON.parse(readFileSync14(pkg, "utf8"));
|
|
11127
|
+
if (parsed.version) return parsed.version;
|
|
11128
|
+
} catch {
|
|
11129
|
+
}
|
|
11130
|
+
dir = path20.dirname(dir);
|
|
11131
|
+
}
|
|
11132
|
+
return "unknown";
|
|
11133
|
+
}
|
|
11134
|
+
async function safeJson2(res) {
|
|
11135
|
+
try {
|
|
11136
|
+
return await res.json();
|
|
11137
|
+
} catch {
|
|
11138
|
+
return null;
|
|
11139
|
+
}
|
|
11140
|
+
}
|
|
11141
|
+
function getArg(argv, name) {
|
|
11142
|
+
const idx = argv.indexOf(name);
|
|
11143
|
+
if (idx >= 0) return argv[idx + 1];
|
|
11144
|
+
const prefix = `${name}=`;
|
|
11145
|
+
const found = argv.find((arg) => arg.startsWith(prefix));
|
|
11146
|
+
return found?.slice(prefix.length);
|
|
11147
|
+
}
|
|
11148
|
+
function output(rows, json) {
|
|
11149
|
+
if (json) {
|
|
11150
|
+
console.log(JSON.stringify({ ok: rows.every((row) => row.ok), checks: rows }, null, 2));
|
|
11151
|
+
return;
|
|
11152
|
+
}
|
|
11153
|
+
console.log("\nexe-os support diagnostics\n");
|
|
11154
|
+
for (const row of rows) {
|
|
11155
|
+
console.log(`${row.ok ? "\u2705" : "\u274C"} ${row.check}: ${row.detail}`);
|
|
11156
|
+
}
|
|
11157
|
+
console.log("");
|
|
11158
|
+
}
|
|
11159
|
+
var DEFAULT_BUG_ENDPOINT, DEFAULT_ADMIN_ENDPOINT;
|
|
11160
|
+
var init_exe_support = __esm({
|
|
11161
|
+
"src/bin/exe-support.ts"() {
|
|
11162
|
+
"use strict";
|
|
11163
|
+
init_config();
|
|
11164
|
+
init_license();
|
|
11165
|
+
DEFAULT_BUG_ENDPOINT = "https://askexe.com/v1/support/bug-reports";
|
|
11166
|
+
DEFAULT_ADMIN_ENDPOINT = "https://askexe.com/admin/support/bug-reports";
|
|
11167
|
+
}
|
|
11168
|
+
});
|
|
11169
|
+
|
|
10948
11170
|
// src/bin/bulk-sync-postgres.ts
|
|
10949
11171
|
var bulk_sync_postgres_exports = {};
|
|
10950
11172
|
__export(bulk_sync_postgres_exports, {
|
|
10951
|
-
main: () =>
|
|
11173
|
+
main: () => main5
|
|
10952
11174
|
});
|
|
10953
|
-
async function
|
|
11175
|
+
async function main5() {
|
|
10954
11176
|
process.env.EXE_IS_DAEMON = "1";
|
|
10955
11177
|
await initStore({ lightweight: true });
|
|
10956
11178
|
const client = getClient();
|
|
@@ -11013,7 +11235,7 @@ var init_bulk_sync_postgres = __esm({
|
|
|
11013
11235
|
init_cloud_sync();
|
|
11014
11236
|
BATCH_SIZE = 500;
|
|
11015
11237
|
if (import.meta.url === `file://${process.argv[1]}`) {
|
|
11016
|
-
|
|
11238
|
+
main5().catch((err) => {
|
|
11017
11239
|
process.stderr.write(`[bulk-sync] FATAL: ${err instanceof Error ? err.message : String(err)}
|
|
11018
11240
|
`);
|
|
11019
11241
|
process.exit(1);
|
|
@@ -11030,12 +11252,12 @@ __export(backfill_conversations_exports, {
|
|
|
11030
11252
|
import crypto6 from "crypto";
|
|
11031
11253
|
import { createReadStream } from "fs";
|
|
11032
11254
|
import { readdir as readdir2, stat } from "fs/promises";
|
|
11033
|
-
import
|
|
11255
|
+
import path21 from "path";
|
|
11034
11256
|
import { createInterface as createInterface3 } from "readline";
|
|
11035
11257
|
import { homedir as homedir3 } from "os";
|
|
11036
11258
|
import { parseArgs } from "util";
|
|
11037
11259
|
async function findJsonlFiles(sinceDate, projectFilter) {
|
|
11038
|
-
const projectsDir =
|
|
11260
|
+
const projectsDir = path21.join(homedir3(), ".claude", "projects");
|
|
11039
11261
|
const files = [];
|
|
11040
11262
|
async function walk(dir, depth = 0) {
|
|
11041
11263
|
if (depth > MAX_WALK_DEPTH) return;
|
|
@@ -11046,7 +11268,7 @@ async function findJsonlFiles(sinceDate, projectFilter) {
|
|
|
11046
11268
|
return;
|
|
11047
11269
|
}
|
|
11048
11270
|
for (const entry of entries) {
|
|
11049
|
-
const full =
|
|
11271
|
+
const full = path21.join(dir, entry.name);
|
|
11050
11272
|
if (entry.isDirectory()) {
|
|
11051
11273
|
if (entry.name === "subagents" || entry.name === "tool-results") continue;
|
|
11052
11274
|
await walk(full, depth + 1);
|
|
@@ -11071,7 +11293,7 @@ async function findJsonlFiles(sinceDate, projectFilter) {
|
|
|
11071
11293
|
if (!entry.isDirectory()) continue;
|
|
11072
11294
|
const decoded = decodeProjectDir(entry.name);
|
|
11073
11295
|
if (decoded.toLowerCase().includes(projectFilter.toLowerCase())) {
|
|
11074
|
-
await walk(
|
|
11296
|
+
await walk(path21.join(projectsDir, entry.name));
|
|
11075
11297
|
}
|
|
11076
11298
|
}
|
|
11077
11299
|
} else {
|
|
@@ -11088,14 +11310,14 @@ function decodeProjectDir(dirName) {
|
|
|
11088
11310
|
return dirName;
|
|
11089
11311
|
}
|
|
11090
11312
|
function projectNameFromPath(filePath) {
|
|
11091
|
-
const projectsDir =
|
|
11092
|
-
const relative =
|
|
11093
|
-
const projectDir = relative.split(
|
|
11313
|
+
const projectsDir = path21.join(homedir3(), ".claude", "projects");
|
|
11314
|
+
const relative = path21.relative(projectsDir, filePath);
|
|
11315
|
+
const projectDir = relative.split(path21.sep)[0] ?? "unknown";
|
|
11094
11316
|
return decodeProjectDir(projectDir);
|
|
11095
11317
|
}
|
|
11096
11318
|
async function parseConversation(filePath) {
|
|
11097
11319
|
const conv = {
|
|
11098
|
-
sessionId:
|
|
11320
|
+
sessionId: path21.basename(filePath, ".jsonl"),
|
|
11099
11321
|
projectName: projectNameFromPath(filePath),
|
|
11100
11322
|
cwd: void 0,
|
|
11101
11323
|
startTime: void 0,
|
|
@@ -11159,7 +11381,7 @@ async function parseConversation(filePath) {
|
|
|
11159
11381
|
}
|
|
11160
11382
|
}
|
|
11161
11383
|
if (conv.cwd) {
|
|
11162
|
-
conv.projectName =
|
|
11384
|
+
conv.projectName = path21.basename(conv.cwd);
|
|
11163
11385
|
const worktreeMatch = conv.cwd.match(/\.worktrees\/([^/]+)/);
|
|
11164
11386
|
if (worktreeMatch?.[1]) {
|
|
11165
11387
|
conv.agentId = worktreeMatch[1];
|
|
@@ -11811,9 +12033,9 @@ Unclassified: ${unclassified}
|
|
|
11811
12033
|
}
|
|
11812
12034
|
async function exportBatches(options) {
|
|
11813
12035
|
const fs8 = await import("fs");
|
|
11814
|
-
const
|
|
12036
|
+
const path56 = await import("path");
|
|
11815
12037
|
const client = getClient();
|
|
11816
|
-
const outDir =
|
|
12038
|
+
const outDir = path56.join(process.cwd(), "exe/output/classifications/input");
|
|
11817
12039
|
fs8.mkdirSync(outDir, { recursive: true });
|
|
11818
12040
|
const countResult = await client.execute({
|
|
11819
12041
|
sql: "SELECT COUNT(*) as cnt FROM memories WHERE intent IS NULL AND outcome IS NULL AND domain IS NULL",
|
|
@@ -11837,7 +12059,7 @@ async function exportBatches(options) {
|
|
|
11837
12059
|
const text = String(row.text || "").replace(/\n/g, " ");
|
|
11838
12060
|
return JSON.stringify({ id: row.id, text });
|
|
11839
12061
|
});
|
|
11840
|
-
const batchFile =
|
|
12062
|
+
const batchFile = path56.join(outDir, `batch-${String(batchNum).padStart(4, "0")}.jsonl`);
|
|
11841
12063
|
fs8.writeFileSync(batchFile, lines.join("\n") + "\n");
|
|
11842
12064
|
exported += batch.rows.length;
|
|
11843
12065
|
offset += options.batchSize;
|
|
@@ -11853,7 +12075,7 @@ async function exportBatches(options) {
|
|
|
11853
12075
|
}
|
|
11854
12076
|
async function importClassifications(importDir) {
|
|
11855
12077
|
const fs8 = await import("fs");
|
|
11856
|
-
const
|
|
12078
|
+
const path56 = await import("path");
|
|
11857
12079
|
const client = getClient();
|
|
11858
12080
|
const files = fs8.readdirSync(importDir).filter((f) => f.endsWith(".jsonl")).sort();
|
|
11859
12081
|
process.stderr.write(`[backfill-metadata] Found ${files.length} JSONL files to import from ${importDir}
|
|
@@ -11861,7 +12083,7 @@ async function importClassifications(importDir) {
|
|
|
11861
12083
|
let imported = 0;
|
|
11862
12084
|
let invalid = 0;
|
|
11863
12085
|
for (const file of files) {
|
|
11864
|
-
const lines = fs8.readFileSync(
|
|
12086
|
+
const lines = fs8.readFileSync(path56.join(importDir, file), "utf-8").split("\n").filter(Boolean);
|
|
11865
12087
|
for (const line of lines) {
|
|
11866
12088
|
try {
|
|
11867
12089
|
const rec = JSON.parse(line);
|
|
@@ -12002,17 +12224,17 @@ __export(identity_exports, {
|
|
|
12002
12224
|
listIdentities: () => listIdentities,
|
|
12003
12225
|
updateIdentity: () => updateIdentity
|
|
12004
12226
|
});
|
|
12005
|
-
import { existsSync as existsSync20, mkdirSync as
|
|
12227
|
+
import { existsSync as existsSync20, mkdirSync as mkdirSync14, readFileSync as readFileSync15, writeFileSync as writeFileSync14 } from "fs";
|
|
12006
12228
|
import { readdirSync as readdirSync4 } from "fs";
|
|
12007
|
-
import
|
|
12229
|
+
import path22 from "path";
|
|
12008
12230
|
import { createHash as createHash5 } from "crypto";
|
|
12009
12231
|
function ensureDir() {
|
|
12010
12232
|
if (!existsSync20(IDENTITY_DIR2)) {
|
|
12011
|
-
|
|
12233
|
+
mkdirSync14(IDENTITY_DIR2, { recursive: true });
|
|
12012
12234
|
}
|
|
12013
12235
|
}
|
|
12014
12236
|
function identityPath(agentId) {
|
|
12015
|
-
return
|
|
12237
|
+
return path22.join(IDENTITY_DIR2, `${agentId}.md`);
|
|
12016
12238
|
}
|
|
12017
12239
|
function sanitizeIdentityBody(body) {
|
|
12018
12240
|
return body.replace(/<!--[\s\S]*?-->/g, "").trim();
|
|
@@ -12057,7 +12279,7 @@ function contentHash(content) {
|
|
|
12057
12279
|
function getIdentity(agentId) {
|
|
12058
12280
|
const filePath = identityPath(agentId);
|
|
12059
12281
|
if (!existsSync20(filePath)) return null;
|
|
12060
|
-
const raw =
|
|
12282
|
+
const raw = readFileSync15(filePath, "utf-8");
|
|
12061
12283
|
const { frontmatter, body } = parseFrontmatter(raw);
|
|
12062
12284
|
return {
|
|
12063
12285
|
agentId,
|
|
@@ -12071,7 +12293,7 @@ async function updateIdentity(agentId, content, updatedBy) {
|
|
|
12071
12293
|
ensureDir();
|
|
12072
12294
|
const filePath = identityPath(agentId);
|
|
12073
12295
|
const hash = contentHash(content);
|
|
12074
|
-
|
|
12296
|
+
writeFileSync14(filePath, content, "utf-8");
|
|
12075
12297
|
try {
|
|
12076
12298
|
const client = getClient();
|
|
12077
12299
|
await client.execute({
|
|
@@ -12129,15 +12351,15 @@ var init_identity = __esm({
|
|
|
12129
12351
|
"use strict";
|
|
12130
12352
|
init_config();
|
|
12131
12353
|
init_database();
|
|
12132
|
-
IDENTITY_DIR2 =
|
|
12354
|
+
IDENTITY_DIR2 = path22.join(EXE_AI_DIR, "identity");
|
|
12133
12355
|
}
|
|
12134
12356
|
});
|
|
12135
12357
|
|
|
12136
12358
|
// src/lib/orchestration-package.ts
|
|
12137
|
-
import { randomUUID as
|
|
12138
|
-
import { copyFileSync as copyFileSync4, existsSync as existsSync21, mkdirSync as
|
|
12359
|
+
import { randomUUID as randomUUID5 } from "crypto";
|
|
12360
|
+
import { copyFileSync as copyFileSync4, existsSync as existsSync21, mkdirSync as mkdirSync15, readFileSync as readFileSync16, writeFileSync as writeFileSync15 } from "fs";
|
|
12139
12361
|
import os13 from "os";
|
|
12140
|
-
import
|
|
12362
|
+
import path23 from "path";
|
|
12141
12363
|
function ensureObject(value, label) {
|
|
12142
12364
|
if (value == null || Array.isArray(value) || typeof value !== "object") {
|
|
12143
12365
|
throw new Error(`${label} must be an object`);
|
|
@@ -12196,15 +12418,15 @@ function validateProcedureEntry(value, index) {
|
|
|
12196
12418
|
};
|
|
12197
12419
|
}
|
|
12198
12420
|
function getRosterPath() {
|
|
12199
|
-
return
|
|
12421
|
+
return path23.join(os13.homedir(), EXE_OS_DIRNAME, ROSTER_FILENAME);
|
|
12200
12422
|
}
|
|
12201
12423
|
function getBackupPath() {
|
|
12202
|
-
return
|
|
12424
|
+
return path23.join(os13.homedir(), EXE_OS_DIRNAME, ROSTER_BACKUP_FILENAME);
|
|
12203
12425
|
}
|
|
12204
12426
|
function readRosterFile() {
|
|
12205
12427
|
const rosterPath = getRosterPath();
|
|
12206
12428
|
if (!existsSync21(rosterPath)) return [];
|
|
12207
|
-
const raw =
|
|
12429
|
+
const raw = readFileSync16(rosterPath, "utf-8");
|
|
12208
12430
|
const parsed = JSON.parse(raw);
|
|
12209
12431
|
if (!Array.isArray(parsed)) {
|
|
12210
12432
|
throw new Error("Roster file must contain a JSON array");
|
|
@@ -12216,7 +12438,7 @@ function writeRosterFile(roster) {
|
|
|
12216
12438
|
throw new Error("Refusing to write empty roster \u2014 this would delete all employees");
|
|
12217
12439
|
}
|
|
12218
12440
|
const rosterPath = getRosterPath();
|
|
12219
|
-
|
|
12441
|
+
mkdirSync15(path23.dirname(rosterPath), { recursive: true });
|
|
12220
12442
|
if (existsSync21(rosterPath)) {
|
|
12221
12443
|
const currentRoster = readRosterFile();
|
|
12222
12444
|
if (roster.length < currentRoster.length) {
|
|
@@ -12226,7 +12448,7 @@ function writeRosterFile(roster) {
|
|
|
12226
12448
|
}
|
|
12227
12449
|
copyFileSync4(rosterPath, getBackupPath());
|
|
12228
12450
|
}
|
|
12229
|
-
|
|
12451
|
+
writeFileSync15(rosterPath, `${JSON.stringify(roster, null, 2)}
|
|
12230
12452
|
`, "utf-8");
|
|
12231
12453
|
}
|
|
12232
12454
|
function buildImportedRosterEntries(roster, timestamp) {
|
|
@@ -12246,7 +12468,7 @@ async function insertBehaviors(behaviors, timestamp) {
|
|
|
12246
12468
|
sql: `INSERT INTO behaviors (id, agent_id, project_name, domain, priority, content, active, created_at, updated_at)
|
|
12247
12469
|
VALUES (?, ?, ?, ?, ?, ?, 1, ?, ?)`,
|
|
12248
12470
|
args: [
|
|
12249
|
-
|
|
12471
|
+
randomUUID5(),
|
|
12250
12472
|
behavior.agent_id,
|
|
12251
12473
|
behavior.project_name,
|
|
12252
12474
|
behavior.domain,
|
|
@@ -12271,7 +12493,7 @@ async function insertProcedures(procedures, timestamp, options) {
|
|
|
12271
12493
|
sql: `INSERT INTO company_procedures (id, title, content, priority, domain, active, created_at, updated_at)
|
|
12272
12494
|
VALUES (?, ?, ?, ?, ?, 1, ?, ?)`,
|
|
12273
12495
|
args: [
|
|
12274
|
-
|
|
12496
|
+
randomUUID5(),
|
|
12275
12497
|
procedure.title,
|
|
12276
12498
|
procedure.content,
|
|
12277
12499
|
procedure.priority,
|
|
@@ -12493,8 +12715,8 @@ var exe_export_exports = {};
|
|
|
12493
12715
|
__export(exe_export_exports, {
|
|
12494
12716
|
runExeExport: () => runExeExport
|
|
12495
12717
|
});
|
|
12496
|
-
import { mkdirSync as
|
|
12497
|
-
import
|
|
12718
|
+
import { mkdirSync as mkdirSync16, writeFileSync as writeFileSync16 } from "fs";
|
|
12719
|
+
import path24 from "path";
|
|
12498
12720
|
function printUsage() {
|
|
12499
12721
|
process.stdout.write("Usage: exe-os export --output <path>\n");
|
|
12500
12722
|
}
|
|
@@ -12515,8 +12737,8 @@ async function runExeExport(argv = process.argv.slice(2)) {
|
|
|
12515
12737
|
await initStore();
|
|
12516
12738
|
try {
|
|
12517
12739
|
const pkg = await exportOrchestration("cli");
|
|
12518
|
-
|
|
12519
|
-
|
|
12740
|
+
mkdirSync16(path24.dirname(outputPath), { recursive: true });
|
|
12741
|
+
writeFileSync16(outputPath, `${JSON.stringify(pkg, null, 2)}
|
|
12520
12742
|
`, "utf-8");
|
|
12521
12743
|
process.stdout.write(
|
|
12522
12744
|
`Exported ${pkg.roster.length} roster entries, ${Object.keys(pkg.identities).length} identities, ${pkg.behaviors.length} behaviors, ${pkg.procedures.length} procedures to ${outputPath}
|
|
@@ -12552,7 +12774,7 @@ var exe_import_exports = {};
|
|
|
12552
12774
|
__export(exe_import_exports, {
|
|
12553
12775
|
runExeImport: () => runExeImport
|
|
12554
12776
|
});
|
|
12555
|
-
import { readFileSync as
|
|
12777
|
+
import { readFileSync as readFileSync17 } from "fs";
|
|
12556
12778
|
function printUsage2() {
|
|
12557
12779
|
process.stdout.write("Usage: exe-os import --from <path> [--merge]\n");
|
|
12558
12780
|
}
|
|
@@ -12575,7 +12797,7 @@ async function runExeImport(argv = process.argv.slice(2)) {
|
|
|
12575
12797
|
if (parsed == null) return;
|
|
12576
12798
|
await initStore();
|
|
12577
12799
|
try {
|
|
12578
|
-
const raw =
|
|
12800
|
+
const raw = readFileSync17(parsed.packagePath, "utf-8");
|
|
12579
12801
|
const pkg = validatePackage(JSON.parse(raw));
|
|
12580
12802
|
const result = await importOrchestration(pkg, parsed.strategy);
|
|
12581
12803
|
process.stdout.write(
|
|
@@ -12616,14 +12838,14 @@ __export(session_registry_exports, {
|
|
|
12616
12838
|
refreshSessionProject: () => refreshSessionProject,
|
|
12617
12839
|
registerSession: () => registerSession
|
|
12618
12840
|
});
|
|
12619
|
-
import { readFileSync as
|
|
12841
|
+
import { readFileSync as readFileSync18, writeFileSync as writeFileSync17, mkdirSync as mkdirSync17, existsSync as existsSync22 } from "fs";
|
|
12620
12842
|
import { execSync as execSync5 } from "child_process";
|
|
12621
|
-
import
|
|
12843
|
+
import path25 from "path";
|
|
12622
12844
|
import os14 from "os";
|
|
12623
12845
|
function registerSession(entry) {
|
|
12624
|
-
const dir =
|
|
12846
|
+
const dir = path25.dirname(REGISTRY_PATH);
|
|
12625
12847
|
if (!existsSync22(dir)) {
|
|
12626
|
-
|
|
12848
|
+
mkdirSync17(dir, { recursive: true });
|
|
12627
12849
|
}
|
|
12628
12850
|
const sessions = listSessions();
|
|
12629
12851
|
const idx = sessions.findIndex((s) => s.windowName === entry.windowName);
|
|
@@ -12632,7 +12854,7 @@ function registerSession(entry) {
|
|
|
12632
12854
|
} else {
|
|
12633
12855
|
sessions.push(entry);
|
|
12634
12856
|
}
|
|
12635
|
-
|
|
12857
|
+
writeFileSync17(REGISTRY_PATH, JSON.stringify(sessions, null, 2));
|
|
12636
12858
|
}
|
|
12637
12859
|
function refreshSessionProject(windowName, projectDir) {
|
|
12638
12860
|
const sessions = listSessions();
|
|
@@ -12640,13 +12862,13 @@ function refreshSessionProject(windowName, projectDir) {
|
|
|
12640
12862
|
if (!entry || entry.projectDir === projectDir) return;
|
|
12641
12863
|
entry.projectDir = projectDir;
|
|
12642
12864
|
try {
|
|
12643
|
-
|
|
12865
|
+
writeFileSync17(REGISTRY_PATH, JSON.stringify(sessions, null, 2));
|
|
12644
12866
|
} catch {
|
|
12645
12867
|
}
|
|
12646
12868
|
}
|
|
12647
12869
|
function listSessions() {
|
|
12648
12870
|
try {
|
|
12649
|
-
const raw =
|
|
12871
|
+
const raw = readFileSync18(REGISTRY_PATH, "utf8");
|
|
12650
12872
|
return JSON.parse(raw);
|
|
12651
12873
|
} catch {
|
|
12652
12874
|
return [];
|
|
@@ -12667,7 +12889,7 @@ function pruneStaleSessions() {
|
|
|
12667
12889
|
const alive = sessions.filter((s) => liveSet.has(s.windowName));
|
|
12668
12890
|
const pruned = sessions.length - alive.length;
|
|
12669
12891
|
if (pruned > 0) {
|
|
12670
|
-
|
|
12892
|
+
writeFileSync17(REGISTRY_PATH, JSON.stringify(alive, null, 2));
|
|
12671
12893
|
}
|
|
12672
12894
|
return pruned;
|
|
12673
12895
|
}
|
|
@@ -12675,7 +12897,7 @@ var REGISTRY_PATH;
|
|
|
12675
12897
|
var init_session_registry = __esm({
|
|
12676
12898
|
"src/lib/session-registry.ts"() {
|
|
12677
12899
|
"use strict";
|
|
12678
|
-
REGISTRY_PATH =
|
|
12900
|
+
REGISTRY_PATH = path25.join(os14.homedir(), ".exe-os", "session-registry.json");
|
|
12679
12901
|
}
|
|
12680
12902
|
});
|
|
12681
12903
|
|
|
@@ -12931,17 +13153,17 @@ __export(intercom_queue_exports, {
|
|
|
12931
13153
|
queueIntercom: () => queueIntercom,
|
|
12932
13154
|
readQueue: () => readQueue
|
|
12933
13155
|
});
|
|
12934
|
-
import { readFileSync as
|
|
12935
|
-
import
|
|
13156
|
+
import { readFileSync as readFileSync19, writeFileSync as writeFileSync18, renameSync as renameSync5, existsSync as existsSync23, mkdirSync as mkdirSync18 } from "fs";
|
|
13157
|
+
import path26 from "path";
|
|
12936
13158
|
import os15 from "os";
|
|
12937
13159
|
function ensureDir2() {
|
|
12938
|
-
const dir =
|
|
12939
|
-
if (!existsSync23(dir))
|
|
13160
|
+
const dir = path26.dirname(QUEUE_PATH);
|
|
13161
|
+
if (!existsSync23(dir)) mkdirSync18(dir, { recursive: true });
|
|
12940
13162
|
}
|
|
12941
13163
|
function readQueue() {
|
|
12942
13164
|
try {
|
|
12943
13165
|
if (!existsSync23(QUEUE_PATH)) return [];
|
|
12944
|
-
return JSON.parse(
|
|
13166
|
+
return JSON.parse(readFileSync19(QUEUE_PATH, "utf8"));
|
|
12945
13167
|
} catch {
|
|
12946
13168
|
return [];
|
|
12947
13169
|
}
|
|
@@ -12949,7 +13171,7 @@ function readQueue() {
|
|
|
12949
13171
|
function writeQueue(queue) {
|
|
12950
13172
|
ensureDir2();
|
|
12951
13173
|
const tmp = `${QUEUE_PATH}.tmp`;
|
|
12952
|
-
|
|
13174
|
+
writeFileSync18(tmp, JSON.stringify(queue, null, 2));
|
|
12953
13175
|
renameSync5(tmp, QUEUE_PATH);
|
|
12954
13176
|
}
|
|
12955
13177
|
function queueIntercom(targetSession, reason) {
|
|
@@ -13041,20 +13263,20 @@ var QUEUE_PATH, MAX_RETRIES2, TTL_MS, INTERCOM_LOG;
|
|
|
13041
13263
|
var init_intercom_queue = __esm({
|
|
13042
13264
|
"src/lib/intercom-queue.ts"() {
|
|
13043
13265
|
"use strict";
|
|
13044
|
-
QUEUE_PATH =
|
|
13266
|
+
QUEUE_PATH = path26.join(os15.homedir(), ".exe-os", "intercom-queue.json");
|
|
13045
13267
|
MAX_RETRIES2 = 5;
|
|
13046
13268
|
TTL_MS = 60 * 60 * 1e3;
|
|
13047
|
-
INTERCOM_LOG =
|
|
13269
|
+
INTERCOM_LOG = path26.join(os15.homedir(), ".exe-os", "intercom.log");
|
|
13048
13270
|
}
|
|
13049
13271
|
});
|
|
13050
13272
|
|
|
13051
13273
|
// src/lib/plan-limits.ts
|
|
13052
|
-
import { readFileSync as
|
|
13053
|
-
import
|
|
13274
|
+
import { readFileSync as readFileSync20, existsSync as existsSync24 } from "fs";
|
|
13275
|
+
import path27 from "path";
|
|
13054
13276
|
function getLicenseSync() {
|
|
13055
13277
|
try {
|
|
13056
13278
|
if (!existsSync24(CACHE_PATH2)) return freeLicense();
|
|
13057
|
-
const raw = JSON.parse(
|
|
13279
|
+
const raw = JSON.parse(readFileSync20(CACHE_PATH2, "utf8"));
|
|
13058
13280
|
if (!raw.token || typeof raw.token !== "string") return freeLicense();
|
|
13059
13281
|
const parts = raw.token.split(".");
|
|
13060
13282
|
if (parts.length !== 3) return freeLicense();
|
|
@@ -13093,7 +13315,7 @@ function assertEmployeeLimitSync(rosterPath) {
|
|
|
13093
13315
|
let count = 0;
|
|
13094
13316
|
try {
|
|
13095
13317
|
if (existsSync24(filePath)) {
|
|
13096
|
-
const raw =
|
|
13318
|
+
const raw = readFileSync20(filePath, "utf8");
|
|
13097
13319
|
const employees = JSON.parse(raw);
|
|
13098
13320
|
count = Array.isArray(employees) ? employees.length : 0;
|
|
13099
13321
|
}
|
|
@@ -13122,7 +13344,7 @@ var init_plan_limits = __esm({
|
|
|
13122
13344
|
this.name = "PlanLimitError";
|
|
13123
13345
|
}
|
|
13124
13346
|
};
|
|
13125
|
-
CACHE_PATH2 =
|
|
13347
|
+
CACHE_PATH2 = path27.join(EXE_AI_DIR, "license-cache.json");
|
|
13126
13348
|
}
|
|
13127
13349
|
});
|
|
13128
13350
|
|
|
@@ -13167,12 +13389,12 @@ var init_task_scope = __esm({
|
|
|
13167
13389
|
|
|
13168
13390
|
// src/lib/notifications.ts
|
|
13169
13391
|
import crypto7 from "crypto";
|
|
13170
|
-
import
|
|
13392
|
+
import path28 from "path";
|
|
13171
13393
|
import os16 from "os";
|
|
13172
13394
|
import {
|
|
13173
|
-
readFileSync as
|
|
13395
|
+
readFileSync as readFileSync21,
|
|
13174
13396
|
readdirSync as readdirSync5,
|
|
13175
|
-
unlinkSync as
|
|
13397
|
+
unlinkSync as unlinkSync8,
|
|
13176
13398
|
existsSync as existsSync25,
|
|
13177
13399
|
rmdirSync
|
|
13178
13400
|
} from "fs";
|
|
@@ -13258,7 +13480,7 @@ var init_session_kill_telemetry = __esm({
|
|
|
13258
13480
|
|
|
13259
13481
|
// src/lib/project-name.ts
|
|
13260
13482
|
import { execSync as execSync8 } from "child_process";
|
|
13261
|
-
import
|
|
13483
|
+
import path29 from "path";
|
|
13262
13484
|
function getProjectName(cwd2) {
|
|
13263
13485
|
const dir = cwd2 ?? process.cwd();
|
|
13264
13486
|
if (_cached2 && _cachedCwd === dir) return _cached2;
|
|
@@ -13271,7 +13493,7 @@ function getProjectName(cwd2) {
|
|
|
13271
13493
|
timeout: 2e3,
|
|
13272
13494
|
stdio: ["pipe", "pipe", "pipe"]
|
|
13273
13495
|
}).trim();
|
|
13274
|
-
repoRoot =
|
|
13496
|
+
repoRoot = path29.dirname(gitCommonDir);
|
|
13275
13497
|
} catch {
|
|
13276
13498
|
repoRoot = execSync8("git rev-parse --show-toplevel", {
|
|
13277
13499
|
cwd: dir,
|
|
@@ -13280,11 +13502,11 @@ function getProjectName(cwd2) {
|
|
|
13280
13502
|
stdio: ["pipe", "pipe", "pipe"]
|
|
13281
13503
|
}).trim();
|
|
13282
13504
|
}
|
|
13283
|
-
_cached2 =
|
|
13505
|
+
_cached2 = path29.basename(repoRoot);
|
|
13284
13506
|
_cachedCwd = dir;
|
|
13285
13507
|
return _cached2;
|
|
13286
13508
|
} catch {
|
|
13287
|
-
_cached2 =
|
|
13509
|
+
_cached2 = path29.basename(dir);
|
|
13288
13510
|
_cachedCwd = dir;
|
|
13289
13511
|
return _cached2;
|
|
13290
13512
|
}
|
|
@@ -13378,11 +13600,11 @@ __export(tasks_crud_exports, {
|
|
|
13378
13600
|
writeCheckpoint: () => writeCheckpoint
|
|
13379
13601
|
});
|
|
13380
13602
|
import crypto9 from "crypto";
|
|
13381
|
-
import
|
|
13603
|
+
import path30 from "path";
|
|
13382
13604
|
import os17 from "os";
|
|
13383
13605
|
import { execSync as execSync9 } from "child_process";
|
|
13384
13606
|
import { mkdir as mkdir5, writeFile as writeFile5, appendFile } from "fs/promises";
|
|
13385
|
-
import { existsSync as existsSync26, readFileSync as
|
|
13607
|
+
import { existsSync as existsSync26, readFileSync as readFileSync22 } from "fs";
|
|
13386
13608
|
async function writeCheckpoint(input) {
|
|
13387
13609
|
const client = getClient();
|
|
13388
13610
|
const row = await resolveTask(client, input.taskId);
|
|
@@ -13581,8 +13803,8 @@ ${scopeMismatchWarning}` : scopeMismatchWarning;
|
|
|
13581
13803
|
}
|
|
13582
13804
|
if (input.baseDir) {
|
|
13583
13805
|
try {
|
|
13584
|
-
await mkdir5(
|
|
13585
|
-
await mkdir5(
|
|
13806
|
+
await mkdir5(path30.join(input.baseDir, "exe", "output"), { recursive: true });
|
|
13807
|
+
await mkdir5(path30.join(input.baseDir, "exe", "research"), { recursive: true });
|
|
13586
13808
|
await ensureArchitectureDoc(input.baseDir, input.projectName);
|
|
13587
13809
|
await ensureGitignoreExe(input.baseDir);
|
|
13588
13810
|
} catch {
|
|
@@ -13618,9 +13840,9 @@ ${scopeMismatchWarning}` : scopeMismatchWarning;
|
|
|
13618
13840
|
});
|
|
13619
13841
|
if (input.baseDir) {
|
|
13620
13842
|
try {
|
|
13621
|
-
const EXE_OS_DIR =
|
|
13622
|
-
const mdPath =
|
|
13623
|
-
const mdDir =
|
|
13843
|
+
const EXE_OS_DIR = path30.join(os17.homedir(), ".exe-os");
|
|
13844
|
+
const mdPath = path30.join(EXE_OS_DIR, taskFile);
|
|
13845
|
+
const mdDir = path30.dirname(mdPath);
|
|
13624
13846
|
if (!existsSync26(mdDir)) await mkdir5(mdDir, { recursive: true });
|
|
13625
13847
|
const reviewer = input.reviewer ?? input.assignedBy;
|
|
13626
13848
|
const mdContent = `# ${input.title}
|
|
@@ -13725,12 +13947,12 @@ function isTmuxSessionAlive(identifier) {
|
|
|
13725
13947
|
if (!identifier || identifier === "unknown") return true;
|
|
13726
13948
|
try {
|
|
13727
13949
|
if (identifier.startsWith("%")) {
|
|
13728
|
-
const
|
|
13950
|
+
const output2 = execSync9("tmux list-panes -a -F '#{pane_id}'", {
|
|
13729
13951
|
timeout: 2e3,
|
|
13730
13952
|
encoding: "utf8",
|
|
13731
13953
|
stdio: ["pipe", "pipe", "pipe"]
|
|
13732
13954
|
});
|
|
13733
|
-
return
|
|
13955
|
+
return output2.split("\n").some((l) => l.trim() === identifier);
|
|
13734
13956
|
} else {
|
|
13735
13957
|
execSync9(`tmux has-session -t ${JSON.stringify(identifier)}`, {
|
|
13736
13958
|
timeout: 2e3,
|
|
@@ -13921,7 +14143,7 @@ async function deleteTaskCore(taskId, _baseDir) {
|
|
|
13921
14143
|
return { taskFile, assignedTo, assignedBy, taskSlug };
|
|
13922
14144
|
}
|
|
13923
14145
|
async function ensureArchitectureDoc(baseDir, projectName) {
|
|
13924
|
-
const archPath =
|
|
14146
|
+
const archPath = path30.join(baseDir, "exe", "ARCHITECTURE.md");
|
|
13925
14147
|
try {
|
|
13926
14148
|
if (existsSync26(archPath)) return;
|
|
13927
14149
|
const template = [
|
|
@@ -13956,10 +14178,10 @@ async function ensureArchitectureDoc(baseDir, projectName) {
|
|
|
13956
14178
|
}
|
|
13957
14179
|
}
|
|
13958
14180
|
async function ensureGitignoreExe(baseDir) {
|
|
13959
|
-
const gitignorePath =
|
|
14181
|
+
const gitignorePath = path30.join(baseDir, ".gitignore");
|
|
13960
14182
|
try {
|
|
13961
14183
|
if (existsSync26(gitignorePath)) {
|
|
13962
|
-
const content =
|
|
14184
|
+
const content = readFileSync22(gitignorePath, "utf-8");
|
|
13963
14185
|
if (/^\/?exe\/?$/m.test(content)) return;
|
|
13964
14186
|
await appendFile(gitignorePath, "\n# Employee task assignments (private)\n/exe/\n");
|
|
13965
14187
|
} else {
|
|
@@ -14002,8 +14224,8 @@ __export(tasks_review_exports, {
|
|
|
14002
14224
|
isStale: () => isStale,
|
|
14003
14225
|
listPendingReviews: () => listPendingReviews
|
|
14004
14226
|
});
|
|
14005
|
-
import
|
|
14006
|
-
import { existsSync as existsSync27, readdirSync as readdirSync6, unlinkSync as
|
|
14227
|
+
import path31 from "path";
|
|
14228
|
+
import { existsSync as existsSync27, readdirSync as readdirSync6, unlinkSync as unlinkSync9 } from "fs";
|
|
14007
14229
|
function formatAge(isoTimestamp) {
|
|
14008
14230
|
if (!isoTimestamp) return "";
|
|
14009
14231
|
const ms = Date.now() - new Date(isoTimestamp).getTime();
|
|
@@ -14272,11 +14494,11 @@ async function cleanupReviewFile(row, taskFile, _baseDir) {
|
|
|
14272
14494
|
);
|
|
14273
14495
|
}
|
|
14274
14496
|
try {
|
|
14275
|
-
const cacheDir =
|
|
14497
|
+
const cacheDir = path31.join(EXE_AI_DIR, "session-cache");
|
|
14276
14498
|
if (existsSync27(cacheDir)) {
|
|
14277
14499
|
for (const f of readdirSync6(cacheDir)) {
|
|
14278
14500
|
if (f.startsWith("review-notified-")) {
|
|
14279
|
-
|
|
14501
|
+
unlinkSync9(path31.join(cacheDir, f));
|
|
14280
14502
|
}
|
|
14281
14503
|
}
|
|
14282
14504
|
}
|
|
@@ -14298,7 +14520,7 @@ var init_tasks_review = __esm({
|
|
|
14298
14520
|
});
|
|
14299
14521
|
|
|
14300
14522
|
// src/lib/tasks-chain.ts
|
|
14301
|
-
import
|
|
14523
|
+
import path32 from "path";
|
|
14302
14524
|
import { readFile as readFile5, writeFile as writeFile6 } from "fs/promises";
|
|
14303
14525
|
async function cascadeUnblock(taskId, baseDir, now2) {
|
|
14304
14526
|
const client = getClient();
|
|
@@ -14315,7 +14537,7 @@ async function cascadeUnblock(taskId, baseDir, now2) {
|
|
|
14315
14537
|
});
|
|
14316
14538
|
for (const ur of unblockedRows.rows) {
|
|
14317
14539
|
try {
|
|
14318
|
-
const ubFile =
|
|
14540
|
+
const ubFile = path32.join(baseDir, String(ur.task_file));
|
|
14319
14541
|
let ubContent = await readFile5(ubFile, "utf-8");
|
|
14320
14542
|
ubContent = ubContent.replace(/\*\*Status:\*\* blocked/, "**Status:** open");
|
|
14321
14543
|
ubContent = ubContent.replace(/\n\*\*Blocked by:\*\*.*\n/, "\n");
|
|
@@ -14500,8 +14722,8 @@ async function embedDirect(text) {
|
|
|
14500
14722
|
const llamaCpp = await import("node-llama-cpp");
|
|
14501
14723
|
const { MODELS_DIR: MODELS_DIR2 } = await Promise.resolve().then(() => (init_config(), config_exports));
|
|
14502
14724
|
const { existsSync: existsSync41 } = await import("fs");
|
|
14503
|
-
const
|
|
14504
|
-
const modelPath =
|
|
14725
|
+
const path56 = await import("path");
|
|
14726
|
+
const modelPath = path56.join(MODELS_DIR2, "jina-embeddings-v5-small-q4_k_m.gguf");
|
|
14505
14727
|
if (!existsSync41(modelPath)) {
|
|
14506
14728
|
throw new Error(`Embedding model not found at ${modelPath}. Run '/exe-setup' to download it.`);
|
|
14507
14729
|
}
|
|
@@ -14868,8 +15090,8 @@ __export(tasks_exports, {
|
|
|
14868
15090
|
updateTaskStatus: () => updateTaskStatus,
|
|
14869
15091
|
writeCheckpoint: () => writeCheckpoint
|
|
14870
15092
|
});
|
|
14871
|
-
import
|
|
14872
|
-
import { writeFileSync as
|
|
15093
|
+
import path33 from "path";
|
|
15094
|
+
import { writeFileSync as writeFileSync19, mkdirSync as mkdirSync19, unlinkSync as unlinkSync10 } from "fs";
|
|
14873
15095
|
async function createTask(input) {
|
|
14874
15096
|
const result = await createTaskCore(input);
|
|
14875
15097
|
if (!input.skipDispatch && result.status !== "blocked" && !process.env.VITEST) {
|
|
@@ -14888,14 +15110,14 @@ async function updateTask(input) {
|
|
|
14888
15110
|
const { row, taskFile, now: now2, taskId } = await updateTaskStatus(input);
|
|
14889
15111
|
try {
|
|
14890
15112
|
const agent = String(row.assigned_to);
|
|
14891
|
-
const cacheDir =
|
|
14892
|
-
const cachePath =
|
|
15113
|
+
const cacheDir = path33.join(EXE_AI_DIR, "session-cache");
|
|
15114
|
+
const cachePath = path33.join(cacheDir, `current-task-${agent}.json`);
|
|
14893
15115
|
if (input.status === "in_progress") {
|
|
14894
|
-
|
|
14895
|
-
|
|
15116
|
+
mkdirSync19(cacheDir, { recursive: true });
|
|
15117
|
+
writeFileSync19(cachePath, JSON.stringify({ taskId, title: String(row.title) }));
|
|
14896
15118
|
} else if (input.status === "done" || input.status === "blocked" || input.status === "cancelled" || input.status === "closed") {
|
|
14897
15119
|
try {
|
|
14898
|
-
|
|
15120
|
+
unlinkSync10(cachePath);
|
|
14899
15121
|
} catch {
|
|
14900
15122
|
}
|
|
14901
15123
|
}
|
|
@@ -15361,13 +15583,13 @@ __export(tmux_routing_exports, {
|
|
|
15361
15583
|
verifyPaneAtCapacity: () => verifyPaneAtCapacity
|
|
15362
15584
|
});
|
|
15363
15585
|
import { execFileSync as execFileSync3, execSync as execSync10 } from "child_process";
|
|
15364
|
-
import { readFileSync as
|
|
15365
|
-
import
|
|
15586
|
+
import { readFileSync as readFileSync23, writeFileSync as writeFileSync20, mkdirSync as mkdirSync20, existsSync as existsSync28, appendFileSync as appendFileSync2, readdirSync as readdirSync7 } from "fs";
|
|
15587
|
+
import path34 from "path";
|
|
15366
15588
|
import os18 from "os";
|
|
15367
15589
|
import { fileURLToPath as fileURLToPath4 } from "url";
|
|
15368
|
-
import { unlinkSync as
|
|
15590
|
+
import { unlinkSync as unlinkSync11 } from "fs";
|
|
15369
15591
|
function spawnLockPath(sessionName) {
|
|
15370
|
-
return
|
|
15592
|
+
return path34.join(SPAWN_LOCK_DIR, `${sessionName}.lock`);
|
|
15371
15593
|
}
|
|
15372
15594
|
function isProcessAlive(pid) {
|
|
15373
15595
|
try {
|
|
@@ -15379,12 +15601,12 @@ function isProcessAlive(pid) {
|
|
|
15379
15601
|
}
|
|
15380
15602
|
function acquireSpawnLock2(sessionName) {
|
|
15381
15603
|
if (!existsSync28(SPAWN_LOCK_DIR)) {
|
|
15382
|
-
|
|
15604
|
+
mkdirSync20(SPAWN_LOCK_DIR, { recursive: true });
|
|
15383
15605
|
}
|
|
15384
15606
|
const lockFile = spawnLockPath(sessionName);
|
|
15385
15607
|
if (existsSync28(lockFile)) {
|
|
15386
15608
|
try {
|
|
15387
|
-
const lock = JSON.parse(
|
|
15609
|
+
const lock = JSON.parse(readFileSync23(lockFile, "utf8"));
|
|
15388
15610
|
const age = Date.now() - lock.timestamp;
|
|
15389
15611
|
if (isProcessAlive(lock.pid) && age < 6e4) {
|
|
15390
15612
|
return false;
|
|
@@ -15392,20 +15614,20 @@ function acquireSpawnLock2(sessionName) {
|
|
|
15392
15614
|
} catch {
|
|
15393
15615
|
}
|
|
15394
15616
|
}
|
|
15395
|
-
|
|
15617
|
+
writeFileSync20(lockFile, JSON.stringify({ pid: process.pid, timestamp: Date.now() }));
|
|
15396
15618
|
return true;
|
|
15397
15619
|
}
|
|
15398
15620
|
function releaseSpawnLock2(sessionName) {
|
|
15399
15621
|
try {
|
|
15400
|
-
|
|
15622
|
+
unlinkSync11(spawnLockPath(sessionName));
|
|
15401
15623
|
} catch {
|
|
15402
15624
|
}
|
|
15403
15625
|
}
|
|
15404
15626
|
function resolveBehaviorsExporterScript() {
|
|
15405
15627
|
try {
|
|
15406
15628
|
const thisFile = fileURLToPath4(import.meta.url);
|
|
15407
|
-
const scriptPath =
|
|
15408
|
-
|
|
15629
|
+
const scriptPath = path34.join(
|
|
15630
|
+
path34.dirname(thisFile),
|
|
15409
15631
|
"..",
|
|
15410
15632
|
"bin",
|
|
15411
15633
|
"exe-export-behaviors.js"
|
|
@@ -15419,12 +15641,12 @@ function exportBehaviorsSync(agentId, projectName, sessionKey) {
|
|
|
15419
15641
|
const script = resolveBehaviorsExporterScript();
|
|
15420
15642
|
if (!script) return null;
|
|
15421
15643
|
try {
|
|
15422
|
-
const
|
|
15644
|
+
const output2 = execFileSync3(
|
|
15423
15645
|
process.execPath,
|
|
15424
15646
|
[script, agentId, projectName, sessionKey],
|
|
15425
15647
|
{ encoding: "utf-8", timeout: BEHAVIORS_EXPORT_TIMEOUT_MS }
|
|
15426
15648
|
).trim();
|
|
15427
|
-
return
|
|
15649
|
+
return output2.length > 0 ? output2 : null;
|
|
15428
15650
|
} catch (err) {
|
|
15429
15651
|
process.stderr.write(
|
|
15430
15652
|
`[tmux-routing] behaviors export failed for ${agentId}: ${err instanceof Error ? err.message : String(err)}
|
|
@@ -15477,11 +15699,11 @@ function extractRootExe(name) {
|
|
|
15477
15699
|
}
|
|
15478
15700
|
function registerParentExe(sessionKey, parentExe, dispatchedBy) {
|
|
15479
15701
|
if (!existsSync28(SESSION_CACHE)) {
|
|
15480
|
-
|
|
15702
|
+
mkdirSync20(SESSION_CACHE, { recursive: true });
|
|
15481
15703
|
}
|
|
15482
15704
|
const rootExe = extractRootExe(parentExe) ?? parentExe;
|
|
15483
|
-
const filePath =
|
|
15484
|
-
|
|
15705
|
+
const filePath = path34.join(SESSION_CACHE, `parent-exe-${sessionKey}.json`);
|
|
15706
|
+
writeFileSync20(filePath, JSON.stringify({
|
|
15485
15707
|
parentExe: rootExe,
|
|
15486
15708
|
dispatchedBy: dispatchedBy || rootExe,
|
|
15487
15709
|
registeredAt: (/* @__PURE__ */ new Date()).toISOString()
|
|
@@ -15489,7 +15711,7 @@ function registerParentExe(sessionKey, parentExe, dispatchedBy) {
|
|
|
15489
15711
|
}
|
|
15490
15712
|
function getParentExe(sessionKey) {
|
|
15491
15713
|
try {
|
|
15492
|
-
const data = JSON.parse(
|
|
15714
|
+
const data = JSON.parse(readFileSync23(path34.join(SESSION_CACHE, `parent-exe-${sessionKey}.json`), "utf8"));
|
|
15493
15715
|
return data.parentExe || null;
|
|
15494
15716
|
} catch {
|
|
15495
15717
|
return null;
|
|
@@ -15497,8 +15719,8 @@ function getParentExe(sessionKey) {
|
|
|
15497
15719
|
}
|
|
15498
15720
|
function getDispatchedBy(sessionKey) {
|
|
15499
15721
|
try {
|
|
15500
|
-
const data = JSON.parse(
|
|
15501
|
-
|
|
15722
|
+
const data = JSON.parse(readFileSync23(
|
|
15723
|
+
path34.join(SESSION_CACHE, `parent-exe-${sessionKey}.json`),
|
|
15502
15724
|
"utf8"
|
|
15503
15725
|
));
|
|
15504
15726
|
return data.dispatchedBy ?? data.parentExe ?? null;
|
|
@@ -15569,7 +15791,7 @@ async function verifyPaneAtCapacity(sessionName) {
|
|
|
15569
15791
|
function readDebounceState() {
|
|
15570
15792
|
try {
|
|
15571
15793
|
if (!existsSync28(DEBOUNCE_FILE)) return {};
|
|
15572
|
-
const raw = JSON.parse(
|
|
15794
|
+
const raw = JSON.parse(readFileSync23(DEBOUNCE_FILE, "utf8"));
|
|
15573
15795
|
const state = {};
|
|
15574
15796
|
for (const [key, val] of Object.entries(raw)) {
|
|
15575
15797
|
if (typeof val === "number") {
|
|
@@ -15585,8 +15807,8 @@ function readDebounceState() {
|
|
|
15585
15807
|
}
|
|
15586
15808
|
function writeDebounceState(state) {
|
|
15587
15809
|
try {
|
|
15588
|
-
if (!existsSync28(SESSION_CACHE))
|
|
15589
|
-
|
|
15810
|
+
if (!existsSync28(SESSION_CACHE)) mkdirSync20(SESSION_CACHE, { recursive: true });
|
|
15811
|
+
writeFileSync20(DEBOUNCE_FILE, JSON.stringify(state));
|
|
15590
15812
|
} catch {
|
|
15591
15813
|
}
|
|
15592
15814
|
}
|
|
@@ -15685,7 +15907,7 @@ function sendIntercom(targetSession) {
|
|
|
15685
15907
|
try {
|
|
15686
15908
|
const rawAgent = targetSession.split("-")[0] ?? targetSession;
|
|
15687
15909
|
const agent = baseAgentName(rawAgent);
|
|
15688
|
-
const markerPath =
|
|
15910
|
+
const markerPath = path34.join(SESSION_CACHE, `current-task-${agent}.json`);
|
|
15689
15911
|
if (existsSync28(markerPath)) {
|
|
15690
15912
|
logIntercom(`SKIP \u2192 ${targetSession} (has in_progress task marker + not idle \u2014 will auto-chain)`);
|
|
15691
15913
|
return "debounced";
|
|
@@ -15696,7 +15918,7 @@ function sendIntercom(targetSession) {
|
|
|
15696
15918
|
try {
|
|
15697
15919
|
const rawAgent = targetSession.split("-")[0] ?? targetSession;
|
|
15698
15920
|
const agent = baseAgentName(rawAgent);
|
|
15699
|
-
const taskDir =
|
|
15921
|
+
const taskDir = path34.join(process.cwd(), "exe", agent);
|
|
15700
15922
|
if (existsSync28(taskDir)) {
|
|
15701
15923
|
const files = readdirSync7(taskDir).filter(
|
|
15702
15924
|
(f) => f.endsWith(".md") && f !== "DONE.txt"
|
|
@@ -15856,26 +16078,26 @@ function spawnEmployee(employeeName, exeSession, projectDir, opts) {
|
|
|
15856
16078
|
const transport = getTransport();
|
|
15857
16079
|
const sessionName = employeeSessionName(employeeName, exeSession, opts?.instance);
|
|
15858
16080
|
const instanceLabel = opts?.instance != null && opts.instance > 0 ? `${employeeName}${opts.instance}` : employeeName;
|
|
15859
|
-
const logDir =
|
|
15860
|
-
const logFile =
|
|
16081
|
+
const logDir = path34.join(os18.homedir(), ".exe-os", "session-logs");
|
|
16082
|
+
const logFile = path34.join(logDir, `${instanceLabel}-${Date.now()}.log`);
|
|
15861
16083
|
if (!existsSync28(logDir)) {
|
|
15862
|
-
|
|
16084
|
+
mkdirSync20(logDir, { recursive: true });
|
|
15863
16085
|
}
|
|
15864
16086
|
transport.kill(sessionName);
|
|
15865
16087
|
let cleanupSuffix = "";
|
|
15866
16088
|
try {
|
|
15867
16089
|
const thisFile = fileURLToPath4(import.meta.url);
|
|
15868
|
-
const cleanupScript =
|
|
16090
|
+
const cleanupScript = path34.join(path34.dirname(thisFile), "..", "bin", "exe-session-cleanup.js");
|
|
15869
16091
|
if (existsSync28(cleanupScript)) {
|
|
15870
16092
|
cleanupSuffix = `; ${process.execPath} "${cleanupScript}" "${employeeName}" "${exeSession}"`;
|
|
15871
16093
|
}
|
|
15872
16094
|
} catch {
|
|
15873
16095
|
}
|
|
15874
16096
|
try {
|
|
15875
|
-
const claudeJsonPath =
|
|
16097
|
+
const claudeJsonPath = path34.join(os18.homedir(), ".claude.json");
|
|
15876
16098
|
let claudeJson = {};
|
|
15877
16099
|
try {
|
|
15878
|
-
claudeJson = JSON.parse(
|
|
16100
|
+
claudeJson = JSON.parse(readFileSync23(claudeJsonPath, "utf8"));
|
|
15879
16101
|
} catch {
|
|
15880
16102
|
}
|
|
15881
16103
|
if (!claudeJson.projects) claudeJson.projects = {};
|
|
@@ -15883,17 +16105,17 @@ function spawnEmployee(employeeName, exeSession, projectDir, opts) {
|
|
|
15883
16105
|
const trustDir = opts?.cwd ?? projectDir;
|
|
15884
16106
|
if (!projects[trustDir]) projects[trustDir] = {};
|
|
15885
16107
|
projects[trustDir].hasTrustDialogAccepted = true;
|
|
15886
|
-
|
|
16108
|
+
writeFileSync20(claudeJsonPath, JSON.stringify(claudeJson, null, 2) + "\n");
|
|
15887
16109
|
} catch {
|
|
15888
16110
|
}
|
|
15889
16111
|
try {
|
|
15890
|
-
const settingsDir =
|
|
16112
|
+
const settingsDir = path34.join(os18.homedir(), ".claude", "projects");
|
|
15891
16113
|
const normalizedKey = (opts?.cwd ?? projectDir).replace(/\//g, "-").replace(/^-/, "");
|
|
15892
|
-
const projSettingsDir =
|
|
15893
|
-
const settingsPath =
|
|
16114
|
+
const projSettingsDir = path34.join(settingsDir, normalizedKey);
|
|
16115
|
+
const settingsPath = path34.join(projSettingsDir, "settings.json");
|
|
15894
16116
|
let settings = {};
|
|
15895
16117
|
try {
|
|
15896
|
-
settings = JSON.parse(
|
|
16118
|
+
settings = JSON.parse(readFileSync23(settingsPath, "utf8"));
|
|
15897
16119
|
} catch {
|
|
15898
16120
|
}
|
|
15899
16121
|
const perms = settings.permissions ?? {};
|
|
@@ -15921,8 +16143,8 @@ function spawnEmployee(employeeName, exeSession, projectDir, opts) {
|
|
|
15921
16143
|
if (changed) {
|
|
15922
16144
|
perms.allow = allow;
|
|
15923
16145
|
settings.permissions = perms;
|
|
15924
|
-
|
|
15925
|
-
|
|
16146
|
+
mkdirSync20(projSettingsDir, { recursive: true });
|
|
16147
|
+
writeFileSync20(settingsPath, JSON.stringify(settings, null, 2) + "\n");
|
|
15926
16148
|
}
|
|
15927
16149
|
} catch {
|
|
15928
16150
|
}
|
|
@@ -15937,7 +16159,7 @@ function spawnEmployee(employeeName, exeSession, projectDir, opts) {
|
|
|
15937
16159
|
let behaviorsFlag = "";
|
|
15938
16160
|
let legacyFallbackWarned = false;
|
|
15939
16161
|
if (!useExeAgent && !useBinSymlink) {
|
|
15940
|
-
const identityPath2 =
|
|
16162
|
+
const identityPath2 = path34.join(
|
|
15941
16163
|
os18.homedir(),
|
|
15942
16164
|
".exe-os",
|
|
15943
16165
|
"identity",
|
|
@@ -15960,7 +16182,7 @@ function spawnEmployee(employeeName, exeSession, projectDir, opts) {
|
|
|
15960
16182
|
}
|
|
15961
16183
|
const behaviorsFile = exportBehaviorsSync(
|
|
15962
16184
|
employeeName,
|
|
15963
|
-
|
|
16185
|
+
path34.basename(spawnCwd),
|
|
15964
16186
|
sessionName
|
|
15965
16187
|
);
|
|
15966
16188
|
if (behaviorsFile) {
|
|
@@ -15975,16 +16197,16 @@ function spawnEmployee(employeeName, exeSession, projectDir, opts) {
|
|
|
15975
16197
|
}
|
|
15976
16198
|
let sessionContextFlag = "";
|
|
15977
16199
|
try {
|
|
15978
|
-
const ctxDir =
|
|
15979
|
-
|
|
15980
|
-
const ctxFile =
|
|
16200
|
+
const ctxDir = path34.join(os18.homedir(), ".exe-os", "session-cache");
|
|
16201
|
+
mkdirSync20(ctxDir, { recursive: true });
|
|
16202
|
+
const ctxFile = path34.join(ctxDir, `session-context-${sessionName}.md`);
|
|
15981
16203
|
const ctxContent = [
|
|
15982
16204
|
`## Session Context`,
|
|
15983
16205
|
`You are running in tmux session: ${sessionName}.`,
|
|
15984
16206
|
`Your parent coordinator session is ${exeSession}.`,
|
|
15985
16207
|
`Your employees (if any) use the -${exeSession} suffix.`
|
|
15986
16208
|
].join("\n");
|
|
15987
|
-
|
|
16209
|
+
writeFileSync20(ctxFile, ctxContent);
|
|
15988
16210
|
sessionContextFlag = ` --append-system-prompt-file ${ctxFile}`;
|
|
15989
16211
|
} catch {
|
|
15990
16212
|
}
|
|
@@ -16067,8 +16289,8 @@ function spawnEmployee(employeeName, exeSession, projectDir, opts) {
|
|
|
16067
16289
|
transport.pipeLog(sessionName, logFile);
|
|
16068
16290
|
try {
|
|
16069
16291
|
const mySession = getMySession();
|
|
16070
|
-
const dispatchInfo =
|
|
16071
|
-
|
|
16292
|
+
const dispatchInfo = path34.join(SESSION_CACHE, `dispatch-info-${sessionName}.json`);
|
|
16293
|
+
writeFileSync20(dispatchInfo, JSON.stringify({
|
|
16072
16294
|
dispatchedBy: mySession,
|
|
16073
16295
|
rootExe: exeSession,
|
|
16074
16296
|
provider: useBinSymlink ? ccProvider : useExeAgent ? opts.provider : useCodex ? "openai" : useOpencode ? "opencode" : "anthropic",
|
|
@@ -16143,15 +16365,15 @@ var init_tmux_routing = __esm({
|
|
|
16143
16365
|
init_plan_limits();
|
|
16144
16366
|
init_employees();
|
|
16145
16367
|
init_agent_symlinks();
|
|
16146
|
-
SPAWN_LOCK_DIR =
|
|
16147
|
-
SESSION_CACHE =
|
|
16368
|
+
SPAWN_LOCK_DIR = path34.join(os18.homedir(), ".exe-os", "spawn-locks");
|
|
16369
|
+
SESSION_CACHE = path34.join(os18.homedir(), ".exe-os", "session-cache");
|
|
16148
16370
|
BEHAVIORS_EXPORT_TIMEOUT_MS = 1e4;
|
|
16149
16371
|
VALID_SESSION_NAME = /^[a-z]+\d*-[a-zA-Z0-9_]+$/;
|
|
16150
16372
|
VERIFY_PANE_LINES = 200;
|
|
16151
16373
|
INTERCOM_DEBOUNCE_MS = 3e4;
|
|
16152
16374
|
CODEX_DEBOUNCE_MS = 12e4;
|
|
16153
|
-
INTERCOM_LOG2 =
|
|
16154
|
-
DEBOUNCE_FILE =
|
|
16375
|
+
INTERCOM_LOG2 = path34.join(os18.homedir(), ".exe-os", "intercom.log");
|
|
16376
|
+
DEBOUNCE_FILE = path34.join(SESSION_CACHE, "intercom-debounce.json");
|
|
16155
16377
|
DEBOUNCE_CLEANUP_AGE_MS = 5 * 60 * 1e3;
|
|
16156
16378
|
BUSY_PATTERN = /[✻✽✶✳·].*…|Running…|• Working|• Ran |• Explored|• Called|esc to interrupt/;
|
|
16157
16379
|
}
|
|
@@ -16453,9 +16675,9 @@ __export(active_agent_exports, {
|
|
|
16453
16675
|
resolveActiveAgentFromTmuxSession: () => resolveActiveAgentFromTmuxSession,
|
|
16454
16676
|
writeActiveAgent: () => writeActiveAgent
|
|
16455
16677
|
});
|
|
16456
|
-
import { readFileSync as
|
|
16678
|
+
import { readFileSync as readFileSync24, writeFileSync as writeFileSync21, mkdirSync as mkdirSync21, unlinkSync as unlinkSync12, readdirSync as readdirSync8 } from "fs";
|
|
16457
16679
|
import { execSync as execSync11 } from "child_process";
|
|
16458
|
-
import
|
|
16680
|
+
import path35 from "path";
|
|
16459
16681
|
function isNameWithOptionalInstance(candidate, baseName) {
|
|
16460
16682
|
if (candidate === baseName) return true;
|
|
16461
16683
|
if (!candidate.startsWith(baseName)) return false;
|
|
@@ -16499,12 +16721,12 @@ function resolveActiveAgentFromTmuxSession(sessionName) {
|
|
|
16499
16721
|
return null;
|
|
16500
16722
|
}
|
|
16501
16723
|
function getMarkerPath() {
|
|
16502
|
-
return
|
|
16724
|
+
return path35.join(CACHE_DIR, `active-agent-${getSessionKey()}.json`);
|
|
16503
16725
|
}
|
|
16504
16726
|
function writeActiveAgent(agentId, agentRole) {
|
|
16505
16727
|
try {
|
|
16506
|
-
|
|
16507
|
-
|
|
16728
|
+
mkdirSync21(CACHE_DIR, { recursive: true });
|
|
16729
|
+
writeFileSync21(
|
|
16508
16730
|
getMarkerPath(),
|
|
16509
16731
|
JSON.stringify({ agentId, agentRole, startedAt: (/* @__PURE__ */ new Date()).toISOString() })
|
|
16510
16732
|
);
|
|
@@ -16513,7 +16735,7 @@ function writeActiveAgent(agentId, agentRole) {
|
|
|
16513
16735
|
}
|
|
16514
16736
|
function clearActiveAgent() {
|
|
16515
16737
|
try {
|
|
16516
|
-
|
|
16738
|
+
unlinkSync12(getMarkerPath());
|
|
16517
16739
|
} catch {
|
|
16518
16740
|
}
|
|
16519
16741
|
}
|
|
@@ -16522,14 +16744,14 @@ function getActiveAgent() {
|
|
|
16522
16744
|
if (httpCtx) return httpCtx;
|
|
16523
16745
|
try {
|
|
16524
16746
|
const markerPath = getMarkerPath();
|
|
16525
|
-
const raw =
|
|
16747
|
+
const raw = readFileSync24(markerPath, "utf8");
|
|
16526
16748
|
const data = JSON.parse(raw);
|
|
16527
16749
|
if (data.agentId) {
|
|
16528
16750
|
if (data.startedAt) {
|
|
16529
16751
|
const age = Date.now() - new Date(data.startedAt).getTime();
|
|
16530
16752
|
if (age > STALE_MS) {
|
|
16531
16753
|
try {
|
|
16532
|
-
|
|
16754
|
+
unlinkSync12(markerPath);
|
|
16533
16755
|
} catch {
|
|
16534
16756
|
}
|
|
16535
16757
|
} else {
|
|
@@ -16570,14 +16792,14 @@ function getAllActiveAgents() {
|
|
|
16570
16792
|
const key = file.slice("active-agent-".length, -".json".length);
|
|
16571
16793
|
if (key === "undefined") continue;
|
|
16572
16794
|
try {
|
|
16573
|
-
const raw =
|
|
16795
|
+
const raw = readFileSync24(path35.join(CACHE_DIR, file), "utf8");
|
|
16574
16796
|
const data = JSON.parse(raw);
|
|
16575
16797
|
if (!data.agentId) continue;
|
|
16576
16798
|
if (data.startedAt) {
|
|
16577
16799
|
const age = Date.now() - new Date(data.startedAt).getTime();
|
|
16578
16800
|
if (age > STALE_MS) {
|
|
16579
16801
|
try {
|
|
16580
|
-
|
|
16802
|
+
unlinkSync12(path35.join(CACHE_DIR, file));
|
|
16581
16803
|
} catch {
|
|
16582
16804
|
}
|
|
16583
16805
|
continue;
|
|
@@ -16600,11 +16822,11 @@ function getAllActiveAgents() {
|
|
|
16600
16822
|
function cleanupSessionMarkers() {
|
|
16601
16823
|
const key = getSessionKey();
|
|
16602
16824
|
try {
|
|
16603
|
-
|
|
16825
|
+
unlinkSync12(path35.join(CACHE_DIR, `active-agent-${key}.json`));
|
|
16604
16826
|
} catch {
|
|
16605
16827
|
}
|
|
16606
16828
|
try {
|
|
16607
|
-
|
|
16829
|
+
unlinkSync12(path35.join(CACHE_DIR, "active-agent-undefined.json"));
|
|
16608
16830
|
} catch {
|
|
16609
16831
|
}
|
|
16610
16832
|
}
|
|
@@ -16616,7 +16838,7 @@ var init_active_agent = __esm({
|
|
|
16616
16838
|
init_session_key();
|
|
16617
16839
|
init_agent_context();
|
|
16618
16840
|
init_employees();
|
|
16619
|
-
CACHE_DIR =
|
|
16841
|
+
CACHE_DIR = path35.join(EXE_AI_DIR, "session-cache");
|
|
16620
16842
|
STALE_MS = 24 * 60 * 60 * 1e3;
|
|
16621
16843
|
}
|
|
16622
16844
|
});
|
|
@@ -17269,17 +17491,17 @@ All memory, tasks, behaviors, documents, and wiki content belonging to {{company
|
|
|
17269
17491
|
// src/bin/exe-rename.ts
|
|
17270
17492
|
var exe_rename_exports = {};
|
|
17271
17493
|
__export(exe_rename_exports, {
|
|
17272
|
-
main: () =>
|
|
17494
|
+
main: () => main6,
|
|
17273
17495
|
renameEmployee: () => renameEmployee
|
|
17274
17496
|
});
|
|
17275
|
-
import { readFileSync as
|
|
17497
|
+
import { readFileSync as readFileSync25, writeFileSync as writeFileSync22, renameSync as renameSync6, unlinkSync as unlinkSync13, existsSync as existsSync29 } from "fs";
|
|
17276
17498
|
import { execSync as execSync12 } from "child_process";
|
|
17277
|
-
import
|
|
17499
|
+
import path36 from "path";
|
|
17278
17500
|
import { homedir as homedir4 } from "os";
|
|
17279
17501
|
async function renameEmployee(oldName, newName, opts = {}) {
|
|
17280
|
-
const rosterPath = opts.rosterPath ??
|
|
17281
|
-
const identityDir = opts.identityDir ??
|
|
17282
|
-
const agentsDir = opts.agentsDir ??
|
|
17502
|
+
const rosterPath = opts.rosterPath ?? path36.join(homedir4(), ".exe-os", "exe-employees.json");
|
|
17503
|
+
const identityDir = opts.identityDir ?? path36.join(homedir4(), ".exe-os", "identity");
|
|
17504
|
+
const agentsDir = opts.agentsDir ?? path36.join(homedir4(), ".claude", "agents");
|
|
17283
17505
|
const validation = validateEmployeeName(newName);
|
|
17284
17506
|
if (!validation.valid) {
|
|
17285
17507
|
return { success: false, error: validation.error };
|
|
@@ -17309,39 +17531,39 @@ async function renameEmployee(oldName, newName, opts = {}) {
|
|
|
17309
17531
|
undo: () => {
|
|
17310
17532
|
employee.name = originalName;
|
|
17311
17533
|
employee.systemPrompt = originalPrompt;
|
|
17312
|
-
|
|
17534
|
+
writeFileSync22(rosterPath, JSON.stringify(employees, null, 2) + "\n", "utf-8");
|
|
17313
17535
|
}
|
|
17314
17536
|
});
|
|
17315
|
-
const oldIdentityPath =
|
|
17316
|
-
const newIdentityPath =
|
|
17537
|
+
const oldIdentityPath = path36.join(identityDir, `${rosterOldName}.md`);
|
|
17538
|
+
const newIdentityPath = path36.join(identityDir, `${newName}.md`);
|
|
17317
17539
|
if (existsSync29(oldIdentityPath)) {
|
|
17318
|
-
const content =
|
|
17540
|
+
const content = readFileSync25(oldIdentityPath, "utf-8");
|
|
17319
17541
|
const updatedContent = rewriteRenamedEmployeeContent(content, rosterOldName, newName);
|
|
17320
17542
|
renameSync6(oldIdentityPath, newIdentityPath);
|
|
17321
|
-
|
|
17543
|
+
writeFileSync22(newIdentityPath, updatedContent, "utf-8");
|
|
17322
17544
|
rollbackStack.push({
|
|
17323
17545
|
description: "restore identity file",
|
|
17324
17546
|
undo: () => {
|
|
17325
17547
|
if (existsSync29(newIdentityPath)) {
|
|
17326
|
-
|
|
17548
|
+
writeFileSync22(newIdentityPath, content, "utf-8");
|
|
17327
17549
|
renameSync6(newIdentityPath, oldIdentityPath);
|
|
17328
17550
|
}
|
|
17329
17551
|
}
|
|
17330
17552
|
});
|
|
17331
17553
|
}
|
|
17332
|
-
const oldAgentPath =
|
|
17333
|
-
const newAgentPath =
|
|
17554
|
+
const oldAgentPath = path36.join(agentsDir, `${rosterOldName}.md`);
|
|
17555
|
+
const newAgentPath = path36.join(agentsDir, `${newName}.md`);
|
|
17334
17556
|
if (existsSync29(oldAgentPath)) {
|
|
17335
|
-
const agentContent =
|
|
17557
|
+
const agentContent = readFileSync25(oldAgentPath, "utf-8");
|
|
17336
17558
|
const updatedAgentContent = rewriteRenamedEmployeeContent(agentContent, rosterOldName, newName);
|
|
17337
17559
|
renameSync6(oldAgentPath, newAgentPath);
|
|
17338
|
-
|
|
17560
|
+
writeFileSync22(newAgentPath, updatedAgentContent, "utf-8");
|
|
17339
17561
|
rollbackStack.push({
|
|
17340
17562
|
description: "restore agent file",
|
|
17341
17563
|
undo: () => {
|
|
17342
17564
|
if (existsSync29(newAgentPath)) {
|
|
17343
17565
|
renameSync6(newAgentPath, oldAgentPath);
|
|
17344
|
-
|
|
17566
|
+
writeFileSync22(oldAgentPath, agentContent, "utf-8");
|
|
17345
17567
|
}
|
|
17346
17568
|
}
|
|
17347
17569
|
});
|
|
@@ -17423,12 +17645,12 @@ function removeOldSymlinks(name) {
|
|
|
17423
17645
|
try {
|
|
17424
17646
|
const exeBinPath = findExeBin2();
|
|
17425
17647
|
if (!exeBinPath) return;
|
|
17426
|
-
const binDir =
|
|
17648
|
+
const binDir = path36.dirname(exeBinPath);
|
|
17427
17649
|
for (const suffix of ["", "-opencode"]) {
|
|
17428
|
-
const linkPath =
|
|
17650
|
+
const linkPath = path36.join(binDir, `${name}${suffix}`);
|
|
17429
17651
|
if (existsSync29(linkPath)) {
|
|
17430
17652
|
try {
|
|
17431
|
-
|
|
17653
|
+
unlinkSync13(linkPath);
|
|
17432
17654
|
} catch {
|
|
17433
17655
|
}
|
|
17434
17656
|
}
|
|
@@ -17436,7 +17658,7 @@ function removeOldSymlinks(name) {
|
|
|
17436
17658
|
} catch {
|
|
17437
17659
|
}
|
|
17438
17660
|
}
|
|
17439
|
-
async function
|
|
17661
|
+
async function main6() {
|
|
17440
17662
|
const args2 = process.argv.slice(2);
|
|
17441
17663
|
if (args2.length < 2) {
|
|
17442
17664
|
console.error("Usage: exe-os rename <oldName> <newName>");
|
|
@@ -17464,7 +17686,7 @@ var init_exe_rename = __esm({
|
|
|
17464
17686
|
init_employee_templates();
|
|
17465
17687
|
init_is_main();
|
|
17466
17688
|
if (isMainModule(import.meta.url)) {
|
|
17467
|
-
|
|
17689
|
+
main6().catch((err) => {
|
|
17468
17690
|
console.error(err instanceof Error ? err.message : String(err));
|
|
17469
17691
|
process.exit(1);
|
|
17470
17692
|
});
|
|
@@ -17473,13 +17695,13 @@ var init_exe_rename = __esm({
|
|
|
17473
17695
|
});
|
|
17474
17696
|
|
|
17475
17697
|
// src/lib/model-downloader.ts
|
|
17476
|
-
import { createWriteStream, createReadStream as createReadStream2, existsSync as existsSync30, unlinkSync as
|
|
17698
|
+
import { createWriteStream, createReadStream as createReadStream2, existsSync as existsSync30, unlinkSync as unlinkSync14, renameSync as renameSync7 } from "fs";
|
|
17477
17699
|
import { mkdir as mkdir6 } from "fs/promises";
|
|
17478
17700
|
import { createHash as createHash6 } from "crypto";
|
|
17479
|
-
import
|
|
17701
|
+
import path37 from "path";
|
|
17480
17702
|
async function downloadModel(opts) {
|
|
17481
17703
|
const { destDir, onProgress, fetchFn = globalThis.fetch } = opts;
|
|
17482
|
-
const destPath =
|
|
17704
|
+
const destPath = path37.join(destDir, LOCAL_FILENAME);
|
|
17483
17705
|
const tmpPath = destPath + ".tmp";
|
|
17484
17706
|
await mkdir6(destDir, { recursive: true });
|
|
17485
17707
|
if (existsSync30(destPath)) {
|
|
@@ -17494,7 +17716,7 @@ async function downloadModel(opts) {
|
|
|
17494
17716
|
let downloaded = 0;
|
|
17495
17717
|
for (let attempt = 1; attempt <= MAX_RETRIES4; attempt++) {
|
|
17496
17718
|
try {
|
|
17497
|
-
if (existsSync30(tmpPath))
|
|
17719
|
+
if (existsSync30(tmpPath)) unlinkSync14(tmpPath);
|
|
17498
17720
|
const response = await fetchFn(GGUF_URL, {
|
|
17499
17721
|
redirect: "follow",
|
|
17500
17722
|
signal: AbortSignal.timeout(DOWNLOAD_TIMEOUT_MS)
|
|
@@ -17526,7 +17748,7 @@ async function downloadModel(opts) {
|
|
|
17526
17748
|
}
|
|
17527
17749
|
const actualHash = hash.digest("hex");
|
|
17528
17750
|
if (actualHash !== EXPECTED_SHA256) {
|
|
17529
|
-
|
|
17751
|
+
unlinkSync14(tmpPath);
|
|
17530
17752
|
throw new Error(
|
|
17531
17753
|
`SHA256 mismatch: expected ${EXPECTED_SHA256}, got ${actualHash}`
|
|
17532
17754
|
);
|
|
@@ -17539,7 +17761,7 @@ async function downloadModel(opts) {
|
|
|
17539
17761
|
process.stderr.write(`
|
|
17540
17762
|
Download attempt ${attempt} failed, retrying...
|
|
17541
17763
|
`);
|
|
17542
|
-
if (existsSync30(tmpPath))
|
|
17764
|
+
if (existsSync30(tmpPath)) unlinkSync14(tmpPath);
|
|
17543
17765
|
}
|
|
17544
17766
|
}
|
|
17545
17767
|
}
|
|
@@ -18113,37 +18335,37 @@ __export(session_wrappers_exports, {
|
|
|
18113
18335
|
});
|
|
18114
18336
|
import {
|
|
18115
18337
|
existsSync as existsSync31,
|
|
18116
|
-
readFileSync as
|
|
18117
|
-
writeFileSync as
|
|
18118
|
-
mkdirSync as
|
|
18338
|
+
readFileSync as readFileSync26,
|
|
18339
|
+
writeFileSync as writeFileSync23,
|
|
18340
|
+
mkdirSync as mkdirSync22,
|
|
18119
18341
|
chmodSync as chmodSync3,
|
|
18120
18342
|
readdirSync as readdirSync9,
|
|
18121
|
-
unlinkSync as
|
|
18343
|
+
unlinkSync as unlinkSync15
|
|
18122
18344
|
} from "fs";
|
|
18123
18345
|
import { execSync as execSync13 } from "child_process";
|
|
18124
|
-
import
|
|
18346
|
+
import path38 from "path";
|
|
18125
18347
|
import { homedir as homedir5 } from "os";
|
|
18126
18348
|
function generateSessionWrappers(packageRoot, homeDir) {
|
|
18127
18349
|
const home = homeDir ?? homedir5();
|
|
18128
|
-
const binDir =
|
|
18129
|
-
const rosterPath =
|
|
18350
|
+
const binDir = path38.join(home, ".exe-os", "bin");
|
|
18351
|
+
const rosterPath = path38.join(home, ".exe-os", "exe-employees.json");
|
|
18130
18352
|
const shouldMirrorToGlobalBin = homeDir === void 0;
|
|
18131
|
-
|
|
18132
|
-
const exeStartDst =
|
|
18353
|
+
mkdirSync22(binDir, { recursive: true });
|
|
18354
|
+
const exeStartDst = path38.join(binDir, "exe-start");
|
|
18133
18355
|
const candidates = [
|
|
18134
|
-
|
|
18135
|
-
|
|
18356
|
+
path38.join(packageRoot, "dist", "bin", "exe-start.sh"),
|
|
18357
|
+
path38.join(packageRoot, "src", "bin", "exe-start.sh")
|
|
18136
18358
|
];
|
|
18137
18359
|
for (const src of candidates) {
|
|
18138
18360
|
if (existsSync31(src)) {
|
|
18139
|
-
|
|
18361
|
+
writeFileSync23(exeStartDst, readFileSync26(src));
|
|
18140
18362
|
chmodSync3(exeStartDst, 493);
|
|
18141
18363
|
break;
|
|
18142
18364
|
}
|
|
18143
18365
|
}
|
|
18144
18366
|
let employees = [];
|
|
18145
18367
|
try {
|
|
18146
|
-
employees = JSON.parse(
|
|
18368
|
+
employees = JSON.parse(readFileSync26(rosterPath, "utf8"));
|
|
18147
18369
|
} catch {
|
|
18148
18370
|
return { created: 0, pathConfigured: false };
|
|
18149
18371
|
}
|
|
@@ -18153,11 +18375,11 @@ function generateSessionWrappers(packageRoot, homeDir) {
|
|
|
18153
18375
|
try {
|
|
18154
18376
|
for (const f of readdirSync9(binDir)) {
|
|
18155
18377
|
if (f === "exe-start") continue;
|
|
18156
|
-
const fPath =
|
|
18378
|
+
const fPath = path38.join(binDir, f);
|
|
18157
18379
|
try {
|
|
18158
|
-
const content =
|
|
18380
|
+
const content = readFileSync26(fPath, "utf8");
|
|
18159
18381
|
if (content.includes("exe-start")) {
|
|
18160
|
-
|
|
18382
|
+
unlinkSync15(fPath);
|
|
18161
18383
|
}
|
|
18162
18384
|
} catch {
|
|
18163
18385
|
}
|
|
@@ -18171,21 +18393,21 @@ exec "${exeStartDst}" "$0" "$@"
|
|
|
18171
18393
|
const globalBinDir = shouldMirrorToGlobalBin ? resolveGlobalBinDir() : null;
|
|
18172
18394
|
for (const emp of employees) {
|
|
18173
18395
|
for (let n = 1; n <= MAX_N; n++) {
|
|
18174
|
-
writeWrapper(
|
|
18396
|
+
writeWrapper(path38.join(binDir, `${emp.name}${n}`), wrapperContent);
|
|
18175
18397
|
if (globalBinDir) {
|
|
18176
|
-
writeWrapper(
|
|
18398
|
+
writeWrapper(path38.join(globalBinDir, `${emp.name}${n}`), wrapperContent);
|
|
18177
18399
|
}
|
|
18178
18400
|
created++;
|
|
18179
|
-
writeWrapper(
|
|
18401
|
+
writeWrapper(path38.join(binDir, `${emp.name}${n}-codex`), wrapperContent);
|
|
18180
18402
|
if (globalBinDir) {
|
|
18181
|
-
writeWrapper(
|
|
18403
|
+
writeWrapper(path38.join(globalBinDir, `${emp.name}${n}-codex`), wrapperContent);
|
|
18182
18404
|
}
|
|
18183
18405
|
created++;
|
|
18184
18406
|
}
|
|
18185
18407
|
}
|
|
18186
18408
|
const codexLauncherCandidates = [
|
|
18187
|
-
|
|
18188
|
-
|
|
18409
|
+
path38.join(packageRoot, "dist", "bin", "exe-start-codex.js"),
|
|
18410
|
+
path38.join(packageRoot, "src", "bin", "exe-start-codex.ts")
|
|
18189
18411
|
];
|
|
18190
18412
|
let codexLauncher = null;
|
|
18191
18413
|
for (const c of codexLauncherCandidates) {
|
|
@@ -18196,11 +18418,11 @@ exec "${exeStartDst}" "$0" "$@"
|
|
|
18196
18418
|
}
|
|
18197
18419
|
if (codexLauncher) {
|
|
18198
18420
|
for (const emp of employees) {
|
|
18199
|
-
const wrapperPath =
|
|
18421
|
+
const wrapperPath = path38.join(binDir, `${emp.name}-codex`);
|
|
18200
18422
|
const content = `#!/bin/bash
|
|
18201
18423
|
exec node "${codexLauncher}" --agent ${emp.name} "$@"
|
|
18202
18424
|
`;
|
|
18203
|
-
|
|
18425
|
+
writeFileSync23(wrapperPath, content);
|
|
18204
18426
|
chmodSync3(wrapperPath, 493);
|
|
18205
18427
|
created++;
|
|
18206
18428
|
}
|
|
@@ -18210,7 +18432,7 @@ exec node "${codexLauncher}" --agent ${emp.name} "$@"
|
|
|
18210
18432
|
}
|
|
18211
18433
|
function writeWrapper(wrapperPath, content) {
|
|
18212
18434
|
try {
|
|
18213
|
-
|
|
18435
|
+
writeFileSync23(wrapperPath, content);
|
|
18214
18436
|
chmodSync3(wrapperPath, 493);
|
|
18215
18437
|
} catch {
|
|
18216
18438
|
}
|
|
@@ -18218,12 +18440,12 @@ function writeWrapper(wrapperPath, content) {
|
|
|
18218
18440
|
function resolveGlobalBinDir() {
|
|
18219
18441
|
try {
|
|
18220
18442
|
const exeOsPath = execSync13("command -v exe-os", { encoding: "utf8", timeout: 3e3 }).trim().split("\n")[0];
|
|
18221
|
-
if (exeOsPath) return
|
|
18443
|
+
if (exeOsPath) return path38.dirname(exeOsPath);
|
|
18222
18444
|
} catch {
|
|
18223
18445
|
}
|
|
18224
18446
|
try {
|
|
18225
18447
|
const prefix = execSync13("npm prefix -g", { encoding: "utf8", timeout: 3e3 }).trim();
|
|
18226
|
-
if (prefix) return
|
|
18448
|
+
if (prefix) return path38.join(prefix, "bin");
|
|
18227
18449
|
} catch {
|
|
18228
18450
|
}
|
|
18229
18451
|
return null;
|
|
@@ -18239,24 +18461,24 @@ export PATH="${binDir}:$PATH"
|
|
|
18239
18461
|
const shell = process.env.SHELL ?? "/bin/bash";
|
|
18240
18462
|
const profilePaths = [];
|
|
18241
18463
|
if (shell.includes("zsh")) {
|
|
18242
|
-
profilePaths.push(
|
|
18464
|
+
profilePaths.push(path38.join(home, ".zshrc"));
|
|
18243
18465
|
} else if (shell.includes("bash")) {
|
|
18244
|
-
profilePaths.push(
|
|
18245
|
-
profilePaths.push(
|
|
18466
|
+
profilePaths.push(path38.join(home, ".bashrc"));
|
|
18467
|
+
profilePaths.push(path38.join(home, ".bash_profile"));
|
|
18246
18468
|
} else {
|
|
18247
|
-
profilePaths.push(
|
|
18469
|
+
profilePaths.push(path38.join(home, ".profile"));
|
|
18248
18470
|
}
|
|
18249
18471
|
for (const profilePath of profilePaths) {
|
|
18250
18472
|
try {
|
|
18251
18473
|
let content = "";
|
|
18252
18474
|
try {
|
|
18253
|
-
content =
|
|
18475
|
+
content = readFileSync26(profilePath, "utf8");
|
|
18254
18476
|
} catch {
|
|
18255
18477
|
}
|
|
18256
18478
|
if (content.includes(".exe-os/bin")) {
|
|
18257
18479
|
return false;
|
|
18258
18480
|
}
|
|
18259
|
-
|
|
18481
|
+
writeFileSync23(profilePath, content + exportLine);
|
|
18260
18482
|
return true;
|
|
18261
18483
|
} catch {
|
|
18262
18484
|
continue;
|
|
@@ -18279,40 +18501,40 @@ __export(setup_wizard_exports, {
|
|
|
18279
18501
|
validateModel: () => validateModel
|
|
18280
18502
|
});
|
|
18281
18503
|
import crypto13 from "crypto";
|
|
18282
|
-
import { existsSync as existsSync32, mkdirSync as
|
|
18504
|
+
import { existsSync as existsSync32, mkdirSync as mkdirSync23, readFileSync as readFileSync27, writeFileSync as writeFileSync24, unlinkSync as unlinkSync16 } from "fs";
|
|
18283
18505
|
import os19 from "os";
|
|
18284
|
-
import
|
|
18506
|
+
import path39 from "path";
|
|
18285
18507
|
import { createInterface as createInterface4 } from "readline";
|
|
18286
18508
|
function findPackageRoot2() {
|
|
18287
|
-
let dir =
|
|
18288
|
-
const root =
|
|
18509
|
+
let dir = path39.dirname(new URL(import.meta.url).pathname);
|
|
18510
|
+
const root = path39.parse(dir).root;
|
|
18289
18511
|
while (dir !== root) {
|
|
18290
|
-
const pkgPath =
|
|
18512
|
+
const pkgPath = path39.join(dir, "package.json");
|
|
18291
18513
|
if (existsSync32(pkgPath)) {
|
|
18292
18514
|
try {
|
|
18293
|
-
const pkg = JSON.parse(
|
|
18515
|
+
const pkg = JSON.parse(readFileSync27(pkgPath, "utf-8"));
|
|
18294
18516
|
if (pkg.name === "@askexenow/exe-os" || pkg.name === "exe-os") return dir;
|
|
18295
18517
|
} catch {
|
|
18296
18518
|
}
|
|
18297
18519
|
}
|
|
18298
|
-
dir =
|
|
18520
|
+
dir = path39.dirname(dir);
|
|
18299
18521
|
}
|
|
18300
18522
|
return null;
|
|
18301
18523
|
}
|
|
18302
18524
|
function loadSetupState() {
|
|
18303
18525
|
try {
|
|
18304
|
-
return JSON.parse(
|
|
18526
|
+
return JSON.parse(readFileSync27(SETUP_STATE_PATH, "utf8"));
|
|
18305
18527
|
} catch {
|
|
18306
18528
|
return { completedSteps: [], startedAt: (/* @__PURE__ */ new Date()).toISOString() };
|
|
18307
18529
|
}
|
|
18308
18530
|
}
|
|
18309
18531
|
function saveSetupState(state) {
|
|
18310
|
-
|
|
18311
|
-
|
|
18532
|
+
mkdirSync23(path39.dirname(SETUP_STATE_PATH), { recursive: true });
|
|
18533
|
+
writeFileSync24(SETUP_STATE_PATH, JSON.stringify(state, null, 2));
|
|
18312
18534
|
}
|
|
18313
18535
|
function clearSetupState() {
|
|
18314
18536
|
try {
|
|
18315
|
-
|
|
18537
|
+
unlinkSync16(SETUP_STATE_PATH);
|
|
18316
18538
|
} catch {
|
|
18317
18539
|
}
|
|
18318
18540
|
}
|
|
@@ -18358,7 +18580,7 @@ async function validateModel(log) {
|
|
|
18358
18580
|
if (totalGB <= 8 || isLowMemory()) {
|
|
18359
18581
|
log(`System memory: ${totalGB.toFixed(0)}GB total, ${freeGB.toFixed(1)}GB free`);
|
|
18360
18582
|
log("Skipping in-memory model validation (low memory \u2014 will validate on first use).");
|
|
18361
|
-
const modelPath =
|
|
18583
|
+
const modelPath = path39.join(MODELS_DIR, LOCAL_FILENAME);
|
|
18362
18584
|
if (existsSync32(modelPath)) {
|
|
18363
18585
|
const { statSync: statSync8 } = await import("fs");
|
|
18364
18586
|
const size = statSync8(modelPath).size;
|
|
@@ -18645,10 +18867,10 @@ async function runSetupWizard(opts = {}) {
|
|
|
18645
18867
|
await saveConfig(config);
|
|
18646
18868
|
log("");
|
|
18647
18869
|
try {
|
|
18648
|
-
const claudeJsonPath =
|
|
18870
|
+
const claudeJsonPath = path39.join(os19.homedir(), ".claude.json");
|
|
18649
18871
|
let claudeJson = {};
|
|
18650
18872
|
try {
|
|
18651
|
-
claudeJson = JSON.parse(
|
|
18873
|
+
claudeJson = JSON.parse(readFileSync27(claudeJsonPath, "utf8"));
|
|
18652
18874
|
} catch {
|
|
18653
18875
|
}
|
|
18654
18876
|
if (!claudeJson.projects) claudeJson.projects = {};
|
|
@@ -18657,7 +18879,7 @@ async function runSetupWizard(opts = {}) {
|
|
|
18657
18879
|
if (!projects[dir]) projects[dir] = {};
|
|
18658
18880
|
projects[dir].hasTrustDialogAccepted = true;
|
|
18659
18881
|
}
|
|
18660
|
-
|
|
18882
|
+
writeFileSync24(claudeJsonPath, JSON.stringify(claudeJson, null, 2) + "\n");
|
|
18661
18883
|
} catch {
|
|
18662
18884
|
}
|
|
18663
18885
|
state.completedSteps.push(5);
|
|
@@ -18671,7 +18893,7 @@ async function runSetupWizard(opts = {}) {
|
|
|
18671
18893
|
const prefs = { ...existingPrefs };
|
|
18672
18894
|
log("=== Config Defaults ===");
|
|
18673
18895
|
log("");
|
|
18674
|
-
const ghosttyDetected = existsSync32(
|
|
18896
|
+
const ghosttyDetected = existsSync32(path39.join(os19.homedir(), ".config", "ghostty")) || existsSync32(path39.join(os19.homedir(), "Library", "Application Support", "com.mitchellh.ghostty"));
|
|
18675
18897
|
if (ghosttyDetected) {
|
|
18676
18898
|
const ghosttyAnswer = await ask3(rl, "Detected Ghostty terminal. Use exe-os Ghostty defaults? (Y/n) ");
|
|
18677
18899
|
prefs.ghostty = ghosttyAnswer.toLowerCase() !== "n";
|
|
@@ -18809,9 +19031,9 @@ async function runSetupWizard(opts = {}) {
|
|
|
18809
19031
|
const cooIdentityContent = getIdentityTemplate("coo");
|
|
18810
19032
|
if (cooIdentityContent) {
|
|
18811
19033
|
const cooIdPath = identityPath2(cooName);
|
|
18812
|
-
|
|
19034
|
+
mkdirSync23(path39.dirname(cooIdPath), { recursive: true });
|
|
18813
19035
|
const replaced = cooIdentityContent.replace(/agent_id:\s*exe/g, `agent_id: ${cooName}`).replace(/\$\{agent_id\}/g, cooName);
|
|
18814
|
-
|
|
19036
|
+
writeFileSync24(cooIdPath, replaced, "utf-8");
|
|
18815
19037
|
}
|
|
18816
19038
|
registerBinSymlinks2(cooName);
|
|
18817
19039
|
createdEmployees.push({ name: cooName, role: "COO" });
|
|
@@ -18927,9 +19149,9 @@ async function runSetupWizard(opts = {}) {
|
|
|
18927
19149
|
const ctoIdentityContent = getIdentityTemplate("cto");
|
|
18928
19150
|
if (ctoIdentityContent) {
|
|
18929
19151
|
const ctoIdPath = identityPath2(ctoName);
|
|
18930
|
-
|
|
19152
|
+
mkdirSync23(path39.dirname(ctoIdPath), { recursive: true });
|
|
18931
19153
|
const replaced = ctoIdentityContent.replace(/agent_id:\s*\w+/g, `agent_id: ${ctoName}`).replace(/\$\{agent_id\}/g, ctoName);
|
|
18932
|
-
|
|
19154
|
+
writeFileSync24(ctoIdPath, replaced, "utf-8");
|
|
18933
19155
|
}
|
|
18934
19156
|
registerBinSymlinks2(ctoName);
|
|
18935
19157
|
createdEmployees.push({ name: ctoName, role: "CTO" });
|
|
@@ -18950,9 +19172,9 @@ async function runSetupWizard(opts = {}) {
|
|
|
18950
19172
|
const cmoIdentityContent = getIdentityTemplate("cmo");
|
|
18951
19173
|
if (cmoIdentityContent) {
|
|
18952
19174
|
const cmoIdPath = identityPath2(cmoName);
|
|
18953
|
-
|
|
19175
|
+
mkdirSync23(path39.dirname(cmoIdPath), { recursive: true });
|
|
18954
19176
|
const replaced = cmoIdentityContent.replace(/agent_id:\s*\w+/g, `agent_id: ${cmoName}`).replace(/\$\{agent_id\}/g, cmoName);
|
|
18955
|
-
|
|
19177
|
+
writeFileSync24(cmoIdPath, replaced, "utf-8");
|
|
18956
19178
|
}
|
|
18957
19179
|
registerBinSymlinks2(cmoName);
|
|
18958
19180
|
createdEmployees.push({ name: cmoName, role: "CMO" });
|
|
@@ -18975,7 +19197,7 @@ async function runSetupWizard(opts = {}) {
|
|
|
18975
19197
|
log(`Session shortcuts generated (${cooName}1, ${cooName}2, ...)`);
|
|
18976
19198
|
}
|
|
18977
19199
|
if (wrapResult.pathConfigured) {
|
|
18978
|
-
const binDir =
|
|
19200
|
+
const binDir = path39.join(os19.homedir(), ".exe-os", "bin");
|
|
18979
19201
|
process.env.PATH = `${binDir}:${process.env.PATH ?? ""}`;
|
|
18980
19202
|
pathJustConfigured = true;
|
|
18981
19203
|
}
|
|
@@ -19018,7 +19240,7 @@ async function runSetupWizard(opts = {}) {
|
|
|
19018
19240
|
const pkgRoot2 = findPackageRoot2();
|
|
19019
19241
|
if (pkgRoot2) {
|
|
19020
19242
|
try {
|
|
19021
|
-
version = JSON.parse(
|
|
19243
|
+
version = JSON.parse(readFileSync27(path39.join(pkgRoot2, "package.json"), "utf-8")).version;
|
|
19022
19244
|
} catch {
|
|
19023
19245
|
}
|
|
19024
19246
|
}
|
|
@@ -19034,6 +19256,7 @@ async function runSetupWizard(opts = {}) {
|
|
|
19034
19256
|
log("");
|
|
19035
19257
|
log(" Recommended start: Phase 1 \u2014 talk to your COO first");
|
|
19036
19258
|
log(" Check/change phase: exe-os org phase");
|
|
19259
|
+
log(" Verify support intake: exe-os support test");
|
|
19037
19260
|
log(" Unlock executives later: exe-os org unlock executives");
|
|
19038
19261
|
log("");
|
|
19039
19262
|
log(` cd into a project folder: cd ~/my-project`);
|
|
@@ -19056,46 +19279,46 @@ var init_setup_wizard = __esm({
|
|
|
19056
19279
|
init_config();
|
|
19057
19280
|
init_keychain();
|
|
19058
19281
|
init_model_downloader();
|
|
19059
|
-
SETUP_STATE_PATH =
|
|
19282
|
+
SETUP_STATE_PATH = path39.join(os19.homedir(), ".exe-os", "setup-state.json");
|
|
19060
19283
|
}
|
|
19061
19284
|
});
|
|
19062
19285
|
|
|
19063
19286
|
// src/lib/update-backup.ts
|
|
19064
19287
|
import { copyFile, readFile as readFile6, readdir as readdir3, writeFile as writeFile7, rm as rm2, mkdir as mkdir7, cp } from "fs/promises";
|
|
19065
19288
|
import { existsSync as existsSync33 } from "fs";
|
|
19066
|
-
import
|
|
19289
|
+
import path40 from "path";
|
|
19067
19290
|
import os20 from "os";
|
|
19068
19291
|
function resolveDataDir2() {
|
|
19069
19292
|
if (process.env.EXE_OS_DIR) return process.env.EXE_OS_DIR;
|
|
19070
19293
|
if (process.env.EXE_MEM_DIR) return process.env.EXE_MEM_DIR;
|
|
19071
|
-
return
|
|
19294
|
+
return path40.join(os20.homedir(), ".exe-os");
|
|
19072
19295
|
}
|
|
19073
19296
|
function externalBackupTargets(homeDir) {
|
|
19074
19297
|
return [
|
|
19075
|
-
{ name: "claude.json", path:
|
|
19076
|
-
{ name: "claude-settings.json", path:
|
|
19077
|
-
{ name: "claude-CLAUDE.md", path:
|
|
19078
|
-
{ name: "tmux.conf", path:
|
|
19079
|
-
{ name: "zshrc", path:
|
|
19080
|
-
{ name: "bashrc", path:
|
|
19081
|
-
{ name: "ghostty-config", path:
|
|
19082
|
-
{ name: "codex-config.toml", path:
|
|
19083
|
-
{ name: "codex-hooks.json", path:
|
|
19084
|
-
{ name: "opencode-config.json", path:
|
|
19298
|
+
{ name: "claude.json", path: path40.join(homeDir, ".claude.json") },
|
|
19299
|
+
{ name: "claude-settings.json", path: path40.join(homeDir, ".claude", "settings.json") },
|
|
19300
|
+
{ name: "claude-CLAUDE.md", path: path40.join(homeDir, ".claude", "CLAUDE.md") },
|
|
19301
|
+
{ name: "tmux.conf", path: path40.join(homeDir, ".tmux.conf") },
|
|
19302
|
+
{ name: "zshrc", path: path40.join(homeDir, ".zshrc") },
|
|
19303
|
+
{ name: "bashrc", path: path40.join(homeDir, ".bashrc") },
|
|
19304
|
+
{ name: "ghostty-config", path: path40.join(homeDir, ".config", "ghostty", "config") },
|
|
19305
|
+
{ name: "codex-config.toml", path: path40.join(homeDir, ".codex", "config.toml") },
|
|
19306
|
+
{ name: "codex-hooks.json", path: path40.join(homeDir, ".codex", "hooks.json") },
|
|
19307
|
+
{ name: "opencode-config.json", path: path40.join(homeDir, ".config", "opencode", "opencode.json") }
|
|
19085
19308
|
];
|
|
19086
19309
|
}
|
|
19087
19310
|
async function createUpdateBackup(currentVersion, dataDir2, homeDir = os20.homedir()) {
|
|
19088
19311
|
const dir = dataDir2 ?? resolveDataDir2();
|
|
19089
|
-
const backupDir =
|
|
19312
|
+
const backupDir = path40.join(dir, BACKUP_DIR_NAME);
|
|
19090
19313
|
if (existsSync33(backupDir)) {
|
|
19091
19314
|
await rm2(backupDir, { recursive: true, force: true });
|
|
19092
19315
|
}
|
|
19093
19316
|
await mkdir7(backupDir, { recursive: true });
|
|
19094
19317
|
const backedUpFiles = [];
|
|
19095
19318
|
for (const target of BACKUP_TARGETS) {
|
|
19096
|
-
const src =
|
|
19319
|
+
const src = path40.join(dir, target.name);
|
|
19097
19320
|
if (!existsSync33(src)) continue;
|
|
19098
|
-
const dest =
|
|
19321
|
+
const dest = path40.join(backupDir, target.name);
|
|
19099
19322
|
if (target.type === "file") {
|
|
19100
19323
|
await copyFile(src, dest);
|
|
19101
19324
|
} else {
|
|
@@ -19106,18 +19329,18 @@ async function createUpdateBackup(currentVersion, dataDir2, homeDir = os20.homed
|
|
|
19106
19329
|
const entries = await readdir3(dir, { withFileTypes: true });
|
|
19107
19330
|
for (const entry of entries) {
|
|
19108
19331
|
if (entry.isFile() && entry.name.endsWith(".db") && entry.name !== BACKUP_DIR_NAME) {
|
|
19109
|
-
const src =
|
|
19110
|
-
const dest =
|
|
19332
|
+
const src = path40.join(dir, entry.name);
|
|
19333
|
+
const dest = path40.join(backupDir, entry.name);
|
|
19111
19334
|
await copyFile(src, dest);
|
|
19112
19335
|
backedUpFiles.push(entry.name);
|
|
19113
19336
|
}
|
|
19114
19337
|
}
|
|
19115
19338
|
const externalFiles = [];
|
|
19116
|
-
const externalDir =
|
|
19339
|
+
const externalDir = path40.join(backupDir, "external");
|
|
19117
19340
|
for (const target of externalBackupTargets(homeDir)) {
|
|
19118
19341
|
if (!existsSync33(target.path)) continue;
|
|
19119
19342
|
await mkdir7(externalDir, { recursive: true });
|
|
19120
|
-
await copyFile(target.path,
|
|
19343
|
+
await copyFile(target.path, path40.join(externalDir, target.name));
|
|
19121
19344
|
externalFiles.push(target);
|
|
19122
19345
|
}
|
|
19123
19346
|
const manifest = {
|
|
@@ -19127,15 +19350,15 @@ async function createUpdateBackup(currentVersion, dataDir2, homeDir = os20.homed
|
|
|
19127
19350
|
...externalFiles.length > 0 ? { externalFiles } : {}
|
|
19128
19351
|
};
|
|
19129
19352
|
await writeFile7(
|
|
19130
|
-
|
|
19353
|
+
path40.join(backupDir, "manifest.json"),
|
|
19131
19354
|
JSON.stringify(manifest, null, 2) + "\n"
|
|
19132
19355
|
);
|
|
19133
19356
|
return manifest;
|
|
19134
19357
|
}
|
|
19135
19358
|
async function restoreFromBackup(dataDir2) {
|
|
19136
19359
|
const dir = dataDir2 ?? resolveDataDir2();
|
|
19137
|
-
const backupDir =
|
|
19138
|
-
const manifestPath =
|
|
19360
|
+
const backupDir = path40.join(dir, BACKUP_DIR_NAME);
|
|
19361
|
+
const manifestPath = path40.join(backupDir, "manifest.json");
|
|
19139
19362
|
if (!existsSync33(manifestPath)) {
|
|
19140
19363
|
throw new Error(
|
|
19141
19364
|
`No backup found at ${backupDir}. Nothing to restore.`
|
|
@@ -19145,8 +19368,8 @@ async function restoreFromBackup(dataDir2) {
|
|
|
19145
19368
|
await readFile6(manifestPath, "utf-8")
|
|
19146
19369
|
);
|
|
19147
19370
|
for (const fileName of manifest.files) {
|
|
19148
|
-
const src =
|
|
19149
|
-
const dest =
|
|
19371
|
+
const src = path40.join(backupDir, fileName);
|
|
19372
|
+
const dest = path40.join(dir, fileName);
|
|
19150
19373
|
if (!existsSync33(src)) continue;
|
|
19151
19374
|
const stat2 = await import("fs/promises").then((m) => m.stat(src));
|
|
19152
19375
|
if (stat2.isDirectory()) {
|
|
@@ -19156,16 +19379,16 @@ async function restoreFromBackup(dataDir2) {
|
|
|
19156
19379
|
}
|
|
19157
19380
|
}
|
|
19158
19381
|
for (const external of manifest.externalFiles ?? []) {
|
|
19159
|
-
const src =
|
|
19382
|
+
const src = path40.join(backupDir, "external", external.name);
|
|
19160
19383
|
if (!existsSync33(src)) continue;
|
|
19161
|
-
await mkdir7(
|
|
19384
|
+
await mkdir7(path40.dirname(external.path), { recursive: true });
|
|
19162
19385
|
await copyFile(src, external.path);
|
|
19163
19386
|
}
|
|
19164
19387
|
return manifest;
|
|
19165
19388
|
}
|
|
19166
19389
|
async function deleteBackup(dataDir2) {
|
|
19167
19390
|
const dir = dataDir2 ?? resolveDataDir2();
|
|
19168
|
-
const backupDir =
|
|
19391
|
+
const backupDir = path40.join(dir, BACKUP_DIR_NAME);
|
|
19169
19392
|
if (existsSync33(backupDir)) {
|
|
19170
19393
|
await rm2(backupDir, { recursive: true, force: true });
|
|
19171
19394
|
}
|
|
@@ -19191,21 +19414,21 @@ var init_update_backup = __esm({
|
|
|
19191
19414
|
|
|
19192
19415
|
// src/lib/update-check.ts
|
|
19193
19416
|
import { execSync as execSync14 } from "child_process";
|
|
19194
|
-
import { readFileSync as
|
|
19195
|
-
import
|
|
19417
|
+
import { readFileSync as readFileSync28 } from "fs";
|
|
19418
|
+
import path41 from "path";
|
|
19196
19419
|
function getLocalVersion(packageRoot) {
|
|
19197
|
-
const pkgPath =
|
|
19198
|
-
const pkg = JSON.parse(
|
|
19420
|
+
const pkgPath = path41.join(packageRoot, "package.json");
|
|
19421
|
+
const pkg = JSON.parse(readFileSync28(pkgPath, "utf-8"));
|
|
19199
19422
|
return pkg.version;
|
|
19200
19423
|
}
|
|
19201
19424
|
function getRemoteVersion() {
|
|
19202
19425
|
try {
|
|
19203
|
-
const
|
|
19426
|
+
const output2 = execSync14("npm view @askexenow/exe-os version", {
|
|
19204
19427
|
encoding: "utf-8",
|
|
19205
19428
|
timeout: 15e3,
|
|
19206
19429
|
stdio: ["pipe", "pipe", "pipe"]
|
|
19207
19430
|
});
|
|
19208
|
-
return
|
|
19431
|
+
return output2.trim();
|
|
19209
19432
|
} catch {
|
|
19210
19433
|
return null;
|
|
19211
19434
|
}
|
|
@@ -19415,6 +19638,15 @@ async function runUpdate(cliArgs) {
|
|
|
19415
19638
|
}
|
|
19416
19639
|
} catch {
|
|
19417
19640
|
}
|
|
19641
|
+
try {
|
|
19642
|
+
console.log("\u{1FA7A} Checking AskExe support intake...");
|
|
19643
|
+
execSync15("exe-os support health", {
|
|
19644
|
+
stdio: ["pipe", "inherit", "inherit"],
|
|
19645
|
+
timeout: 3e4
|
|
19646
|
+
});
|
|
19647
|
+
} catch {
|
|
19648
|
+
console.log(" \u26A0\uFE0F Support health check failed. Run: exe-os support test");
|
|
19649
|
+
}
|
|
19418
19650
|
console.log("\n\u{1F680} Ready. Start your COO session to use the new version.\n");
|
|
19419
19651
|
}
|
|
19420
19652
|
var init_update = __esm({
|
|
@@ -19436,10 +19668,10 @@ var init_update = __esm({
|
|
|
19436
19668
|
// src/lib/stack-update.ts
|
|
19437
19669
|
import { execFileSync as execFileSync4 } from "child_process";
|
|
19438
19670
|
import { createVerify, verify as verifySignature } from "crypto";
|
|
19439
|
-
import { existsSync as existsSync34, mkdirSync as
|
|
19671
|
+
import { existsSync as existsSync34, mkdirSync as mkdirSync24, readdirSync as readdirSync10, readFileSync as readFileSync29, renameSync as renameSync8, writeFileSync as writeFileSync25 } from "fs";
|
|
19440
19672
|
import http from "http";
|
|
19441
19673
|
import https from "https";
|
|
19442
|
-
import
|
|
19674
|
+
import path42 from "path";
|
|
19443
19675
|
function isSignedEnvelope(value) {
|
|
19444
19676
|
return !!value && typeof value === "object" && "manifest" in value && "signature" in value;
|
|
19445
19677
|
}
|
|
@@ -19473,21 +19705,21 @@ function stableJson(value) {
|
|
|
19473
19705
|
return `{${Object.keys(obj).sort().map((key) => `${JSON.stringify(key)}:${stableJson(obj[key])}`).join(",")}}`;
|
|
19474
19706
|
}
|
|
19475
19707
|
function findLatestBackupEnvFile(envFile) {
|
|
19476
|
-
const backupDir =
|
|
19708
|
+
const backupDir = path42.join(path42.dirname(envFile), ".exe-stack-backups");
|
|
19477
19709
|
if (!existsSync34(backupDir)) return null;
|
|
19478
19710
|
const backups = readdirSync10(backupDir).filter((name) => name.startsWith("env-") && name.endsWith(".bak")).sort();
|
|
19479
19711
|
const latest = backups.at(-1);
|
|
19480
|
-
return latest ?
|
|
19712
|
+
return latest ? path42.join(backupDir, latest) : null;
|
|
19481
19713
|
}
|
|
19482
19714
|
async function rollbackStackUpdate(options) {
|
|
19483
19715
|
const exec2 = options.exec ?? defaultExec;
|
|
19484
|
-
const backupEnvFile = options.lockFile && existsSync34(options.lockFile) ? JSON.parse(
|
|
19716
|
+
const backupEnvFile = options.lockFile && existsSync34(options.lockFile) ? JSON.parse(readFileSync29(options.lockFile, "utf8")).backupEnvFile : void 0;
|
|
19485
19717
|
const rollbackEnv = backupEnvFile && existsSync34(backupEnvFile) ? backupEnvFile : findLatestBackupEnvFile(options.envFile);
|
|
19486
19718
|
if (!rollbackEnv) throw new Error(`No stack backup env found beside ${options.envFile}`);
|
|
19487
|
-
|
|
19719
|
+
writeFileSync25(options.envFile, readFileSync29(rollbackEnv), { mode: 384 });
|
|
19488
19720
|
const composeArgs = ["compose", "--file", options.composeFile, "--env-file", options.envFile];
|
|
19489
19721
|
exec2("docker", [...composeArgs, "up", "-d"]);
|
|
19490
|
-
return { status: "rolled_back", targetVersion: "previous", changes: [], backupEnvFile: rollbackEnv, lockFile: options.lockFile ??
|
|
19722
|
+
return { status: "rolled_back", targetVersion: "previous", changes: [], backupEnvFile: rollbackEnv, lockFile: options.lockFile ?? path42.join(path42.dirname(options.envFile), ".exe-stack-lock.json") };
|
|
19491
19723
|
}
|
|
19492
19724
|
function parseStackManifest(raw, publicKey) {
|
|
19493
19725
|
const parsedRaw = JSON.parse(raw);
|
|
@@ -19512,7 +19744,7 @@ function parseStackManifest(raw, publicKey) {
|
|
|
19512
19744
|
}
|
|
19513
19745
|
async function loadStackManifest(ref, fetchText = defaultFetchText, publicKey, authToken) {
|
|
19514
19746
|
if (/^https?:\/\//.test(ref)) return parseStackManifest(await fetchTextWithAuth(ref, fetchText, authToken), publicKey);
|
|
19515
|
-
return parseStackManifest(
|
|
19747
|
+
return parseStackManifest(readFileSync29(ref, "utf8"), publicKey);
|
|
19516
19748
|
}
|
|
19517
19749
|
async function fetchTextWithAuth(ref, fetchText, authToken) {
|
|
19518
19750
|
if (!authToken || fetchText !== defaultFetchText) return fetchText(ref);
|
|
@@ -19641,9 +19873,9 @@ Emergency override requires --break-glass <reason> and writes an audit file.`
|
|
|
19641
19873
|
function writeBreakGlassAudit(plan, issues, options) {
|
|
19642
19874
|
const now2 = options.now ?? (() => /* @__PURE__ */ new Date());
|
|
19643
19875
|
const stamp = now2().toISOString().replace(/[:.]/g, "-");
|
|
19644
|
-
const defaultDir = existsSync34("exe/output") ? "exe/output" :
|
|
19645
|
-
const auditFile = options.breakGlassAuditFile ??
|
|
19646
|
-
|
|
19876
|
+
const defaultDir = existsSync34("exe/output") ? "exe/output" : path42.dirname(options.envFile ?? ".");
|
|
19877
|
+
const auditFile = options.breakGlassAuditFile ?? path42.join(defaultDir, `stack-update-break-glass-${stamp}.md`);
|
|
19878
|
+
mkdirSync24(path42.dirname(auditFile), { recursive: true });
|
|
19647
19879
|
const body = [
|
|
19648
19880
|
`# Stack Update Break-Glass Audit \u2014 ${now2().toISOString()}`,
|
|
19649
19881
|
"",
|
|
@@ -19657,7 +19889,7 @@ function writeBreakGlassAudit(plan, issues, options) {
|
|
|
19657
19889
|
"Return this deployment to the standard pinned GHCR image path immediately after the emergency is resolved.",
|
|
19658
19890
|
""
|
|
19659
19891
|
].join("\n");
|
|
19660
|
-
|
|
19892
|
+
writeFileSync25(auditFile, body, { mode: 384 });
|
|
19661
19893
|
console.warn(`[stack-update] BREAK-GLASS deploy override recorded: ${auditFile}`);
|
|
19662
19894
|
}
|
|
19663
19895
|
function assertBreakingChangesAllowed(plan, allowedIds) {
|
|
@@ -19679,33 +19911,33 @@ async function runStackUpdate(options) {
|
|
|
19679
19911
|
const now2 = options.now ?? (() => /* @__PURE__ */ new Date());
|
|
19680
19912
|
if (options.rollback) return rollbackStackUpdate(options);
|
|
19681
19913
|
const manifest = await loadStackManifest(options.manifestRef, options.fetchText, options.manifestPublicKey, options.manifestAuthToken);
|
|
19682
|
-
const envRaw =
|
|
19914
|
+
const envRaw = readFileSync29(options.envFile, "utf8");
|
|
19683
19915
|
const plan = createStackUpdatePlan(manifest, envRaw, options.targetVersion);
|
|
19684
19916
|
assertBreakingChangesAllowed(plan, options.allowedBreakingChangeIds ?? []);
|
|
19685
19917
|
assertDeploymentScopeAllowed(plan, options.deploymentPersona ?? "customer");
|
|
19686
19918
|
const plannedEnvRaw = patchEnv(envRaw, Object.fromEntries(plan.changes.map((c) => [c.key, c.after])));
|
|
19687
|
-
const composeRaw =
|
|
19919
|
+
const composeRaw = readFileSync29(options.composeFile, "utf8");
|
|
19688
19920
|
assertProductionDeployGate(plan, plannedEnvRaw, composeRaw, {
|
|
19689
19921
|
breakGlassReason: options.breakGlassReason,
|
|
19690
19922
|
breakGlassAuditFile: options.breakGlassAuditFile,
|
|
19691
19923
|
now: now2,
|
|
19692
19924
|
envFile: options.envFile
|
|
19693
19925
|
});
|
|
19694
|
-
const lockFile = options.lockFile ??
|
|
19926
|
+
const lockFile = options.lockFile ?? path42.join(path42.dirname(options.envFile), ".exe-stack-lock.json");
|
|
19695
19927
|
const previousVersion = readCurrentStackVersion(lockFile);
|
|
19696
19928
|
if (options.dryRun || plan.changes.length === 0) {
|
|
19697
19929
|
return { status: "planned", targetVersion: plan.targetVersion, changes: plan.changes, lockFile };
|
|
19698
19930
|
}
|
|
19699
19931
|
await postDeployAudit(options, "started", plan.targetVersion, previousVersion);
|
|
19700
|
-
const backupDir =
|
|
19701
|
-
|
|
19932
|
+
const backupDir = path42.join(path42.dirname(options.envFile), ".exe-stack-backups");
|
|
19933
|
+
mkdirSync24(backupDir, { recursive: true });
|
|
19702
19934
|
const stamp = now2().toISOString().replace(/[:.]/g, "-");
|
|
19703
|
-
const backupEnvFile =
|
|
19704
|
-
|
|
19935
|
+
const backupEnvFile = path42.join(backupDir, `env-${stamp}.bak`);
|
|
19936
|
+
writeFileSync25(backupEnvFile, envRaw, { mode: 384 });
|
|
19705
19937
|
const updates = Object.fromEntries(plan.changes.map((c) => [c.key, c.after]));
|
|
19706
19938
|
const patched = patchEnv(envRaw, updates);
|
|
19707
19939
|
const tmp = `${options.envFile}.tmp-${process.pid}`;
|
|
19708
|
-
|
|
19940
|
+
writeFileSync25(tmp, patched, { mode: 384 });
|
|
19709
19941
|
renameSync8(tmp, options.envFile);
|
|
19710
19942
|
const composeArgs = ["compose", "--file", options.composeFile, "--env-file", options.envFile];
|
|
19711
19943
|
let registryForLogout;
|
|
@@ -19718,11 +19950,11 @@ async function runStackUpdate(options) {
|
|
|
19718
19950
|
exec2("docker", [...composeArgs, "pull"]);
|
|
19719
19951
|
exec2("docker", [...composeArgs, "up", "-d"]);
|
|
19720
19952
|
await verifyReleaseHealth(plan.release, options.healthRetries ?? 12, options.healthDelayMs ?? 5e3);
|
|
19721
|
-
|
|
19953
|
+
writeFileSync25(lockFile, JSON.stringify({ stackVersion: plan.targetVersion, updatedAt: now2().toISOString(), backupEnvFile, services: plan.release.services }, null, 2) + "\n");
|
|
19722
19954
|
await postDeployAudit(options, "success", plan.targetVersion, previousVersion, void 0, { changes: plan.changes.length });
|
|
19723
19955
|
return { status: "updated", targetVersion: plan.targetVersion, changes: plan.changes, backupEnvFile, lockFile };
|
|
19724
19956
|
} catch (err) {
|
|
19725
|
-
|
|
19957
|
+
writeFileSync25(options.envFile, envRaw, { mode: 384 });
|
|
19726
19958
|
try {
|
|
19727
19959
|
exec2("docker", [...composeArgs, "up", "-d"]);
|
|
19728
19960
|
} catch {
|
|
@@ -19755,7 +19987,7 @@ async function fetchImageCredentials(options) {
|
|
|
19755
19987
|
function readCurrentStackVersion(lockFile) {
|
|
19756
19988
|
if (!existsSync34(lockFile)) return void 0;
|
|
19757
19989
|
try {
|
|
19758
|
-
const parsed = JSON.parse(
|
|
19990
|
+
const parsed = JSON.parse(readFileSync29(lockFile, "utf8"));
|
|
19759
19991
|
return parsed.stackVersion;
|
|
19760
19992
|
} catch {
|
|
19761
19993
|
return void 0;
|
|
@@ -19843,8 +20075,8 @@ async function defaultPostJson(url, body, authToken) {
|
|
|
19843
20075
|
if (!res.ok) throw new Error(`Failed to POST ${url}: HTTP ${res.status}`);
|
|
19844
20076
|
}
|
|
19845
20077
|
function defaultStackPaths() {
|
|
19846
|
-
const cwdCompose =
|
|
19847
|
-
const cwdEnv =
|
|
20078
|
+
const cwdCompose = path42.resolve("docker-compose.yml");
|
|
20079
|
+
const cwdEnv = path42.resolve(".env");
|
|
19848
20080
|
return {
|
|
19849
20081
|
composeFile: process.env.EXE_STACK_COMPOSE_FILE || (existsSync34(cwdCompose) ? cwdCompose : "/opt/exe-stack/docker-compose.yml"),
|
|
19850
20082
|
envFile: process.env.EXE_STACK_ENV_FILE || (existsSync34(cwdEnv) ? cwdEnv : "/opt/exe-stack/.env"),
|
|
@@ -19858,7 +20090,7 @@ function defaultStackPaths() {
|
|
|
19858
20090
|
function loadDefaultPublicKey() {
|
|
19859
20091
|
if (process.env.EXE_STACK_PUBLIC_KEY) return process.env.EXE_STACK_PUBLIC_KEY;
|
|
19860
20092
|
if (process.env.EXE_STACK_PUBLIC_KEY_FILE && existsSync34(process.env.EXE_STACK_PUBLIC_KEY_FILE)) {
|
|
19861
|
-
return
|
|
20093
|
+
return readFileSync29(process.env.EXE_STACK_PUBLIC_KEY_FILE, "utf8");
|
|
19862
20094
|
}
|
|
19863
20095
|
return void 0;
|
|
19864
20096
|
}
|
|
@@ -19873,9 +20105,9 @@ var init_stack_update = __esm({
|
|
|
19873
20105
|
// src/bin/stack-update.ts
|
|
19874
20106
|
var stack_update_exports = {};
|
|
19875
20107
|
__export(stack_update_exports, {
|
|
19876
|
-
runStackUpdateCli: () =>
|
|
20108
|
+
runStackUpdateCli: () => main7
|
|
19877
20109
|
});
|
|
19878
|
-
import { readFileSync as
|
|
20110
|
+
import { readFileSync as readFileSync30 } from "fs";
|
|
19879
20111
|
function parseArgs4(args2) {
|
|
19880
20112
|
const defaults = defaultStackPaths();
|
|
19881
20113
|
const opts = {
|
|
@@ -19907,8 +20139,8 @@ function parseArgs4(args2) {
|
|
|
19907
20139
|
else if (arg === "--env-file") opts.envFile = next();
|
|
19908
20140
|
else if (arg.startsWith("--env-file=")) opts.envFile = arg.split("=").slice(1).join("=");
|
|
19909
20141
|
else if (arg === "--lock-file") opts.lockFile = next();
|
|
19910
|
-
else if (arg === "--public-key") opts.manifestPublicKey =
|
|
19911
|
-
else if (arg.startsWith("--public-key=")) opts.manifestPublicKey =
|
|
20142
|
+
else if (arg === "--public-key") opts.manifestPublicKey = readFileSync30(next(), "utf8");
|
|
20143
|
+
else if (arg.startsWith("--public-key=")) opts.manifestPublicKey = readFileSync30(arg.split("=").slice(1).join("="), "utf8");
|
|
19912
20144
|
else if (arg === "--auth-token") opts.manifestAuthToken = next();
|
|
19913
20145
|
else if (arg.startsWith("--auth-token=")) opts.manifestAuthToken = arg.split("=").slice(1).join("=");
|
|
19914
20146
|
else if (arg === "--auth-token-env") opts.manifestAuthToken = process.env[next()] ?? "";
|
|
@@ -19999,7 +20231,7 @@ function printBreaking(changes) {
|
|
|
19999
20231
|
if (c.expectedDowntimeMinutes) console.log(` Expected downtime: ${c.expectedDowntimeMinutes} minutes`);
|
|
20000
20232
|
}
|
|
20001
20233
|
}
|
|
20002
|
-
async function
|
|
20234
|
+
async function main7() {
|
|
20003
20235
|
const opts = parseArgs4(process.argv.slice(2));
|
|
20004
20236
|
if (opts.rollback) {
|
|
20005
20237
|
if (!opts.yes) {
|
|
@@ -20011,11 +20243,11 @@ async function main6() {
|
|
|
20011
20243
|
return;
|
|
20012
20244
|
}
|
|
20013
20245
|
const manifest = await loadStackManifest(opts.manifestRef, void 0, opts.manifestPublicKey, opts.manifestAuthToken);
|
|
20014
|
-
const envRaw =
|
|
20246
|
+
const envRaw = readFileSync30(opts.envFile, "utf8");
|
|
20015
20247
|
const plan = createStackUpdatePlan(manifest, envRaw, opts.targetVersion);
|
|
20016
20248
|
assertDeploymentScopeAllowed(plan, opts.deploymentPersona);
|
|
20017
20249
|
const plannedEnvRaw = patchEnv(envRaw, Object.fromEntries(plan.changes.map((c) => [c.key, c.after])));
|
|
20018
|
-
assertProductionDeployGate(plan, plannedEnvRaw,
|
|
20250
|
+
assertProductionDeployGate(plan, plannedEnvRaw, readFileSync30(opts.composeFile, "utf8"), {
|
|
20019
20251
|
breakGlassReason: opts.breakGlassReason,
|
|
20020
20252
|
breakGlassAuditFile: opts.breakGlassAuditFile,
|
|
20021
20253
|
envFile: opts.envFile
|
|
@@ -20044,7 +20276,7 @@ var init_stack_update2 = __esm({
|
|
|
20044
20276
|
init_is_main();
|
|
20045
20277
|
init_stack_update();
|
|
20046
20278
|
if (isMainModule(import.meta.url)) {
|
|
20047
|
-
|
|
20279
|
+
main7().catch((err) => {
|
|
20048
20280
|
console.error(err instanceof Error ? err.message : String(err));
|
|
20049
20281
|
process.exit(1);
|
|
20050
20282
|
});
|
|
@@ -20216,7 +20448,7 @@ var init_registry_proxy = __esm({
|
|
|
20216
20448
|
// src/bin/registry-proxy.ts
|
|
20217
20449
|
var registry_proxy_exports = {};
|
|
20218
20450
|
__export(registry_proxy_exports, {
|
|
20219
|
-
main: () =>
|
|
20451
|
+
main: () => main8
|
|
20220
20452
|
});
|
|
20221
20453
|
function printHelp2() {
|
|
20222
20454
|
console.log(`exe-os registry-proxy \u2014 authenticated pull-through proxy for AskExe customer images
|
|
@@ -20235,7 +20467,7 @@ Docker image shape for clients:
|
|
|
20235
20467
|
registry.askexe.com/askexe/exe-crm:v0.9.3
|
|
20236
20468
|
`);
|
|
20237
20469
|
}
|
|
20238
|
-
async function
|
|
20470
|
+
async function main8(args2 = process.argv.slice(2)) {
|
|
20239
20471
|
if (args2.includes("--help") || args2.includes("-h")) {
|
|
20240
20472
|
printHelp2();
|
|
20241
20473
|
return;
|
|
@@ -20248,7 +20480,7 @@ var init_registry_proxy2 = __esm({
|
|
|
20248
20480
|
init_is_main();
|
|
20249
20481
|
init_registry_proxy();
|
|
20250
20482
|
if (isMainModule(import.meta.url)) {
|
|
20251
|
-
|
|
20483
|
+
main8().catch((err) => {
|
|
20252
20484
|
console.error(err instanceof Error ? err.message : String(err));
|
|
20253
20485
|
process.exit(1);
|
|
20254
20486
|
});
|
|
@@ -22567,17 +22799,17 @@ var init_sanitize_ansi = __esm({
|
|
|
22567
22799
|
if (!hasAnsiControlCharacters(text)) {
|
|
22568
22800
|
return text;
|
|
22569
22801
|
}
|
|
22570
|
-
let
|
|
22802
|
+
let output2 = "";
|
|
22571
22803
|
for (const token of tokenizeAnsi(text)) {
|
|
22572
22804
|
if (token.type === "text" || token.type === "osc") {
|
|
22573
|
-
|
|
22805
|
+
output2 += token.value;
|
|
22574
22806
|
continue;
|
|
22575
22807
|
}
|
|
22576
22808
|
if (token.type === "csi" && token.finalCharacter === "m" && token.intermediateString === "" && sgrParametersRegex.test(token.parameterString)) {
|
|
22577
|
-
|
|
22809
|
+
output2 += token.value;
|
|
22578
22810
|
}
|
|
22579
22811
|
}
|
|
22580
|
-
return
|
|
22812
|
+
return output2;
|
|
22581
22813
|
};
|
|
22582
22814
|
sanitize_ansi_default = sanitizeAnsi;
|
|
22583
22815
|
}
|
|
@@ -23364,7 +23596,7 @@ var init_render_border = __esm({
|
|
|
23364
23596
|
"src/tui/ink/render-border.js"() {
|
|
23365
23597
|
"use strict";
|
|
23366
23598
|
init_colorize();
|
|
23367
|
-
renderBorder = (x, y, node,
|
|
23599
|
+
renderBorder = (x, y, node, output2) => {
|
|
23368
23600
|
if (node.style.borderStyle) {
|
|
23369
23601
|
const width = node.yogaNode.getComputedWidth();
|
|
23370
23602
|
const height = node.yogaNode.getComputedHeight();
|
|
@@ -23407,18 +23639,18 @@ var init_render_border = __esm({
|
|
|
23407
23639
|
}
|
|
23408
23640
|
const offsetY = showTopBorder ? 1 : 0;
|
|
23409
23641
|
if (topBorder) {
|
|
23410
|
-
|
|
23642
|
+
output2.write(x, y, topBorder, { transformers: [] });
|
|
23411
23643
|
}
|
|
23412
23644
|
if (showLeftBorder) {
|
|
23413
|
-
|
|
23645
|
+
output2.write(x, y + offsetY, leftBorder, { transformers: [] });
|
|
23414
23646
|
}
|
|
23415
23647
|
if (showRightBorder) {
|
|
23416
|
-
|
|
23648
|
+
output2.write(x + width - 1, y + offsetY, rightBorder, {
|
|
23417
23649
|
transformers: []
|
|
23418
23650
|
});
|
|
23419
23651
|
}
|
|
23420
23652
|
if (bottomBorder) {
|
|
23421
|
-
|
|
23653
|
+
output2.write(x, y + height - 1, bottomBorder, { transformers: [] });
|
|
23422
23654
|
}
|
|
23423
23655
|
}
|
|
23424
23656
|
};
|
|
@@ -23432,7 +23664,7 @@ var init_render_background = __esm({
|
|
|
23432
23664
|
"src/tui/ink/render-background.js"() {
|
|
23433
23665
|
"use strict";
|
|
23434
23666
|
init_colorize();
|
|
23435
|
-
renderBackground = (x, y, node,
|
|
23667
|
+
renderBackground = (x, y, node, output2) => {
|
|
23436
23668
|
if (!node.style.backgroundColor) {
|
|
23437
23669
|
return;
|
|
23438
23670
|
}
|
|
@@ -23449,7 +23681,7 @@ var init_render_background = __esm({
|
|
|
23449
23681
|
}
|
|
23450
23682
|
const backgroundLine = colorize_default(" ".repeat(contentWidth), node.style.backgroundColor, "background");
|
|
23451
23683
|
for (let row = 0; row < contentHeight; row++) {
|
|
23452
|
-
|
|
23684
|
+
output2.write(x + leftBorderWidth, y + topBorderHeight + row, backgroundLine, { transformers: [] });
|
|
23453
23685
|
}
|
|
23454
23686
|
};
|
|
23455
23687
|
render_background_default = renderBackground;
|
|
@@ -23485,13 +23717,13 @@ var init_render_node_to_output = __esm({
|
|
|
23485
23717
|
if (node.yogaNode?.getDisplay() === src_default.DISPLAY_NONE) {
|
|
23486
23718
|
return "";
|
|
23487
23719
|
}
|
|
23488
|
-
let
|
|
23720
|
+
let output2 = "";
|
|
23489
23721
|
if (node.nodeName === "ink-text") {
|
|
23490
|
-
|
|
23722
|
+
output2 = squash_text_nodes_default(node);
|
|
23491
23723
|
} else if (node.nodeName === "ink-box" || node.nodeName === "ink-root") {
|
|
23492
23724
|
const separator = node.style.flexDirection === "row" || node.style.flexDirection === "row-reverse" ? " " : "\n";
|
|
23493
23725
|
const childNodes = node.style.flexDirection === "row-reverse" || node.style.flexDirection === "column-reverse" ? [...node.childNodes].reverse() : [...node.childNodes];
|
|
23494
|
-
|
|
23726
|
+
output2 = childNodes.map((childNode) => {
|
|
23495
23727
|
const screenReaderOutput = renderNodeToScreenReaderOutput(childNode, {
|
|
23496
23728
|
parentRole: node.internal_accessibility?.role,
|
|
23497
23729
|
skipStaticElements: options.skipStaticElements
|
|
@@ -23505,16 +23737,16 @@ var init_render_node_to_output = __esm({
|
|
|
23505
23737
|
const stateKeys = Object.keys(state);
|
|
23506
23738
|
const stateDescription = stateKeys.filter((key) => state[key]).join(", ");
|
|
23507
23739
|
if (stateDescription) {
|
|
23508
|
-
|
|
23740
|
+
output2 = `(${stateDescription}) ${output2}`;
|
|
23509
23741
|
}
|
|
23510
23742
|
}
|
|
23511
23743
|
if (role && role !== options.parentRole) {
|
|
23512
|
-
|
|
23744
|
+
output2 = `${role}: ${output2}`;
|
|
23513
23745
|
}
|
|
23514
23746
|
}
|
|
23515
|
-
return
|
|
23747
|
+
return output2;
|
|
23516
23748
|
};
|
|
23517
|
-
renderNodeToOutput = (node,
|
|
23749
|
+
renderNodeToOutput = (node, output2, options) => {
|
|
23518
23750
|
const { offsetX = 0, offsetY = 0, transformers = [], skipStaticElements } = options;
|
|
23519
23751
|
if (skipStaticElements && node.internal_static) {
|
|
23520
23752
|
return;
|
|
@@ -23540,14 +23772,14 @@ var init_render_node_to_output = __esm({
|
|
|
23540
23772
|
text = wrap_text_default(text, maxWidth, textWrap);
|
|
23541
23773
|
}
|
|
23542
23774
|
text = applyPaddingToText(node, text);
|
|
23543
|
-
|
|
23775
|
+
output2.write(x, y, text, { transformers: newTransformers });
|
|
23544
23776
|
}
|
|
23545
23777
|
return;
|
|
23546
23778
|
}
|
|
23547
23779
|
let clipped = false;
|
|
23548
23780
|
if (node.nodeName === "ink-box") {
|
|
23549
|
-
render_background_default(x, y, node,
|
|
23550
|
-
render_border_default(x, y, node,
|
|
23781
|
+
render_background_default(x, y, node, output2);
|
|
23782
|
+
render_border_default(x, y, node, output2);
|
|
23551
23783
|
const clipHorizontally = node.style.overflowX === "hidden" || node.style.overflow === "hidden";
|
|
23552
23784
|
const clipVertically = node.style.overflowY === "hidden" || node.style.overflow === "hidden";
|
|
23553
23785
|
if (clipHorizontally || clipVertically) {
|
|
@@ -23555,13 +23787,13 @@ var init_render_node_to_output = __esm({
|
|
|
23555
23787
|
const x2 = clipHorizontally ? x + yogaNode.getComputedWidth() - yogaNode.getComputedBorder(src_default.EDGE_RIGHT) : void 0;
|
|
23556
23788
|
const y1 = clipVertically ? y + yogaNode.getComputedBorder(src_default.EDGE_TOP) : void 0;
|
|
23557
23789
|
const y2 = clipVertically ? y + yogaNode.getComputedHeight() - yogaNode.getComputedBorder(src_default.EDGE_BOTTOM) : void 0;
|
|
23558
|
-
|
|
23790
|
+
output2.clip({ x1, x2, y1, y2 });
|
|
23559
23791
|
clipped = true;
|
|
23560
23792
|
}
|
|
23561
23793
|
}
|
|
23562
23794
|
if (node.nodeName === "ink-root" || node.nodeName === "ink-box") {
|
|
23563
23795
|
for (const childNode of node.childNodes) {
|
|
23564
|
-
renderNodeToOutput(childNode,
|
|
23796
|
+
renderNodeToOutput(childNode, output2, {
|
|
23565
23797
|
offsetX: x,
|
|
23566
23798
|
offsetY: y,
|
|
23567
23799
|
transformers: newTransformers,
|
|
@@ -23569,7 +23801,7 @@ var init_render_node_to_output = __esm({
|
|
|
23569
23801
|
});
|
|
23570
23802
|
}
|
|
23571
23803
|
if (clipped) {
|
|
23572
|
-
|
|
23804
|
+
output2.unclip();
|
|
23573
23805
|
}
|
|
23574
23806
|
}
|
|
23575
23807
|
}
|
|
@@ -23654,7 +23886,7 @@ var init_output = __esm({
|
|
|
23654
23886
|
});
|
|
23655
23887
|
}
|
|
23656
23888
|
get() {
|
|
23657
|
-
const
|
|
23889
|
+
const output2 = [];
|
|
23658
23890
|
for (let y = 0; y < this.height; y++) {
|
|
23659
23891
|
const row = [];
|
|
23660
23892
|
for (let x = 0; x < this.width; x++) {
|
|
@@ -23665,7 +23897,7 @@ var init_output = __esm({
|
|
|
23665
23897
|
styles: []
|
|
23666
23898
|
});
|
|
23667
23899
|
}
|
|
23668
|
-
|
|
23900
|
+
output2.push(row);
|
|
23669
23901
|
}
|
|
23670
23902
|
const clips = [];
|
|
23671
23903
|
for (const operation of this.operations) {
|
|
@@ -23718,7 +23950,7 @@ var init_output = __esm({
|
|
|
23718
23950
|
}
|
|
23719
23951
|
let offsetY = 0;
|
|
23720
23952
|
for (let [index, line] of lines.entries()) {
|
|
23721
|
-
const currentLine =
|
|
23953
|
+
const currentLine = output2[y + offsetY];
|
|
23722
23954
|
if (!currentLine) {
|
|
23723
23955
|
continue;
|
|
23724
23956
|
}
|
|
@@ -23746,13 +23978,13 @@ var init_output = __esm({
|
|
|
23746
23978
|
}
|
|
23747
23979
|
}
|
|
23748
23980
|
}
|
|
23749
|
-
const generatedOutput =
|
|
23981
|
+
const generatedOutput = output2.map((line) => {
|
|
23750
23982
|
const lineWithoutEmptyItems = line.filter((item) => item !== void 0);
|
|
23751
23983
|
return styledCharsToString(lineWithoutEmptyItems).trimEnd();
|
|
23752
23984
|
}).join("\n");
|
|
23753
23985
|
return {
|
|
23754
23986
|
output: generatedOutput,
|
|
23755
|
-
height:
|
|
23987
|
+
height: output2.length
|
|
23756
23988
|
};
|
|
23757
23989
|
}
|
|
23758
23990
|
};
|
|
@@ -23769,10 +24001,10 @@ var init_renderer = __esm({
|
|
|
23769
24001
|
renderer = (node, isScreenReaderEnabled) => {
|
|
23770
24002
|
if (node.yogaNode) {
|
|
23771
24003
|
if (isScreenReaderEnabled) {
|
|
23772
|
-
const
|
|
24004
|
+
const output3 = renderNodeToScreenReaderOutput(node, {
|
|
23773
24005
|
skipStaticElements: true
|
|
23774
24006
|
});
|
|
23775
|
-
const outputHeight2 =
|
|
24007
|
+
const outputHeight2 = output3 === "" ? 0 : output3.split("\n").length;
|
|
23776
24008
|
let staticOutput2 = "";
|
|
23777
24009
|
if (node.staticNode) {
|
|
23778
24010
|
staticOutput2 = renderNodeToScreenReaderOutput(node.staticNode, {
|
|
@@ -23780,17 +24012,17 @@ var init_renderer = __esm({
|
|
|
23780
24012
|
});
|
|
23781
24013
|
}
|
|
23782
24014
|
return {
|
|
23783
|
-
output:
|
|
24015
|
+
output: output3,
|
|
23784
24016
|
outputHeight: outputHeight2,
|
|
23785
24017
|
staticOutput: staticOutput2 ? `${staticOutput2}
|
|
23786
24018
|
` : ""
|
|
23787
24019
|
};
|
|
23788
24020
|
}
|
|
23789
|
-
const
|
|
24021
|
+
const output2 = new Output({
|
|
23790
24022
|
width: node.yogaNode.getComputedWidth(),
|
|
23791
24023
|
height: node.yogaNode.getComputedHeight()
|
|
23792
24024
|
});
|
|
23793
|
-
render_node_to_output_default(node,
|
|
24025
|
+
render_node_to_output_default(node, output2, {
|
|
23794
24026
|
skipStaticElements: true
|
|
23795
24027
|
});
|
|
23796
24028
|
let staticOutput;
|
|
@@ -23803,7 +24035,7 @@ var init_renderer = __esm({
|
|
|
23803
24035
|
skipStaticElements: false
|
|
23804
24036
|
});
|
|
23805
24037
|
}
|
|
23806
|
-
const { output: generatedOutput, height: outputHeight } =
|
|
24038
|
+
const { output: generatedOutput, height: outputHeight } = output2.get();
|
|
23807
24039
|
return {
|
|
23808
24040
|
output: generatedOutput,
|
|
23809
24041
|
outputHeight,
|
|
@@ -24614,8 +24846,8 @@ var init_ErrorOverview = __esm({
|
|
|
24614
24846
|
"use strict";
|
|
24615
24847
|
init_Box();
|
|
24616
24848
|
init_Text();
|
|
24617
|
-
cleanupPath = (
|
|
24618
|
-
return
|
|
24849
|
+
cleanupPath = (path56) => {
|
|
24850
|
+
return path56?.replace(`file://${cwd()}/`, "");
|
|
24619
24851
|
};
|
|
24620
24852
|
stackUtils = new StackUtils({
|
|
24621
24853
|
cwd: cwd(),
|
|
@@ -25236,13 +25468,13 @@ var init_ink = __esm({
|
|
|
25236
25468
|
incremental: options.incrementalRendering
|
|
25237
25469
|
});
|
|
25238
25470
|
this.cursorPosition = void 0;
|
|
25239
|
-
this.throttledLog = unthrottled ? this.log : throttle((
|
|
25240
|
-
const shouldWrite = this.log.willRender(
|
|
25471
|
+
this.throttledLog = unthrottled ? this.log : throttle((output2) => {
|
|
25472
|
+
const shouldWrite = this.log.willRender(output2);
|
|
25241
25473
|
const sync = shouldSynchronize(this.options.stdout);
|
|
25242
25474
|
if (sync && shouldWrite) {
|
|
25243
25475
|
this.options.stdout.write(bsu);
|
|
25244
25476
|
}
|
|
25245
|
-
this.log(
|
|
25477
|
+
this.log(output2);
|
|
25246
25478
|
if (sync && shouldWrite) {
|
|
25247
25479
|
this.options.stdout.write(esu);
|
|
25248
25480
|
}
|
|
@@ -25333,22 +25565,22 @@ var init_ink = __esm({
|
|
|
25333
25565
|
return;
|
|
25334
25566
|
}
|
|
25335
25567
|
const startTime = performance.now();
|
|
25336
|
-
const { output, outputHeight, staticOutput } = renderer_default(this.rootNode, this.isScreenReaderEnabled);
|
|
25568
|
+
const { output: output2, outputHeight, staticOutput } = renderer_default(this.rootNode, this.isScreenReaderEnabled);
|
|
25337
25569
|
this.options.onRender?.({ renderTime: performance.now() - startTime });
|
|
25338
25570
|
const hasStaticOutput = staticOutput && staticOutput !== "\n";
|
|
25339
25571
|
if (this.options.debug) {
|
|
25340
25572
|
if (hasStaticOutput) {
|
|
25341
25573
|
this.fullStaticOutput += staticOutput;
|
|
25342
25574
|
}
|
|
25343
|
-
this.options.stdout.write(this.fullStaticOutput +
|
|
25575
|
+
this.options.stdout.write(this.fullStaticOutput + output2);
|
|
25344
25576
|
return;
|
|
25345
25577
|
}
|
|
25346
25578
|
if (isInCi2) {
|
|
25347
25579
|
if (hasStaticOutput) {
|
|
25348
25580
|
this.options.stdout.write(staticOutput);
|
|
25349
25581
|
}
|
|
25350
|
-
this.lastOutput =
|
|
25351
|
-
this.lastOutputToRender =
|
|
25582
|
+
this.lastOutput = output2;
|
|
25583
|
+
this.lastOutputToRender = output2 + "\n";
|
|
25352
25584
|
this.lastOutputHeight = outputHeight;
|
|
25353
25585
|
return;
|
|
25354
25586
|
}
|
|
@@ -25362,14 +25594,14 @@ var init_ink = __esm({
|
|
|
25362
25594
|
this.options.stdout.write(erase + staticOutput);
|
|
25363
25595
|
this.lastOutputHeight = 0;
|
|
25364
25596
|
}
|
|
25365
|
-
if (
|
|
25597
|
+
if (output2 === this.lastOutput && !hasStaticOutput) {
|
|
25366
25598
|
if (sync) {
|
|
25367
25599
|
this.options.stdout.write(esu);
|
|
25368
25600
|
}
|
|
25369
25601
|
return;
|
|
25370
25602
|
}
|
|
25371
25603
|
const terminalWidth = this.getTerminalWidth();
|
|
25372
|
-
const wrappedOutput = wrapAnsi2(
|
|
25604
|
+
const wrappedOutput = wrapAnsi2(output2, terminalWidth, {
|
|
25373
25605
|
trim: false,
|
|
25374
25606
|
hard: true
|
|
25375
25607
|
});
|
|
@@ -25379,7 +25611,7 @@ var init_ink = __esm({
|
|
|
25379
25611
|
const erase = this.lastOutputHeight > 0 ? ansiEscapes3.eraseLines(this.lastOutputHeight) : "";
|
|
25380
25612
|
this.options.stdout.write(erase + wrappedOutput);
|
|
25381
25613
|
}
|
|
25382
|
-
this.lastOutput =
|
|
25614
|
+
this.lastOutput = output2;
|
|
25383
25615
|
this.lastOutputToRender = wrappedOutput;
|
|
25384
25616
|
this.lastOutputHeight = wrappedOutput === "" ? 0 : wrappedOutput.split("\n").length;
|
|
25385
25617
|
if (sync) {
|
|
@@ -25391,14 +25623,14 @@ var init_ink = __esm({
|
|
|
25391
25623
|
this.fullStaticOutput += staticOutput;
|
|
25392
25624
|
}
|
|
25393
25625
|
const isFullscreen = this.options.stdout.isTTY && outputHeight >= this.options.stdout.rows;
|
|
25394
|
-
const outputToRender = isFullscreen ?
|
|
25626
|
+
const outputToRender = isFullscreen ? output2 : output2 + "\n";
|
|
25395
25627
|
if (this.lastOutputHeight >= this.options.stdout.rows) {
|
|
25396
25628
|
const sync = shouldSynchronize(this.options.stdout);
|
|
25397
25629
|
if (sync) {
|
|
25398
25630
|
this.options.stdout.write(bsu);
|
|
25399
25631
|
}
|
|
25400
|
-
this.options.stdout.write(ansiEscapes3.clearTerminal + this.fullStaticOutput +
|
|
25401
|
-
this.lastOutput =
|
|
25632
|
+
this.options.stdout.write(ansiEscapes3.clearTerminal + this.fullStaticOutput + output2);
|
|
25633
|
+
this.lastOutput = output2;
|
|
25402
25634
|
this.lastOutputToRender = outputToRender;
|
|
25403
25635
|
this.lastOutputHeight = outputHeight;
|
|
25404
25636
|
this.log.sync(outputToRender);
|
|
@@ -25418,10 +25650,10 @@ var init_ink = __esm({
|
|
|
25418
25650
|
if (sync) {
|
|
25419
25651
|
this.options.stdout.write(esu);
|
|
25420
25652
|
}
|
|
25421
|
-
} else if (
|
|
25653
|
+
} else if (output2 !== this.lastOutput || this.log.isCursorDirty()) {
|
|
25422
25654
|
this.throttledLog(outputToRender);
|
|
25423
25655
|
}
|
|
25424
|
-
this.lastOutput =
|
|
25656
|
+
this.lastOutput = output2;
|
|
25425
25657
|
this.lastOutputToRender = outputToRender;
|
|
25426
25658
|
this.lastOutputHeight = outputHeight;
|
|
25427
25659
|
};
|
|
@@ -28760,7 +28992,7 @@ var init_anthropic = __esm({
|
|
|
28760
28992
|
|
|
28761
28993
|
// src/lib/providers/openai-compat.ts
|
|
28762
28994
|
import OpenAI from "openai";
|
|
28763
|
-
import { randomUUID as
|
|
28995
|
+
import { randomUUID as randomUUID6 } from "crypto";
|
|
28764
28996
|
var OpenAICompatProvider;
|
|
28765
28997
|
var init_openai_compat = __esm({
|
|
28766
28998
|
"src/lib/providers/openai-compat.ts"() {
|
|
@@ -28877,7 +29109,7 @@ var init_openai_compat = __esm({
|
|
|
28877
29109
|
}
|
|
28878
29110
|
content.push({
|
|
28879
29111
|
type: "tool_use",
|
|
28880
|
-
id: call.id ??
|
|
29112
|
+
id: call.id ?? randomUUID6(),
|
|
28881
29113
|
name: fn.name,
|
|
28882
29114
|
input
|
|
28883
29115
|
});
|
|
@@ -29078,10 +29310,10 @@ var init_hooks = __esm({
|
|
|
29078
29310
|
});
|
|
29079
29311
|
|
|
29080
29312
|
// src/runtime/safety-checks.ts
|
|
29081
|
-
import
|
|
29313
|
+
import path43 from "path";
|
|
29082
29314
|
import os21 from "os";
|
|
29083
29315
|
function checkPathSafety(filePath) {
|
|
29084
|
-
const resolved =
|
|
29316
|
+
const resolved = path43.resolve(filePath);
|
|
29085
29317
|
for (const { pattern, reason } of BYPASS_IMMUNE_PATTERNS) {
|
|
29086
29318
|
const matches = typeof pattern === "function" ? pattern(resolved) : pattern.test(resolved);
|
|
29087
29319
|
if (matches) {
|
|
@@ -29091,7 +29323,7 @@ function checkPathSafety(filePath) {
|
|
|
29091
29323
|
return { safe: true, bypassImmune: true };
|
|
29092
29324
|
}
|
|
29093
29325
|
function checkReadPathSafety(filePath) {
|
|
29094
|
-
const resolved =
|
|
29326
|
+
const resolved = path43.resolve(filePath);
|
|
29095
29327
|
const credPatterns = BYPASS_IMMUNE_PATTERNS.filter(
|
|
29096
29328
|
(p) => typeof p.pattern !== "function" && (p.reason.includes("secrets") || p.reason.includes("Private key") || p.reason.includes("Credential"))
|
|
29097
29329
|
);
|
|
@@ -29117,11 +29349,11 @@ var init_safety_checks = __esm({
|
|
|
29117
29349
|
reason: "Git config can set hooks and command execution"
|
|
29118
29350
|
},
|
|
29119
29351
|
{
|
|
29120
|
-
pattern: (p) => p.startsWith(
|
|
29352
|
+
pattern: (p) => p.startsWith(path43.join(HOME, ".claude")),
|
|
29121
29353
|
reason: "Claude configuration files are protected"
|
|
29122
29354
|
},
|
|
29123
29355
|
{
|
|
29124
|
-
pattern: (p) => p.startsWith(
|
|
29356
|
+
pattern: (p) => p.startsWith(path43.join(HOME, ".exe-os")),
|
|
29125
29357
|
reason: "exe-os configuration files are protected"
|
|
29126
29358
|
},
|
|
29127
29359
|
{
|
|
@@ -29138,7 +29370,7 @@ var init_safety_checks = __esm({
|
|
|
29138
29370
|
},
|
|
29139
29371
|
{
|
|
29140
29372
|
pattern: (p) => {
|
|
29141
|
-
const name =
|
|
29373
|
+
const name = path43.basename(p);
|
|
29142
29374
|
return [".bashrc", ".zshrc", ".profile", ".bash_profile", ".zprofile", ".zshenv"].includes(name);
|
|
29143
29375
|
},
|
|
29144
29376
|
reason: "Shell configuration files can execute arbitrary code on login"
|
|
@@ -29165,7 +29397,7 @@ __export(file_read_exports, {
|
|
|
29165
29397
|
FileReadTool: () => FileReadTool
|
|
29166
29398
|
});
|
|
29167
29399
|
import fs3 from "fs/promises";
|
|
29168
|
-
import
|
|
29400
|
+
import path44 from "path";
|
|
29169
29401
|
import { z } from "zod";
|
|
29170
29402
|
function isBinary(buf) {
|
|
29171
29403
|
for (let i = 0; i < buf.length; i++) {
|
|
@@ -29201,7 +29433,7 @@ var init_file_read = __esm({
|
|
|
29201
29433
|
return { behavior: "allow" };
|
|
29202
29434
|
},
|
|
29203
29435
|
async call(input, context) {
|
|
29204
|
-
const filePath =
|
|
29436
|
+
const filePath = path44.isAbsolute(input.file_path) ? input.file_path : path44.resolve(context.cwd, input.file_path);
|
|
29205
29437
|
let stat2;
|
|
29206
29438
|
try {
|
|
29207
29439
|
stat2 = await fs3.stat(filePath);
|
|
@@ -29241,7 +29473,7 @@ __export(glob_exports, {
|
|
|
29241
29473
|
GlobTool: () => GlobTool
|
|
29242
29474
|
});
|
|
29243
29475
|
import fs4 from "fs/promises";
|
|
29244
|
-
import
|
|
29476
|
+
import path45 from "path";
|
|
29245
29477
|
import { z as z2 } from "zod";
|
|
29246
29478
|
async function walkDir(dir, maxDepth = 10) {
|
|
29247
29479
|
const results = [];
|
|
@@ -29257,7 +29489,7 @@ async function walkDir(dir, maxDepth = 10) {
|
|
|
29257
29489
|
if (entry.isDirectory() && (entry.name === "node_modules" || entry.name === ".git")) {
|
|
29258
29490
|
continue;
|
|
29259
29491
|
}
|
|
29260
|
-
const fullPath =
|
|
29492
|
+
const fullPath = path45.join(current, entry.name);
|
|
29261
29493
|
if (entry.isDirectory()) {
|
|
29262
29494
|
await walk(fullPath, depth + 1);
|
|
29263
29495
|
} else {
|
|
@@ -29291,11 +29523,11 @@ var init_glob = __esm({
|
|
|
29291
29523
|
inputSchema: inputSchema2,
|
|
29292
29524
|
isReadOnly: true,
|
|
29293
29525
|
async call(input, context) {
|
|
29294
|
-
const baseDir = input.path ?
|
|
29526
|
+
const baseDir = input.path ? path45.isAbsolute(input.path) ? input.path : path45.resolve(context.cwd, input.path) : context.cwd;
|
|
29295
29527
|
try {
|
|
29296
29528
|
const entries = await walkDir(baseDir);
|
|
29297
29529
|
const matched = entries.filter(
|
|
29298
|
-
(e) => simpleGlobMatch(
|
|
29530
|
+
(e) => simpleGlobMatch(path45.relative(baseDir, e.path), input.pattern)
|
|
29299
29531
|
);
|
|
29300
29532
|
matched.sort((a, b) => b.mtime - a.mtime);
|
|
29301
29533
|
if (matched.length === 0) {
|
|
@@ -29321,7 +29553,7 @@ __export(grep_exports, {
|
|
|
29321
29553
|
});
|
|
29322
29554
|
import { spawn as spawn2 } from "child_process";
|
|
29323
29555
|
import fs5 from "fs/promises";
|
|
29324
|
-
import
|
|
29556
|
+
import path46 from "path";
|
|
29325
29557
|
import { z as z3 } from "zod";
|
|
29326
29558
|
function runRipgrep(input, searchPath, context) {
|
|
29327
29559
|
return new Promise((resolve, reject) => {
|
|
@@ -29349,8 +29581,8 @@ function runRipgrep(input, searchPath, context) {
|
|
|
29349
29581
|
context.abortSignal.addEventListener("abort", onAbort, { once: true });
|
|
29350
29582
|
child.on("close", (code) => {
|
|
29351
29583
|
context.abortSignal.removeEventListener("abort", onAbort);
|
|
29352
|
-
const
|
|
29353
|
-
if (code === 1 && !
|
|
29584
|
+
const output2 = Buffer.concat(chunks).toString("utf-8").trim();
|
|
29585
|
+
if (code === 1 && !output2) {
|
|
29354
29586
|
resolve({ content: "No matches found." });
|
|
29355
29587
|
return;
|
|
29356
29588
|
}
|
|
@@ -29358,7 +29590,7 @@ function runRipgrep(input, searchPath, context) {
|
|
|
29358
29590
|
reject(new Error("ripgrep error"));
|
|
29359
29591
|
return;
|
|
29360
29592
|
}
|
|
29361
|
-
resolve({ content:
|
|
29593
|
+
resolve({ content: output2 || "No matches found." });
|
|
29362
29594
|
});
|
|
29363
29595
|
child.on("error", () => reject(new Error("rg not found")));
|
|
29364
29596
|
});
|
|
@@ -29375,7 +29607,7 @@ async function nodeGrep(input, searchPath) {
|
|
|
29375
29607
|
}
|
|
29376
29608
|
for (const entry of entries) {
|
|
29377
29609
|
if (entry.name === "node_modules" || entry.name === ".git") continue;
|
|
29378
|
-
const fullPath =
|
|
29610
|
+
const fullPath = path46.join(dir, entry.name);
|
|
29379
29611
|
if (entry.isDirectory()) {
|
|
29380
29612
|
await walk(fullPath);
|
|
29381
29613
|
} else {
|
|
@@ -29421,7 +29653,7 @@ var init_grep = __esm({
|
|
|
29421
29653
|
inputSchema: inputSchema3,
|
|
29422
29654
|
isReadOnly: true,
|
|
29423
29655
|
async call(input, context) {
|
|
29424
|
-
const searchPath = input.path ?
|
|
29656
|
+
const searchPath = input.path ? path46.isAbsolute(input.path) ? input.path : path46.resolve(context.cwd, input.path) : context.cwd;
|
|
29425
29657
|
try {
|
|
29426
29658
|
const result = await runRipgrep(input, searchPath, context);
|
|
29427
29659
|
return result;
|
|
@@ -29446,7 +29678,7 @@ __export(file_write_exports, {
|
|
|
29446
29678
|
FileWriteTool: () => FileWriteTool
|
|
29447
29679
|
});
|
|
29448
29680
|
import fs6 from "fs/promises";
|
|
29449
|
-
import
|
|
29681
|
+
import path47 from "path";
|
|
29450
29682
|
import { z as z4 } from "zod";
|
|
29451
29683
|
var inputSchema4, FileWriteTool;
|
|
29452
29684
|
var init_file_write = __esm({
|
|
@@ -29474,8 +29706,8 @@ var init_file_write = __esm({
|
|
|
29474
29706
|
return { behavior: "allow" };
|
|
29475
29707
|
},
|
|
29476
29708
|
async call(input, context) {
|
|
29477
|
-
const filePath =
|
|
29478
|
-
const dir =
|
|
29709
|
+
const filePath = path47.isAbsolute(input.file_path) ? input.file_path : path47.resolve(context.cwd, input.file_path);
|
|
29710
|
+
const dir = path47.dirname(filePath);
|
|
29479
29711
|
await fs6.mkdir(dir, { recursive: true });
|
|
29480
29712
|
await fs6.writeFile(filePath, input.content, "utf-8");
|
|
29481
29713
|
return {
|
|
@@ -29493,7 +29725,7 @@ __export(file_edit_exports, {
|
|
|
29493
29725
|
FileEditTool: () => FileEditTool
|
|
29494
29726
|
});
|
|
29495
29727
|
import fs7 from "fs/promises";
|
|
29496
|
-
import
|
|
29728
|
+
import path48 from "path";
|
|
29497
29729
|
import { z as z5 } from "zod";
|
|
29498
29730
|
function countOccurrences(haystack, needle) {
|
|
29499
29731
|
let count = 0;
|
|
@@ -29534,7 +29766,7 @@ var init_file_edit = __esm({
|
|
|
29534
29766
|
return { behavior: "allow" };
|
|
29535
29767
|
},
|
|
29536
29768
|
async call(input, context) {
|
|
29537
|
-
const filePath =
|
|
29769
|
+
const filePath = path48.isAbsolute(input.file_path) ? input.file_path : path48.resolve(context.cwd, input.file_path);
|
|
29538
29770
|
let content;
|
|
29539
29771
|
try {
|
|
29540
29772
|
content = await fs7.readFile(filePath, "utf-8");
|
|
@@ -29757,8 +29989,8 @@ var init_bash = __esm({
|
|
|
29757
29989
|
return;
|
|
29758
29990
|
}
|
|
29759
29991
|
if (code !== 0) {
|
|
29760
|
-
const
|
|
29761
|
-
resolve({ content:
|
|
29992
|
+
const output2 = stderr || stdout || `Exit code ${code}`;
|
|
29993
|
+
resolve({ content: output2, isError: true });
|
|
29762
29994
|
return;
|
|
29763
29995
|
}
|
|
29764
29996
|
resolve({ content: stdout || "(no output)" });
|
|
@@ -29776,7 +30008,7 @@ var init_bash = __esm({
|
|
|
29776
30008
|
// src/tui/views/CommandCenter.tsx
|
|
29777
30009
|
import { useState as useState6, useEffect as useEffect8, useMemo as useMemo4, useCallback as useCallback4, useRef as useRef4 } from "react";
|
|
29778
30010
|
import TextInput from "ink-text-input";
|
|
29779
|
-
import
|
|
30011
|
+
import path49 from "path";
|
|
29780
30012
|
import { homedir as homedir6 } from "os";
|
|
29781
30013
|
import { Fragment as Fragment2, jsx as jsx7, jsxs as jsxs5 } from "react/jsx-runtime";
|
|
29782
30014
|
function CommandCenterView({
|
|
@@ -29811,7 +30043,7 @@ function CommandCenterView({
|
|
|
29811
30043
|
const { createPermissionsFromPreset: createPermissionsFromPreset2, EMPLOYEE_PERMISSIONS: EMPLOYEE_PERMISSIONS2 } = await Promise.resolve().then(() => (init_permissions(), permissions_exports));
|
|
29812
30044
|
const { getPresetByRole: getPresetByRole2 } = await Promise.resolve().then(() => (init_permission_presets(), permission_presets_exports));
|
|
29813
30045
|
const { createDefaultHooks: createDefaultHooks2 } = await Promise.resolve().then(() => (init_hooks(), hooks_exports));
|
|
29814
|
-
const { readFileSync:
|
|
30046
|
+
const { readFileSync: readFileSync37, existsSync: existsSync41 } = await import("fs");
|
|
29815
30047
|
const { join } = await import("path");
|
|
29816
30048
|
const { homedir: homedir8 } = await import("os");
|
|
29817
30049
|
const configPath = join(homedir8(), ".exe-os", "config.json");
|
|
@@ -29819,7 +30051,7 @@ function CommandCenterView({
|
|
|
29819
30051
|
let providerConfigs = {};
|
|
29820
30052
|
if (existsSync41(configPath)) {
|
|
29821
30053
|
try {
|
|
29822
|
-
const raw = JSON.parse(
|
|
30054
|
+
const raw = JSON.parse(readFileSync37(configPath, "utf8"));
|
|
29823
30055
|
if (Array.isArray(raw.failoverChain)) failoverChain = raw.failoverChain;
|
|
29824
30056
|
if (raw.providers && typeof raw.providers === "object") {
|
|
29825
30057
|
providerConfigs = raw.providers;
|
|
@@ -29880,7 +30112,7 @@ function CommandCenterView({
|
|
|
29880
30112
|
const markerDir = join(homedir8(), ".exe-os", "session-cache");
|
|
29881
30113
|
const agentFiles = (await import("fs")).readdirSync(markerDir).filter((f) => f.startsWith("active-agent-"));
|
|
29882
30114
|
for (const f of agentFiles) {
|
|
29883
|
-
const data = JSON.parse(
|
|
30115
|
+
const data = JSON.parse(readFileSync37(join(markerDir, f), "utf8"));
|
|
29884
30116
|
if (data.agentRole) {
|
|
29885
30117
|
agentRole = data.agentRole;
|
|
29886
30118
|
break;
|
|
@@ -30025,7 +30257,7 @@ function CommandCenterView({
|
|
|
30025
30257
|
const demoEntries = DEMO_PROJECTS.map((p) => ({
|
|
30026
30258
|
projectName: p.projectName,
|
|
30027
30259
|
exeSession: p.exeSession,
|
|
30028
|
-
projectDir:
|
|
30260
|
+
projectDir: path49.join(homedir6(), p.projectName),
|
|
30029
30261
|
employeeCount: p.employees.length,
|
|
30030
30262
|
activeCount: p.employees.filter((e) => e.status === "active").length,
|
|
30031
30263
|
memoryCount: p.employees.length * 4e3,
|
|
@@ -30401,11 +30633,11 @@ function TmuxPane({ sessionName, employeeName, employeeRole, projectName, onDeta
|
|
|
30401
30633
|
const capture = () => {
|
|
30402
30634
|
try {
|
|
30403
30635
|
const { execSync: execSync18 } = __require("child_process");
|
|
30404
|
-
const
|
|
30636
|
+
const output2 = execSync18(
|
|
30405
30637
|
`tmux capture-pane -t ${JSON.stringify(sessionName)} -p -e 2>/dev/null | tail -${CAPTURE_LINES}`,
|
|
30406
30638
|
{ encoding: "utf8", timeout: 3e3 }
|
|
30407
30639
|
);
|
|
30408
|
-
setLines(
|
|
30640
|
+
setLines(output2.split("\n"));
|
|
30409
30641
|
setAlive(true);
|
|
30410
30642
|
} catch {
|
|
30411
30643
|
setAlive(false);
|
|
@@ -30506,7 +30738,7 @@ var init_TmuxPane = __esm({
|
|
|
30506
30738
|
});
|
|
30507
30739
|
|
|
30508
30740
|
// src/lib/task-router.ts
|
|
30509
|
-
import { randomUUID as
|
|
30741
|
+
import { randomUUID as randomUUID7 } from "crypto";
|
|
30510
30742
|
function resolveBloomRouting(complexity, config = DEFAULT_BLOOM_CONFIG) {
|
|
30511
30743
|
const tier = config.complexityToTier[complexity];
|
|
30512
30744
|
const rule = config.tierRules[tier];
|
|
@@ -31029,7 +31261,7 @@ var init_useOrchestrator = __esm({
|
|
|
31029
31261
|
|
|
31030
31262
|
// src/tui/views/Sessions.tsx
|
|
31031
31263
|
import React19, { useState as useState9, useEffect as useEffect11, useCallback as useCallback6 } from "react";
|
|
31032
|
-
import
|
|
31264
|
+
import path50 from "path";
|
|
31033
31265
|
import { homedir as homedir7 } from "os";
|
|
31034
31266
|
import { jsx as jsx9, jsxs as jsxs7 } from "react/jsx-runtime";
|
|
31035
31267
|
function isCoordinatorEntry(entry) {
|
|
@@ -31067,7 +31299,7 @@ function SessionsView({
|
|
|
31067
31299
|
if (demo) {
|
|
31068
31300
|
setProjects(DEMO_PROJECTS.map((p) => ({
|
|
31069
31301
|
...p,
|
|
31070
|
-
projectDir:
|
|
31302
|
+
projectDir: path50.join(homedir7(), p.projectName),
|
|
31071
31303
|
employees: p.employees.map((e) => ({ ...e, attached: e.status === "active" }))
|
|
31072
31304
|
})));
|
|
31073
31305
|
return;
|
|
@@ -32282,12 +32514,12 @@ async function loadGatewayConfig() {
|
|
|
32282
32514
|
state.running = false;
|
|
32283
32515
|
}
|
|
32284
32516
|
try {
|
|
32285
|
-
const { existsSync: existsSync41, readFileSync:
|
|
32517
|
+
const { existsSync: existsSync41, readFileSync: readFileSync37 } = await import("fs");
|
|
32286
32518
|
const { join } = await import("path");
|
|
32287
32519
|
const home = process.env.HOME ?? "";
|
|
32288
32520
|
const configPath = join(home, ".exe-os", "gateway.json");
|
|
32289
32521
|
if (existsSync41(configPath)) {
|
|
32290
|
-
const raw = JSON.parse(
|
|
32522
|
+
const raw = JSON.parse(readFileSync37(configPath, "utf8"));
|
|
32291
32523
|
state.port = raw.port ?? 3100;
|
|
32292
32524
|
state.gatewayUrl = raw.gatewayUrl ?? "";
|
|
32293
32525
|
if (raw.adapters) {
|
|
@@ -32885,12 +33117,12 @@ function TeamView({ onBack, onViewSessions }) {
|
|
|
32885
33117
|
setMembers(teamData);
|
|
32886
33118
|
setDbError(null);
|
|
32887
33119
|
try {
|
|
32888
|
-
const { existsSync: existsSync41, readFileSync:
|
|
33120
|
+
const { existsSync: existsSync41, readFileSync: readFileSync37 } = await import("fs");
|
|
32889
33121
|
const { join } = await import("path");
|
|
32890
33122
|
const home = process.env.HOME ?? "";
|
|
32891
33123
|
const gatewayConfig = join(home, ".exe-os", "gateway.json");
|
|
32892
33124
|
if (existsSync41(gatewayConfig)) {
|
|
32893
|
-
const raw = JSON.parse(
|
|
33125
|
+
const raw = JSON.parse(readFileSync37(gatewayConfig, "utf8"));
|
|
32894
33126
|
if (raw.agents && raw.agents.length > 0) {
|
|
32895
33127
|
setExternals(raw.agents.map((a) => ({
|
|
32896
33128
|
name: a.name,
|
|
@@ -33070,8 +33302,8 @@ __export(wiki_client_exports, {
|
|
|
33070
33302
|
listDocuments: () => listDocuments,
|
|
33071
33303
|
listWorkspaces: () => listWorkspaces
|
|
33072
33304
|
});
|
|
33073
|
-
async function wikiFetch(config,
|
|
33074
|
-
const url = `${config.baseUrl}/api/v1${
|
|
33305
|
+
async function wikiFetch(config, path56, method = "GET", body) {
|
|
33306
|
+
const url = `${config.baseUrl}/api/v1${path56}`;
|
|
33075
33307
|
const headers = {
|
|
33076
33308
|
Authorization: `Bearer ${config.apiKey}`,
|
|
33077
33309
|
"Content-Type": "application/json"
|
|
@@ -33104,7 +33336,7 @@ async function wikiFetch(config, path55, method = "GET", body) {
|
|
|
33104
33336
|
}
|
|
33105
33337
|
}
|
|
33106
33338
|
if (!response.ok) {
|
|
33107
|
-
throw new Error(`Wiki API ${method} ${
|
|
33339
|
+
throw new Error(`Wiki API ${method} ${path56}: ${response.status} ${response.statusText}`);
|
|
33108
33340
|
}
|
|
33109
33341
|
return response.json();
|
|
33110
33342
|
} finally {
|
|
@@ -33721,17 +33953,17 @@ function SettingsView({ onBack }) {
|
|
|
33721
33953
|
}
|
|
33722
33954
|
let version = "unknown";
|
|
33723
33955
|
try {
|
|
33724
|
-
const { readFileSync:
|
|
33956
|
+
const { readFileSync: readFileSync37 } = await import("fs");
|
|
33725
33957
|
const { createRequire: createRequire3 } = await import("module");
|
|
33726
33958
|
const require2 = createRequire3(import.meta.url);
|
|
33727
33959
|
const pkgPath = require2.resolve("@askexenow/exe-os/package.json");
|
|
33728
|
-
const pkg = JSON.parse(
|
|
33960
|
+
const pkg = JSON.parse(readFileSync37(pkgPath, "utf8"));
|
|
33729
33961
|
version = pkg.version;
|
|
33730
33962
|
} catch {
|
|
33731
33963
|
try {
|
|
33732
|
-
const { readFileSync:
|
|
33964
|
+
const { readFileSync: readFileSync37 } = await import("fs");
|
|
33733
33965
|
const { join: joinPath } = await import("path");
|
|
33734
|
-
const pkg = JSON.parse(
|
|
33966
|
+
const pkg = JSON.parse(readFileSync37(joinPath(process.cwd(), "package.json"), "utf8"));
|
|
33735
33967
|
version = pkg.version;
|
|
33736
33968
|
} catch {
|
|
33737
33969
|
}
|
|
@@ -34588,24 +34820,24 @@ __export(code_context_index_exports, {
|
|
|
34588
34820
|
traceCodeSymbol: () => traceCodeSymbol
|
|
34589
34821
|
});
|
|
34590
34822
|
import crypto14 from "crypto";
|
|
34591
|
-
import
|
|
34592
|
-
import { existsSync as existsSync36, mkdirSync as
|
|
34823
|
+
import path51 from "path";
|
|
34824
|
+
import { existsSync as existsSync36, mkdirSync as mkdirSync25, readFileSync as readFileSync32, readdirSync as readdirSync11, statSync as statSync7, writeFileSync as writeFileSync26 } from "fs";
|
|
34593
34825
|
import { spawnSync } from "child_process";
|
|
34594
34826
|
function normalizeProjectRoot(projectRoot) {
|
|
34595
|
-
return
|
|
34827
|
+
return path51.resolve(projectRoot || process.cwd());
|
|
34596
34828
|
}
|
|
34597
34829
|
function hashText(text) {
|
|
34598
34830
|
return crypto14.createHash("sha256").update(text).digest("hex");
|
|
34599
34831
|
}
|
|
34600
34832
|
function indexDir() {
|
|
34601
|
-
const dir =
|
|
34602
|
-
|
|
34833
|
+
const dir = path51.join(EXE_AI_DIR, "code-context");
|
|
34834
|
+
mkdirSync25(dir, { recursive: true });
|
|
34603
34835
|
return dir;
|
|
34604
34836
|
}
|
|
34605
34837
|
function getCodeContextIndexPath(projectRoot) {
|
|
34606
34838
|
const root = normalizeProjectRoot(projectRoot);
|
|
34607
34839
|
const rootHash = hashText(root).slice(0, 16);
|
|
34608
|
-
return
|
|
34840
|
+
return path51.join(indexDir(), `${rootHash}.json`);
|
|
34609
34841
|
}
|
|
34610
34842
|
function currentBranch(projectRoot) {
|
|
34611
34843
|
const result = spawnSync("git", ["branch", "--show-current"], { cwd: projectRoot, encoding: "utf8", timeout: 2e3 });
|
|
@@ -34618,8 +34850,8 @@ function shouldIgnore(relPath) {
|
|
|
34618
34850
|
}
|
|
34619
34851
|
function listRecursive(projectRoot, dir = projectRoot, out = []) {
|
|
34620
34852
|
for (const entry of readdirSync11(dir, { withFileTypes: true })) {
|
|
34621
|
-
const abs =
|
|
34622
|
-
const rel =
|
|
34853
|
+
const abs = path51.join(dir, entry.name);
|
|
34854
|
+
const rel = path51.relative(projectRoot, abs).replaceAll(path51.sep, "/");
|
|
34623
34855
|
if (shouldIgnore(rel)) continue;
|
|
34624
34856
|
if (entry.isDirectory()) listRecursive(projectRoot, abs, out);
|
|
34625
34857
|
else if (entry.isFile()) out.push(rel);
|
|
@@ -34635,7 +34867,7 @@ function listCodeFiles(projectRoot, maxFiles) {
|
|
|
34635
34867
|
const rg = spawnSync("rg", ["--files"], { cwd: projectRoot, encoding: "utf8", timeout: 5e3, maxBuffer: 1024 * 1024 * 16 });
|
|
34636
34868
|
files = rg.status === 0 && rg.stdout.trim() ? rg.stdout.split("\n").map((s) => s.trim()).filter(Boolean) : listRecursive(projectRoot);
|
|
34637
34869
|
}
|
|
34638
|
-
return files.map((file) => file.replaceAll(
|
|
34870
|
+
return files.map((file) => file.replaceAll(path51.sep, "/")).filter((file) => isChunkable(file) && !shouldIgnore(file)).slice(0, maxFiles).sort();
|
|
34639
34871
|
}
|
|
34640
34872
|
function parseImportPaths(importText) {
|
|
34641
34873
|
const paths = [];
|
|
@@ -34648,13 +34880,13 @@ function parseImportPaths(importText) {
|
|
|
34648
34880
|
}
|
|
34649
34881
|
function resolveImport(fromFile, importPath, allFiles) {
|
|
34650
34882
|
if (!importPath.startsWith(".")) return null;
|
|
34651
|
-
const base =
|
|
34883
|
+
const base = path51.posix.normalize(path51.posix.join(path51.posix.dirname(fromFile.replaceAll(path51.sep, "/")), importPath));
|
|
34652
34884
|
const withoutKnownExt = base.replace(/\.(?:[a-z0-9]+)$/i, "");
|
|
34653
34885
|
const candidates = [base];
|
|
34654
34886
|
for (const ext of ["ts", "tsx", "js", "jsx", "py", "rs", "go", "java", "cs", "cpp", "c", "rb", "php", "swift", "kt", "scala", "sql", "md", "json", "yaml", "yml"]) {
|
|
34655
34887
|
candidates.push(`${withoutKnownExt}.${ext}`, `${base}.${ext}`);
|
|
34656
34888
|
}
|
|
34657
|
-
for (const indexName of ["index.ts", "index.tsx", "index.js", "mod.rs", "__init__.py"]) candidates.push(
|
|
34889
|
+
for (const indexName of ["index.ts", "index.tsx", "index.js", "mod.rs", "__init__.py"]) candidates.push(path51.posix.join(base, indexName));
|
|
34658
34890
|
return candidates.find((candidate) => allFiles.has(candidate)) ?? null;
|
|
34659
34891
|
}
|
|
34660
34892
|
function symbolId(filePath, chunk) {
|
|
@@ -34664,7 +34896,7 @@ function loadIndex(projectRoot) {
|
|
|
34664
34896
|
const file = getCodeContextIndexPath(projectRoot);
|
|
34665
34897
|
if (!existsSync36(file)) return null;
|
|
34666
34898
|
try {
|
|
34667
|
-
const parsed = JSON.parse(
|
|
34899
|
+
const parsed = JSON.parse(readFileSync32(file, "utf8"));
|
|
34668
34900
|
if (parsed.version !== INDEX_VERSION || parsed.projectRoot !== projectRoot) return null;
|
|
34669
34901
|
return parsed;
|
|
34670
34902
|
} catch {
|
|
@@ -34672,10 +34904,10 @@ function loadIndex(projectRoot) {
|
|
|
34672
34904
|
}
|
|
34673
34905
|
}
|
|
34674
34906
|
function saveIndex(index) {
|
|
34675
|
-
|
|
34907
|
+
writeFileSync26(getCodeContextIndexPath(index.projectRoot), JSON.stringify(index, null, 2));
|
|
34676
34908
|
}
|
|
34677
34909
|
function buildFileRecord(projectRoot, relPath, allFiles, previous) {
|
|
34678
|
-
const absPath =
|
|
34910
|
+
const absPath = path51.join(projectRoot, relPath);
|
|
34679
34911
|
let stat2;
|
|
34680
34912
|
try {
|
|
34681
34913
|
stat2 = statSync7(absPath);
|
|
@@ -34685,7 +34917,7 @@ function buildFileRecord(projectRoot, relPath, allFiles, previous) {
|
|
|
34685
34917
|
if (!stat2.isFile()) return { record: null, reused: false };
|
|
34686
34918
|
const language = languageForFile(relPath);
|
|
34687
34919
|
if (!language || !isChunkable(relPath)) return { record: null, reused: false };
|
|
34688
|
-
const source =
|
|
34920
|
+
const source = readFileSync32(absPath, "utf8");
|
|
34689
34921
|
const hash = hashText(source);
|
|
34690
34922
|
if (previous && previous.hash === hash && previous.mtimeMs === stat2.mtimeMs && previous.size === stat2.size && previous.language === language) {
|
|
34691
34923
|
return { record: previous, reused: true };
|
|
@@ -34713,13 +34945,13 @@ function buildCodeContextIndex(options = {}) {
|
|
|
34713
34945
|
const branch = currentBranch(projectRoot);
|
|
34714
34946
|
const previous = options.force ? null : loadIndex(projectRoot);
|
|
34715
34947
|
const files = listCodeFiles(projectRoot, maxFiles);
|
|
34716
|
-
const allFiles = new Set(files.map((file) => file.replaceAll(
|
|
34948
|
+
const allFiles = new Set(files.map((file) => file.replaceAll(path51.sep, "/")));
|
|
34717
34949
|
const fileRecords = {};
|
|
34718
34950
|
let rebuiltFiles = 0;
|
|
34719
34951
|
let reusedFiles = 0;
|
|
34720
34952
|
let skippedFiles = 0;
|
|
34721
34953
|
for (const rel of files) {
|
|
34722
|
-
const normalized = rel.replaceAll(
|
|
34954
|
+
const normalized = rel.replaceAll(path51.sep, "/");
|
|
34723
34955
|
const { record, reused } = buildFileRecord(projectRoot, normalized, allFiles, previous?.files[normalized]);
|
|
34724
34956
|
if (record) {
|
|
34725
34957
|
fileRecords[normalized] = record;
|
|
@@ -34748,11 +34980,11 @@ function loadOrBuildCodeContextIndex(options = {}) {
|
|
|
34748
34980
|
if (loaded) {
|
|
34749
34981
|
const currentFiles = listCodeFiles(projectRoot, options.maxFiles ?? DEFAULT_MAX_FILES);
|
|
34750
34982
|
const unchanged = currentFiles.every((rel) => {
|
|
34751
|
-
const normalized = rel.replaceAll(
|
|
34983
|
+
const normalized = rel.replaceAll(path51.sep, "/");
|
|
34752
34984
|
const existing = loaded.files[normalized];
|
|
34753
34985
|
if (!existing) return false;
|
|
34754
34986
|
try {
|
|
34755
|
-
const stat2 = statSync7(
|
|
34987
|
+
const stat2 = statSync7(path51.join(projectRoot, normalized));
|
|
34756
34988
|
return stat2.mtimeMs === existing.mtimeMs && stat2.size === existing.size;
|
|
34757
34989
|
} catch {
|
|
34758
34990
|
return false;
|
|
@@ -34805,9 +35037,9 @@ function globToRegex(pattern) {
|
|
|
34805
35037
|
}
|
|
34806
35038
|
function matchesPath(filePath, patterns) {
|
|
34807
35039
|
if (!patterns || patterns.length === 0) return true;
|
|
34808
|
-
const normalized = filePath.replaceAll(
|
|
35040
|
+
const normalized = filePath.replaceAll(path51.sep, "/");
|
|
34809
35041
|
return patterns.some((pattern) => {
|
|
34810
|
-
const p = pattern.replaceAll(
|
|
35042
|
+
const p = pattern.replaceAll(path51.sep, "/").replace(/^\.\//, "");
|
|
34811
35043
|
return normalized === p || normalized.startsWith(`${p}/`) || normalized.endsWith(p) || globToRegex(p).test(normalized);
|
|
34812
35044
|
});
|
|
34813
35045
|
}
|
|
@@ -34925,7 +35157,7 @@ function traceCodeSymbol(symbolName, options = {}) {
|
|
|
34925
35157
|
}
|
|
34926
35158
|
function resolveTargetFile(index, input) {
|
|
34927
35159
|
if (input.filePath) {
|
|
34928
|
-
const normalized = input.filePath.replaceAll(
|
|
35160
|
+
const normalized = input.filePath.replaceAll(path51.sep, "/").replace(/^\.\//, "");
|
|
34929
35161
|
if (index.files[normalized]) return { filePath: normalized, target: normalized };
|
|
34930
35162
|
const suffix = Object.keys(index.files).find((file) => file.endsWith(normalized));
|
|
34931
35163
|
if (suffix) return { filePath: suffix, target: input.filePath };
|
|
@@ -34955,7 +35187,7 @@ function analyzeBlastRadius(input) {
|
|
|
34955
35187
|
}
|
|
34956
35188
|
}
|
|
34957
35189
|
}
|
|
34958
|
-
const targetBase =
|
|
35190
|
+
const targetBase = path51.basename(target.filePath).replace(/\.[^.]+$/, "").toLowerCase();
|
|
34959
35191
|
const symbolLower = input.symbol?.toLowerCase();
|
|
34960
35192
|
const tests = Object.keys(index.files).filter((file) => {
|
|
34961
35193
|
const lower = file.toLowerCase();
|
|
@@ -35188,13 +35420,13 @@ __export(installer_exports2, {
|
|
|
35188
35420
|
verifyOpenCodeHooks: () => verifyOpenCodeHooks
|
|
35189
35421
|
});
|
|
35190
35422
|
import { readFile as readFile7, writeFile as writeFile8, mkdir as mkdir8 } from "fs/promises";
|
|
35191
|
-
import { existsSync as existsSync37, readFileSync as
|
|
35192
|
-
import
|
|
35423
|
+
import { existsSync as existsSync37, readFileSync as readFileSync33 } from "fs";
|
|
35424
|
+
import path52 from "path";
|
|
35193
35425
|
import os22 from "os";
|
|
35194
35426
|
async function registerOpenCodeMcp(packageRoot, homeDir = os22.homedir()) {
|
|
35195
35427
|
void packageRoot;
|
|
35196
|
-
const configDir =
|
|
35197
|
-
const configPath =
|
|
35428
|
+
const configDir = path52.join(homeDir, ".config", "opencode");
|
|
35429
|
+
const configPath = path52.join(configDir, "opencode.json");
|
|
35198
35430
|
await mkdir8(configDir, { recursive: true });
|
|
35199
35431
|
let config = {};
|
|
35200
35432
|
if (existsSync37(configPath)) {
|
|
@@ -35225,8 +35457,8 @@ async function registerOpenCodeMcp(packageRoot, homeDir = os22.homedir()) {
|
|
|
35225
35457
|
return true;
|
|
35226
35458
|
}
|
|
35227
35459
|
async function installOpenCodePlugin(packageRoot, homeDir = os22.homedir()) {
|
|
35228
|
-
const pluginDir =
|
|
35229
|
-
const pluginPath =
|
|
35460
|
+
const pluginDir = path52.join(homeDir, ".config", "opencode", "plugins");
|
|
35461
|
+
const pluginPath = path52.join(pluginDir, "exe-os.mjs");
|
|
35230
35462
|
await mkdir8(pluginDir, { recursive: true });
|
|
35231
35463
|
const pluginContent = PLUGIN_TEMPLATE.replace(
|
|
35232
35464
|
/__PACKAGE_ROOT__/g,
|
|
@@ -35242,18 +35474,18 @@ async function installOpenCodePlugin(packageRoot, homeDir = os22.homedir()) {
|
|
|
35242
35474
|
return true;
|
|
35243
35475
|
}
|
|
35244
35476
|
function verifyOpenCodeHooks(homeDir = os22.homedir()) {
|
|
35245
|
-
const configPath =
|
|
35246
|
-
const pluginPath =
|
|
35477
|
+
const configPath = path52.join(homeDir, ".config", "opencode", "opencode.json");
|
|
35478
|
+
const pluginPath = path52.join(homeDir, ".config", "opencode", "plugins", "exe-os.mjs");
|
|
35247
35479
|
if (!existsSync37(configPath)) return false;
|
|
35248
35480
|
try {
|
|
35249
|
-
const config = JSON.parse(
|
|
35481
|
+
const config = JSON.parse(readFileSync33(configPath, "utf-8"));
|
|
35250
35482
|
if (!config.mcp?.["exe-os"]?.enabled) return false;
|
|
35251
35483
|
} catch {
|
|
35252
35484
|
return false;
|
|
35253
35485
|
}
|
|
35254
35486
|
if (!existsSync37(pluginPath)) return false;
|
|
35255
35487
|
try {
|
|
35256
|
-
const plugin =
|
|
35488
|
+
const plugin = readFileSync33(pluginPath, "utf-8");
|
|
35257
35489
|
if (!plugin.includes(EXE_HOOK_FILES.postToolCombined)) return false;
|
|
35258
35490
|
if (textHasLegacySplitPostToolHook(plugin)) return false;
|
|
35259
35491
|
} catch {
|
|
@@ -35295,14 +35527,14 @@ __export(installer_exports3, {
|
|
|
35295
35527
|
verifyCodexHooks: () => verifyCodexHooks
|
|
35296
35528
|
});
|
|
35297
35529
|
import { readFile as readFile8, writeFile as writeFile9, mkdir as mkdir9 } from "fs/promises";
|
|
35298
|
-
import { existsSync as existsSync38, readFileSync as
|
|
35299
|
-
import
|
|
35530
|
+
import { existsSync as existsSync38, readFileSync as readFileSync34 } from "fs";
|
|
35531
|
+
import path53 from "path";
|
|
35300
35532
|
import os23 from "os";
|
|
35301
35533
|
async function mergeCodexHooks(packageRoot, homeDir = os23.homedir()) {
|
|
35302
|
-
const codexDir =
|
|
35303
|
-
const hooksPath =
|
|
35304
|
-
const logsDir =
|
|
35305
|
-
const hookLogPath =
|
|
35534
|
+
const codexDir = path53.join(homeDir, ".codex");
|
|
35535
|
+
const hooksPath = path53.join(codexDir, "hooks.json");
|
|
35536
|
+
const logsDir = path53.join(homeDir, ".exe-os", "logs");
|
|
35537
|
+
const hookLogPath = path53.join(logsDir, "hooks.log");
|
|
35306
35538
|
const logSuffix = ` 2>> "${hookLogPath}"`;
|
|
35307
35539
|
await mkdir9(codexDir, { recursive: true });
|
|
35308
35540
|
await mkdir9(logsDir, { recursive: true });
|
|
@@ -35327,7 +35559,7 @@ async function mergeCodexHooks(packageRoot, homeDir = os23.homedir()) {
|
|
|
35327
35559
|
// Combined hook: runs ingest + error-recall in one Node process.
|
|
35328
35560
|
// Eliminates a cold-start cycle per tool call (~3-6s savings on Codex).
|
|
35329
35561
|
type: "command",
|
|
35330
|
-
command: `node "${
|
|
35562
|
+
command: `node "${path53.join(packageRoot, "dist", "hooks", "post-tool-combined.js")}"${logSuffix}`
|
|
35331
35563
|
}
|
|
35332
35564
|
]
|
|
35333
35565
|
},
|
|
@@ -35341,7 +35573,7 @@ async function mergeCodexHooks(packageRoot, homeDir = os23.homedir()) {
|
|
|
35341
35573
|
// Single hook: prompt-submit handles memory retrieval + entity boost.
|
|
35342
35574
|
// exe-heartbeat-hook is CC-specific (intercom) — omitted on Codex.
|
|
35343
35575
|
type: "command",
|
|
35344
|
-
command: `node "${
|
|
35576
|
+
command: `node "${path53.join(packageRoot, "dist", "hooks", "prompt-submit.js")}"${logSuffix}`
|
|
35345
35577
|
}
|
|
35346
35578
|
]
|
|
35347
35579
|
},
|
|
@@ -35353,7 +35585,7 @@ async function mergeCodexHooks(packageRoot, homeDir = os23.homedir()) {
|
|
|
35353
35585
|
hooks: [
|
|
35354
35586
|
{
|
|
35355
35587
|
type: "command",
|
|
35356
|
-
command: `node "${
|
|
35588
|
+
command: `node "${path53.join(packageRoot, "dist", "hooks", "stop.js")}"${logSuffix}`
|
|
35357
35589
|
}
|
|
35358
35590
|
]
|
|
35359
35591
|
},
|
|
@@ -35366,7 +35598,7 @@ async function mergeCodexHooks(packageRoot, homeDir = os23.homedir()) {
|
|
|
35366
35598
|
hooks: [
|
|
35367
35599
|
{
|
|
35368
35600
|
type: "command",
|
|
35369
|
-
command: `node "${
|
|
35601
|
+
command: `node "${path53.join(packageRoot, "dist", "hooks", "pre-tool-use.js")}"${logSuffix}`
|
|
35370
35602
|
}
|
|
35371
35603
|
]
|
|
35372
35604
|
},
|
|
@@ -35415,10 +35647,10 @@ async function mergeCodexHooks(packageRoot, homeDir = os23.homedir()) {
|
|
|
35415
35647
|
return { added, skipped };
|
|
35416
35648
|
}
|
|
35417
35649
|
function verifyCodexHooks(homeDir = os23.homedir()) {
|
|
35418
|
-
const hooksPath =
|
|
35650
|
+
const hooksPath = path53.join(homeDir, ".codex", "hooks.json");
|
|
35419
35651
|
if (!existsSync38(hooksPath)) return false;
|
|
35420
35652
|
try {
|
|
35421
|
-
const hooksJson = JSON.parse(
|
|
35653
|
+
const hooksJson = JSON.parse(readFileSync34(hooksPath, "utf-8"));
|
|
35422
35654
|
if (!hooksJson.hooks) return false;
|
|
35423
35655
|
const required = ["PostToolUse", "UserPromptSubmit", "Stop", "PreToolUse"];
|
|
35424
35656
|
for (const event of required) {
|
|
@@ -35450,8 +35682,8 @@ function verifyCodexHooks(homeDir = os23.homedir()) {
|
|
|
35450
35682
|
async function installCodexStatusLine(homeDir = os23.homedir()) {
|
|
35451
35683
|
const prefs = loadPreferences(homeDir);
|
|
35452
35684
|
if (prefs.codexStatusLine === false) return "opted-out";
|
|
35453
|
-
const codexDir =
|
|
35454
|
-
const configPath =
|
|
35685
|
+
const codexDir = path53.join(homeDir, ".codex");
|
|
35686
|
+
const configPath = path53.join(codexDir, "config.toml");
|
|
35455
35687
|
await mkdir9(codexDir, { recursive: true });
|
|
35456
35688
|
let content = "";
|
|
35457
35689
|
if (existsSync38(configPath)) {
|
|
@@ -35506,8 +35738,8 @@ ${line}
|
|
|
35506
35738
|
return { content: next, changed: next !== sectionContent };
|
|
35507
35739
|
}
|
|
35508
35740
|
async function registerCodexMcpServer(packageRoot, homeDir = os23.homedir()) {
|
|
35509
|
-
const codexDir =
|
|
35510
|
-
const configPath =
|
|
35741
|
+
const codexDir = path53.join(homeDir, ".codex");
|
|
35742
|
+
const configPath = path53.join(codexDir, "config.toml");
|
|
35511
35743
|
void packageRoot;
|
|
35512
35744
|
await mkdir9(codexDir, { recursive: true });
|
|
35513
35745
|
let content = "";
|
|
@@ -35536,8 +35768,8 @@ async function registerCodexMcpServer(packageRoot, homeDir = os23.homedir()) {
|
|
|
35536
35768
|
return "registered";
|
|
35537
35769
|
}
|
|
35538
35770
|
async function ensureCodexHooksFeature(homeDir = os23.homedir()) {
|
|
35539
|
-
const configPath =
|
|
35540
|
-
await mkdir9(
|
|
35771
|
+
const configPath = path53.join(homeDir, ".codex", "config.toml");
|
|
35772
|
+
await mkdir9(path53.join(homeDir, ".codex"), { recursive: true });
|
|
35541
35773
|
let content = "";
|
|
35542
35774
|
if (existsSync38(configPath)) {
|
|
35543
35775
|
content = await readFile8(configPath, "utf-8");
|
|
@@ -35614,32 +35846,32 @@ __export(mcp_diagnostics_exports, {
|
|
|
35614
35846
|
diagnoseClaudeMcpConfig: () => diagnoseClaudeMcpConfig,
|
|
35615
35847
|
formatMcpDiagnosticReport: () => formatMcpDiagnosticReport
|
|
35616
35848
|
});
|
|
35617
|
-
import { existsSync as existsSync39, readFileSync as
|
|
35618
|
-
import
|
|
35849
|
+
import { existsSync as existsSync39, readFileSync as readFileSync35 } from "fs";
|
|
35850
|
+
import path54 from "path";
|
|
35619
35851
|
import os24 from "os";
|
|
35620
35852
|
function readJson(filePath) {
|
|
35621
35853
|
if (!existsSync39(filePath)) return null;
|
|
35622
35854
|
try {
|
|
35623
|
-
return JSON.parse(
|
|
35855
|
+
return JSON.parse(readFileSync35(filePath, "utf8"));
|
|
35624
35856
|
} catch {
|
|
35625
35857
|
return null;
|
|
35626
35858
|
}
|
|
35627
35859
|
}
|
|
35628
35860
|
function pathApplies2(projectPath, cwd2) {
|
|
35629
|
-
const project =
|
|
35630
|
-
const current =
|
|
35631
|
-
return current === project || current.startsWith(project +
|
|
35861
|
+
const project = path54.resolve(projectPath);
|
|
35862
|
+
const current = path54.resolve(cwd2);
|
|
35863
|
+
return current === project || current.startsWith(project + path54.sep);
|
|
35632
35864
|
}
|
|
35633
35865
|
function findAncestorMcpJsons2(cwd2, homeDir) {
|
|
35634
35866
|
const files = [];
|
|
35635
|
-
let dir =
|
|
35636
|
-
const root =
|
|
35637
|
-
const stop =
|
|
35867
|
+
let dir = path54.resolve(cwd2);
|
|
35868
|
+
const root = path54.parse(dir).root;
|
|
35869
|
+
const stop = path54.resolve(homeDir);
|
|
35638
35870
|
while (dir !== root) {
|
|
35639
|
-
const candidate =
|
|
35871
|
+
const candidate = path54.join(dir, ".mcp.json");
|
|
35640
35872
|
if (existsSync39(candidate)) files.push(candidate);
|
|
35641
35873
|
if (dir === stop) break;
|
|
35642
|
-
dir =
|
|
35874
|
+
dir = path54.dirname(dir);
|
|
35643
35875
|
}
|
|
35644
35876
|
return files;
|
|
35645
35877
|
}
|
|
@@ -35656,8 +35888,8 @@ function serverAllowedByPermissions(serverName, prefixes) {
|
|
|
35656
35888
|
return prefixes.has(serverName) || prefixes.has(serverName.replace(/-/g, "_"));
|
|
35657
35889
|
}
|
|
35658
35890
|
function diagnoseClaudeMcpConfig(homeDir = os24.homedir(), cwd2 = process.cwd(), env = process.env) {
|
|
35659
|
-
const claudeJsonPath =
|
|
35660
|
-
const settingsPath =
|
|
35891
|
+
const claudeJsonPath = path54.join(homeDir, ".claude.json");
|
|
35892
|
+
const settingsPath = path54.join(homeDir, ".claude", "settings.json");
|
|
35661
35893
|
const claudeJson = readJson(claudeJsonPath);
|
|
35662
35894
|
const settings = readJson(settingsPath);
|
|
35663
35895
|
const issues = [];
|
|
@@ -35777,7 +36009,7 @@ function diagnoseClaudeMcpConfig(homeDir = os24.homedir(), cwd2 = process.cwd(),
|
|
|
35777
36009
|
});
|
|
35778
36010
|
}
|
|
35779
36011
|
return {
|
|
35780
|
-
cwd:
|
|
36012
|
+
cwd: path54.resolve(cwd2),
|
|
35781
36013
|
globalServers,
|
|
35782
36014
|
projectServers: projectServers.sort((a, b) => a.name.localeCompare(b.name)),
|
|
35783
36015
|
mcpJsonServers: mcpJsonServers.sort((a, b) => a.name.localeCompare(b.name)),
|
|
@@ -35814,14 +36046,14 @@ var init_mcp_diagnostics = __esm({
|
|
|
35814
36046
|
});
|
|
35815
36047
|
|
|
35816
36048
|
// src/bin/cli.ts
|
|
35817
|
-
import { existsSync as existsSync40, readFileSync as
|
|
35818
|
-
import
|
|
36049
|
+
import { existsSync as existsSync40, readFileSync as readFileSync36, writeFileSync as writeFileSync27, readdirSync as readdirSync12, rmSync as rmSync2 } from "fs";
|
|
36050
|
+
import path55 from "path";
|
|
35819
36051
|
import os25 from "os";
|
|
35820
36052
|
var args = process.argv.slice(2);
|
|
35821
36053
|
if (args.includes("--version") || args.includes("-v")) {
|
|
35822
36054
|
try {
|
|
35823
|
-
const pkgPath =
|
|
35824
|
-
const pkg = JSON.parse(
|
|
36055
|
+
const pkgPath = path55.join(path55.dirname(new URL(import.meta.url).pathname), "..", "..", "package.json");
|
|
36056
|
+
const pkg = JSON.parse(readFileSync36(pkgPath, "utf8"));
|
|
35825
36057
|
console.log(pkg.version);
|
|
35826
36058
|
} catch {
|
|
35827
36059
|
console.log("unknown");
|
|
@@ -35943,6 +36175,9 @@ if (args.includes("--global")) {
|
|
|
35943
36175
|
const { main: runCloud } = await Promise.resolve().then(() => (init_exe_cloud(), exe_cloud_exports));
|
|
35944
36176
|
await runCloud();
|
|
35945
36177
|
}
|
|
36178
|
+
} else if (args[0] === "support") {
|
|
36179
|
+
const { main: runSupport } = await Promise.resolve().then(() => (init_exe_support(), exe_support_exports));
|
|
36180
|
+
await runSupport(args.slice(1));
|
|
35946
36181
|
} else if (args[0] === "bulk-sync-postgres") {
|
|
35947
36182
|
const { main: runBulkSyncPostgres } = await Promise.resolve().then(() => (init_bulk_sync_postgres(), bulk_sync_postgres_exports));
|
|
35948
36183
|
await runBulkSyncPostgres();
|
|
@@ -36046,11 +36281,11 @@ ID: ${result.id}`);
|
|
|
36046
36281
|
});
|
|
36047
36282
|
await init_App2().then(() => App_exports);
|
|
36048
36283
|
} else {
|
|
36049
|
-
const claudeDir =
|
|
36050
|
-
const settingsPath =
|
|
36284
|
+
const claudeDir = path55.join(os25.homedir(), ".claude");
|
|
36285
|
+
const settingsPath = path55.join(claudeDir, "settings.json");
|
|
36051
36286
|
const hasClaudeCode = existsSync40(settingsPath) && (() => {
|
|
36052
36287
|
try {
|
|
36053
|
-
const raw =
|
|
36288
|
+
const raw = readFileSync36(settingsPath, "utf8");
|
|
36054
36289
|
return raw.includes("exe-os") || raw.includes("exe-mem");
|
|
36055
36290
|
} catch {
|
|
36056
36291
|
return false;
|
|
@@ -36060,9 +36295,9 @@ ID: ${result.id}`);
|
|
|
36060
36295
|
const { DEFAULT_COORDINATOR_TEMPLATE_NAME: DEFAULT_COORDINATOR_TEMPLATE_NAME2 } = await Promise.resolve().then(() => (init_employees(), employees_exports));
|
|
36061
36296
|
let cooName = DEFAULT_COORDINATOR_TEMPLATE_NAME2;
|
|
36062
36297
|
try {
|
|
36063
|
-
const rosterPath =
|
|
36298
|
+
const rosterPath = path55.join(os25.homedir(), ".exe-os", "exe-employees.json");
|
|
36064
36299
|
if (existsSync40(rosterPath)) {
|
|
36065
|
-
const roster = JSON.parse(
|
|
36300
|
+
const roster = JSON.parse(readFileSync36(rosterPath, "utf8"));
|
|
36066
36301
|
const coo = roster.find((e) => e.role === "COO");
|
|
36067
36302
|
if (coo) cooName = coo.name;
|
|
36068
36303
|
}
|
|
@@ -36215,14 +36450,14 @@ async function runCodexInstall() {
|
|
|
36215
36450
|
}
|
|
36216
36451
|
async function runClaudeCheck() {
|
|
36217
36452
|
const { detectMcpNameCollisions: detectMcpNameCollisions2 } = await Promise.resolve().then(() => (init_installer(), installer_exports));
|
|
36218
|
-
const claudeDir =
|
|
36219
|
-
const settingsPath =
|
|
36220
|
-
const claudeJsonPath =
|
|
36453
|
+
const claudeDir = path55.join(os25.homedir(), ".claude");
|
|
36454
|
+
const settingsPath = path55.join(claudeDir, "settings.json");
|
|
36455
|
+
const claudeJsonPath = path55.join(os25.homedir(), ".claude.json");
|
|
36221
36456
|
let ok = true;
|
|
36222
36457
|
if (existsSync40(settingsPath)) {
|
|
36223
36458
|
let settings;
|
|
36224
36459
|
try {
|
|
36225
|
-
settings = JSON.parse(
|
|
36460
|
+
settings = JSON.parse(readFileSync36(settingsPath, "utf8"));
|
|
36226
36461
|
} catch {
|
|
36227
36462
|
console.log("\x1B[31m\u2717\x1B[0m settings.json is malformed (invalid JSON)");
|
|
36228
36463
|
ok = false;
|
|
@@ -36251,7 +36486,7 @@ async function runClaudeCheck() {
|
|
|
36251
36486
|
if (existsSync40(claudeJsonPath)) {
|
|
36252
36487
|
let claudeJson;
|
|
36253
36488
|
try {
|
|
36254
|
-
claudeJson = JSON.parse(
|
|
36489
|
+
claudeJson = JSON.parse(readFileSync36(claudeJsonPath, "utf8"));
|
|
36255
36490
|
} catch {
|
|
36256
36491
|
console.log("\x1B[31m\u2717\x1B[0m claude.json is malformed (invalid JSON)");
|
|
36257
36492
|
ok = false;
|
|
@@ -36284,7 +36519,7 @@ async function runClaudeCheck() {
|
|
|
36284
36519
|
} else {
|
|
36285
36520
|
console.log("\x1B[32m\u2713\x1B[0m No .mcp.json/project MCP name collisions detected");
|
|
36286
36521
|
}
|
|
36287
|
-
const skillsDir =
|
|
36522
|
+
const skillsDir = path55.join(claudeDir, "skills");
|
|
36288
36523
|
if (existsSync40(skillsDir)) {
|
|
36289
36524
|
console.log("\x1B[32m\u2713\x1B[0m Slash skills directory exists");
|
|
36290
36525
|
} else {
|
|
@@ -36309,16 +36544,16 @@ async function runClaudeUninstall(flags = []) {
|
|
|
36309
36544
|
const dryRun = flags.includes("--dry-run");
|
|
36310
36545
|
const purge = flags.includes("--purge");
|
|
36311
36546
|
const homeDir = os25.homedir();
|
|
36312
|
-
const claudeDir =
|
|
36313
|
-
const settingsPath =
|
|
36314
|
-
const claudeJsonPath =
|
|
36315
|
-
const exeOsDir =
|
|
36547
|
+
const claudeDir = path55.join(homeDir, ".claude");
|
|
36548
|
+
const settingsPath = path55.join(claudeDir, "settings.json");
|
|
36549
|
+
const claudeJsonPath = path55.join(homeDir, ".claude.json");
|
|
36550
|
+
const exeOsDir = path55.join(homeDir, ".exe-os");
|
|
36316
36551
|
let removed = 0;
|
|
36317
36552
|
const log = (msg) => console.log(dryRun ? `[dry-run] ${msg}` : msg);
|
|
36318
36553
|
let settings = {};
|
|
36319
36554
|
if (existsSync40(settingsPath)) {
|
|
36320
36555
|
try {
|
|
36321
|
-
settings = JSON.parse(
|
|
36556
|
+
settings = JSON.parse(readFileSync36(settingsPath, "utf8"));
|
|
36322
36557
|
} catch {
|
|
36323
36558
|
console.error("Your ~/.claude/settings.json appears malformed.");
|
|
36324
36559
|
if (purge) {
|
|
@@ -36356,7 +36591,7 @@ async function runClaudeUninstall(flags = []) {
|
|
|
36356
36591
|
permCount = before - settings.permissions.allow.length;
|
|
36357
36592
|
}
|
|
36358
36593
|
if (!dryRun) {
|
|
36359
|
-
|
|
36594
|
+
writeFileSync27(settingsPath, JSON.stringify(settings, null, 2) + "\n");
|
|
36360
36595
|
}
|
|
36361
36596
|
log("\u2713 Removed exe-os hooks from settings.json");
|
|
36362
36597
|
if (permCount > 0) log(`\u2713 Removed ${permCount} MCP permission entries`);
|
|
@@ -36364,7 +36599,7 @@ async function runClaudeUninstall(flags = []) {
|
|
|
36364
36599
|
}
|
|
36365
36600
|
}
|
|
36366
36601
|
if (existsSync40(claudeJsonPath)) {
|
|
36367
|
-
const raw =
|
|
36602
|
+
const raw = readFileSync36(claudeJsonPath, "utf8");
|
|
36368
36603
|
if (raw.length > 1e6) {
|
|
36369
36604
|
console.error("claude.json exceeds 1 MB \u2014 skipping parse.");
|
|
36370
36605
|
} else {
|
|
@@ -36385,7 +36620,7 @@ async function runClaudeUninstall(flags = []) {
|
|
|
36385
36620
|
}
|
|
36386
36621
|
if (removedMcp) {
|
|
36387
36622
|
if (!dryRun) {
|
|
36388
|
-
|
|
36623
|
+
writeFileSync27(claudeJsonPath, JSON.stringify(claudeJson, null, 2) + "\n");
|
|
36389
36624
|
}
|
|
36390
36625
|
log("\u2713 Removed exe-os MCP server from claude.json");
|
|
36391
36626
|
removed++;
|
|
@@ -36393,14 +36628,14 @@ async function runClaudeUninstall(flags = []) {
|
|
|
36393
36628
|
}
|
|
36394
36629
|
}
|
|
36395
36630
|
}
|
|
36396
|
-
const skillsDir =
|
|
36631
|
+
const skillsDir = path55.join(claudeDir, "skills");
|
|
36397
36632
|
if (existsSync40(skillsDir)) {
|
|
36398
36633
|
let skillCount = 0;
|
|
36399
36634
|
try {
|
|
36400
36635
|
const entries = readdirSync12(skillsDir);
|
|
36401
36636
|
for (const entry of entries) {
|
|
36402
36637
|
if (entry.startsWith("exe")) {
|
|
36403
|
-
const fullPath =
|
|
36638
|
+
const fullPath = path55.join(skillsDir, entry);
|
|
36404
36639
|
if (!dryRun) rmSync2(fullPath, { recursive: true, force: true });
|
|
36405
36640
|
skillCount++;
|
|
36406
36641
|
}
|
|
@@ -36412,30 +36647,30 @@ async function runClaudeUninstall(flags = []) {
|
|
|
36412
36647
|
removed++;
|
|
36413
36648
|
}
|
|
36414
36649
|
}
|
|
36415
|
-
const claudeMdPath =
|
|
36650
|
+
const claudeMdPath = path55.join(claudeDir, "CLAUDE.md");
|
|
36416
36651
|
if (existsSync40(claudeMdPath)) {
|
|
36417
|
-
const content =
|
|
36652
|
+
const content = readFileSync36(claudeMdPath, "utf8");
|
|
36418
36653
|
const startMarker = "<!-- exe-os:orchestration-start -->";
|
|
36419
36654
|
const endMarker = "<!-- exe-os:orchestration-end -->";
|
|
36420
36655
|
const startIdx = content.indexOf(startMarker);
|
|
36421
36656
|
const endIdx = content.indexOf(endMarker);
|
|
36422
36657
|
if (startIdx !== -1 && endIdx !== -1) {
|
|
36423
36658
|
const cleaned = (content.slice(0, startIdx) + content.slice(endIdx + endMarker.length)).replace(/\n{3,}/g, "\n\n").trim() + "\n";
|
|
36424
|
-
if (!dryRun)
|
|
36659
|
+
if (!dryRun) writeFileSync27(claudeMdPath, cleaned);
|
|
36425
36660
|
log("\u2713 Removed orchestration block from CLAUDE.md");
|
|
36426
36661
|
removed++;
|
|
36427
36662
|
}
|
|
36428
36663
|
}
|
|
36429
|
-
const agentsDir =
|
|
36664
|
+
const agentsDir = path55.join(claudeDir, "agents");
|
|
36430
36665
|
if (existsSync40(agentsDir)) {
|
|
36431
36666
|
let agentCount = 0;
|
|
36432
36667
|
try {
|
|
36433
36668
|
const entries = readdirSync12(agentsDir).filter((f) => f.endsWith(".md"));
|
|
36434
36669
|
let knownNames = /* @__PURE__ */ new Set();
|
|
36435
|
-
const rosterPath =
|
|
36670
|
+
const rosterPath = path55.join(exeOsDir, "exe-employees.json");
|
|
36436
36671
|
if (existsSync40(rosterPath)) {
|
|
36437
36672
|
try {
|
|
36438
|
-
const roster = JSON.parse(
|
|
36673
|
+
const roster = JSON.parse(readFileSync36(rosterPath, "utf8"));
|
|
36439
36674
|
knownNames = new Set(roster.map((e) => e.name));
|
|
36440
36675
|
} catch {
|
|
36441
36676
|
}
|
|
@@ -36443,7 +36678,7 @@ async function runClaudeUninstall(flags = []) {
|
|
|
36443
36678
|
for (const entry of entries) {
|
|
36444
36679
|
const name = entry.replace(/\.md$/, "");
|
|
36445
36680
|
if (knownNames.has(name)) {
|
|
36446
|
-
if (!dryRun) rmSync2(
|
|
36681
|
+
if (!dryRun) rmSync2(path55.join(agentsDir, entry), { force: true });
|
|
36447
36682
|
agentCount++;
|
|
36448
36683
|
}
|
|
36449
36684
|
}
|
|
@@ -36454,16 +36689,16 @@ async function runClaudeUninstall(flags = []) {
|
|
|
36454
36689
|
removed++;
|
|
36455
36690
|
}
|
|
36456
36691
|
}
|
|
36457
|
-
const projectsDir =
|
|
36692
|
+
const projectsDir = path55.join(claudeDir, "projects");
|
|
36458
36693
|
if (existsSync40(projectsDir)) {
|
|
36459
36694
|
let projectCount = 0;
|
|
36460
36695
|
try {
|
|
36461
36696
|
const projects = readdirSync12(projectsDir);
|
|
36462
36697
|
for (const proj of projects) {
|
|
36463
|
-
const projSettings =
|
|
36698
|
+
const projSettings = path55.join(projectsDir, proj, "settings.json");
|
|
36464
36699
|
if (!existsSync40(projSettings)) continue;
|
|
36465
36700
|
try {
|
|
36466
|
-
const pSettings = JSON.parse(
|
|
36701
|
+
const pSettings = JSON.parse(readFileSync36(projSettings, "utf8"));
|
|
36467
36702
|
let changed = false;
|
|
36468
36703
|
if (Array.isArray(pSettings.permissions?.allow)) {
|
|
36469
36704
|
const before = pSettings.permissions.allow.length;
|
|
@@ -36473,7 +36708,7 @@ async function runClaudeUninstall(flags = []) {
|
|
|
36473
36708
|
if (pSettings.permissions.allow.length < before) changed = true;
|
|
36474
36709
|
}
|
|
36475
36710
|
if (changed && !dryRun) {
|
|
36476
|
-
|
|
36711
|
+
writeFileSync27(projSettings, JSON.stringify(pSettings, null, 2) + "\n");
|
|
36477
36712
|
}
|
|
36478
36713
|
if (changed) projectCount++;
|
|
36479
36714
|
} catch {
|
|
@@ -36497,17 +36732,17 @@ async function runClaudeUninstall(flags = []) {
|
|
|
36497
36732
|
};
|
|
36498
36733
|
const exeBinPath = findExeBin3();
|
|
36499
36734
|
if (!exeBinPath) throw new Error("exe-os not found in PATH");
|
|
36500
|
-
const binDir =
|
|
36735
|
+
const binDir = path55.dirname(exeBinPath);
|
|
36501
36736
|
let symlinkCount = 0;
|
|
36502
|
-
const rosterPath =
|
|
36737
|
+
const rosterPath = path55.join(exeOsDir, "exe-employees.json");
|
|
36503
36738
|
if (existsSync40(rosterPath)) {
|
|
36504
|
-
const roster = JSON.parse(
|
|
36739
|
+
const roster = JSON.parse(readFileSync36(rosterPath, "utf8"));
|
|
36505
36740
|
const { DEFAULT_COORDINATOR_TEMPLATE_NAME: DEFAULT_COORDINATOR_TEMPLATE_NAME2 } = await Promise.resolve().then(() => (init_employees(), employees_exports));
|
|
36506
36741
|
const coordinatorName = roster.find((e) => e.role?.toLowerCase() === "coo")?.name ?? DEFAULT_COORDINATOR_TEMPLATE_NAME2;
|
|
36507
36742
|
for (const emp of roster) {
|
|
36508
36743
|
if (emp.name === coordinatorName) continue;
|
|
36509
36744
|
for (const suffix of ["", "-opencode"]) {
|
|
36510
|
-
const linkPath =
|
|
36745
|
+
const linkPath = path55.join(binDir, `${emp.name}${suffix}`);
|
|
36511
36746
|
if (existsSync40(linkPath)) {
|
|
36512
36747
|
if (!dryRun) rmSync2(linkPath, { force: true });
|
|
36513
36748
|
symlinkCount++;
|
|
@@ -36546,7 +36781,7 @@ async function checkForUpdateOnBoot() {
|
|
|
36546
36781
|
const config = await loadConfig2();
|
|
36547
36782
|
if (!config.autoUpdate.checkOnBoot) return;
|
|
36548
36783
|
const { checkForUpdate: checkForUpdate2 } = await Promise.resolve().then(() => (init_update(), update_exports));
|
|
36549
|
-
const packageRoot =
|
|
36784
|
+
const packageRoot = path55.resolve(
|
|
36550
36785
|
new URL("../..", import.meta.url).pathname
|
|
36551
36786
|
);
|
|
36552
36787
|
const result = checkForUpdate2(packageRoot);
|
|
@@ -36607,7 +36842,7 @@ async function runActivate(key) {
|
|
|
36607
36842
|
const idTemplate = getIdentityTemplate(identityKey);
|
|
36608
36843
|
if (idTemplate) {
|
|
36609
36844
|
const idPath = identityPath2(name);
|
|
36610
|
-
const dir =
|
|
36845
|
+
const dir = path55.dirname(idPath);
|
|
36611
36846
|
if (!fs8.existsSync(dir)) fs8.mkdirSync(dir, { recursive: true });
|
|
36612
36847
|
fs8.writeFileSync(idPath, idTemplate.replace(/^agent_id: \w+/m, `agent_id: ${name}`), "utf-8");
|
|
36613
36848
|
}
|