@adhdev/daemon-core 0.9.82-rc.66 → 0.9.82-rc.68
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/index.d.ts +1 -1
- package/dist/index.js +747 -591
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +748 -593
- package/dist/index.mjs.map +1 -1
- package/dist/installer.d.ts +1 -4
- package/dist/launch.d.ts +1 -1
- package/dist/logging/async-batch-writer.d.ts +10 -0
- package/dist/mesh/beads-db.d.ts +18 -0
- package/dist/mesh/mesh-work-queue.d.ts +4 -0
- package/dist/status/reporter.d.ts +2 -0
- package/package.json +3 -1
- package/src/cli-adapters/provider-cli-shared.ts +18 -10
- package/src/commands/mesh-coordinator.ts +13 -143
- package/src/commands/router.ts +5 -3
- package/src/detection/ide-detector.ts +26 -16
- package/src/index.ts +1 -1
- package/src/installer.d.ts +1 -1
- package/src/installer.ts +8 -6
- package/src/launch.d.ts +1 -1
- package/src/launch.ts +37 -28
- package/src/logging/async-batch-writer.ts +55 -0
- package/src/logging/logger.ts +2 -1
- package/src/mesh/beads-db.ts +163 -0
- package/src/mesh/mesh-ledger.ts +1 -1
- package/src/mesh/mesh-work-queue.ts +23 -41
- package/src/providers/ide-provider-instance.ts +17 -3
- package/src/providers/provider-loader.ts +10 -4
- package/src/providers/version-archive.ts +38 -20
- package/src/status/reporter.ts +15 -0
- package/src/system/host-memory.ts +29 -12
package/dist/index.js
CHANGED
|
@@ -1683,15 +1683,162 @@ var init_mesh_ledger = __esm({
|
|
|
1683
1683
|
}
|
|
1684
1684
|
});
|
|
1685
1685
|
|
|
1686
|
+
// src/mesh/beads-db.ts
|
|
1687
|
+
function safeMeshId(meshId) {
|
|
1688
|
+
return meshId.replace(/[^a-zA-Z0-9_-]/g, "_");
|
|
1689
|
+
}
|
|
1690
|
+
function legacyQueuePath(meshId) {
|
|
1691
|
+
return (0, import_path5.join)(getLedgerDir(), `${safeMeshId(meshId)}.queue.json`);
|
|
1692
|
+
}
|
|
1693
|
+
var import_better_sqlite3, import_fs5, import_path5, BeadsDB;
|
|
1694
|
+
var init_beads_db = __esm({
|
|
1695
|
+
"src/mesh/beads-db.ts"() {
|
|
1696
|
+
"use strict";
|
|
1697
|
+
import_better_sqlite3 = __toESM(require("better-sqlite3"));
|
|
1698
|
+
import_fs5 = require("fs");
|
|
1699
|
+
import_path5 = require("path");
|
|
1700
|
+
init_mesh_ledger();
|
|
1701
|
+
BeadsDB = class _BeadsDB {
|
|
1702
|
+
static instance;
|
|
1703
|
+
db;
|
|
1704
|
+
migratedMeshIds = /* @__PURE__ */ new Set();
|
|
1705
|
+
constructor(dbPath) {
|
|
1706
|
+
const dir = (0, import_path5.dirname)(dbPath);
|
|
1707
|
+
if (!(0, import_fs5.existsSync)(dir)) (0, import_fs5.mkdirSync)(dir, { recursive: true });
|
|
1708
|
+
this.db = new import_better_sqlite3.default(dbPath);
|
|
1709
|
+
this.db.pragma("journal_mode = WAL");
|
|
1710
|
+
this.db.pragma("synchronous = NORMAL");
|
|
1711
|
+
this.db.pragma("foreign_keys = ON");
|
|
1712
|
+
this.db.pragma("busy_timeout = 5000");
|
|
1713
|
+
this.migrate();
|
|
1714
|
+
}
|
|
1715
|
+
static getInstance() {
|
|
1716
|
+
if (!this.instance) {
|
|
1717
|
+
this.instance = new _BeadsDB((0, import_path5.join)(getLedgerDir(), "beads.db"));
|
|
1718
|
+
}
|
|
1719
|
+
return this.instance;
|
|
1720
|
+
}
|
|
1721
|
+
static resetForTests() {
|
|
1722
|
+
this.instance?.close();
|
|
1723
|
+
this.instance = void 0;
|
|
1724
|
+
}
|
|
1725
|
+
close() {
|
|
1726
|
+
this.db.close();
|
|
1727
|
+
}
|
|
1728
|
+
transaction(fn) {
|
|
1729
|
+
return this.db.transaction(fn).immediate();
|
|
1730
|
+
}
|
|
1731
|
+
migrate() {
|
|
1732
|
+
this.db.exec(`
|
|
1733
|
+
CREATE TABLE IF NOT EXISTS mesh_queue (
|
|
1734
|
+
id TEXT PRIMARY KEY,
|
|
1735
|
+
mesh_id TEXT NOT NULL,
|
|
1736
|
+
status TEXT NOT NULL,
|
|
1737
|
+
target_node_id TEXT,
|
|
1738
|
+
target_session_id TEXT,
|
|
1739
|
+
assigned_node_id TEXT,
|
|
1740
|
+
assigned_session_id TEXT,
|
|
1741
|
+
created_at TEXT NOT NULL,
|
|
1742
|
+
updated_at TEXT NOT NULL,
|
|
1743
|
+
payload TEXT NOT NULL
|
|
1744
|
+
);
|
|
1745
|
+
|
|
1746
|
+
CREATE INDEX IF NOT EXISTS idx_mesh_queue_mesh_status_created
|
|
1747
|
+
ON mesh_queue(mesh_id, status, created_at);
|
|
1748
|
+
CREATE INDEX IF NOT EXISTS idx_mesh_queue_assignment
|
|
1749
|
+
ON mesh_queue(mesh_id, assigned_node_id, assigned_session_id, status);
|
|
1750
|
+
`);
|
|
1751
|
+
}
|
|
1752
|
+
ensureLegacyQueueMigrated(meshId) {
|
|
1753
|
+
if (this.migratedMeshIds.has(meshId)) return;
|
|
1754
|
+
this.migratedMeshIds.add(meshId);
|
|
1755
|
+
const count = this.db.prepare("SELECT COUNT(*) AS count FROM mesh_queue WHERE mesh_id = ?").get(meshId);
|
|
1756
|
+
if (count.count > 0) return;
|
|
1757
|
+
const path28 = legacyQueuePath(meshId);
|
|
1758
|
+
if (!(0, import_fs5.existsSync)(path28)) return;
|
|
1759
|
+
try {
|
|
1760
|
+
const entries = JSON.parse((0, import_fs5.readFileSync)(path28, "utf-8"));
|
|
1761
|
+
if (!Array.isArray(entries)) return;
|
|
1762
|
+
const insert = this.db.prepare(`
|
|
1763
|
+
INSERT OR REPLACE INTO mesh_queue (
|
|
1764
|
+
id, mesh_id, status, target_node_id, target_session_id,
|
|
1765
|
+
assigned_node_id, assigned_session_id, created_at, updated_at, payload
|
|
1766
|
+
) VALUES (
|
|
1767
|
+
@id, @meshId, @status, @targetNodeId, @targetSessionId,
|
|
1768
|
+
@assignedNodeId, @assignedSessionId, @createdAt, @updatedAt, @payload
|
|
1769
|
+
)
|
|
1770
|
+
`);
|
|
1771
|
+
for (const entry of entries) {
|
|
1772
|
+
insert.run(this.toRow(entry));
|
|
1773
|
+
}
|
|
1774
|
+
} catch {
|
|
1775
|
+
return;
|
|
1776
|
+
}
|
|
1777
|
+
}
|
|
1778
|
+
getQueueEntries(meshId, statuses) {
|
|
1779
|
+
this.ensureLegacyQueueMigrated(meshId);
|
|
1780
|
+
if (statuses?.length) {
|
|
1781
|
+
const placeholders = statuses.map(() => "?").join(", ");
|
|
1782
|
+
const rows2 = this.db.prepare(`SELECT payload FROM mesh_queue WHERE mesh_id = ? AND status IN (${placeholders}) ORDER BY created_at ASC`).all(meshId, ...statuses);
|
|
1783
|
+
return rows2.map((row) => JSON.parse(row.payload));
|
|
1784
|
+
}
|
|
1785
|
+
const rows = this.db.prepare("SELECT payload FROM mesh_queue WHERE mesh_id = ? ORDER BY created_at ASC").all(meshId);
|
|
1786
|
+
return rows.map((row) => JSON.parse(row.payload));
|
|
1787
|
+
}
|
|
1788
|
+
getQueueRevision(meshId) {
|
|
1789
|
+
this.ensureLegacyQueueMigrated(meshId);
|
|
1790
|
+
const rows = this.db.prepare("SELECT id, status, updated_at FROM mesh_queue WHERE mesh_id = ? ORDER BY id ASC").all(meshId);
|
|
1791
|
+
return rows.map((row) => `${row.id}:${row.status}:${row.updated_at}`).join("|");
|
|
1792
|
+
}
|
|
1793
|
+
replaceQueue(meshId, queue) {
|
|
1794
|
+
const deleteStmt = this.db.prepare("DELETE FROM mesh_queue WHERE mesh_id = ?");
|
|
1795
|
+
const insert = this.db.prepare(`
|
|
1796
|
+
INSERT INTO mesh_queue (
|
|
1797
|
+
id, mesh_id, status, target_node_id, target_session_id,
|
|
1798
|
+
assigned_node_id, assigned_session_id, created_at, updated_at, payload
|
|
1799
|
+
) VALUES (
|
|
1800
|
+
@id, @meshId, @status, @targetNodeId, @targetSessionId,
|
|
1801
|
+
@assignedNodeId, @assignedSessionId, @createdAt, @updatedAt, @payload
|
|
1802
|
+
)
|
|
1803
|
+
`);
|
|
1804
|
+
deleteStmt.run(meshId);
|
|
1805
|
+
for (const entry of queue) insert.run(this.toRow(entry));
|
|
1806
|
+
}
|
|
1807
|
+
deleteQueue(meshId) {
|
|
1808
|
+
this.db.prepare("DELETE FROM mesh_queue WHERE mesh_id = ?").run(meshId);
|
|
1809
|
+
this.migratedMeshIds.delete(meshId);
|
|
1810
|
+
}
|
|
1811
|
+
toRow(entry) {
|
|
1812
|
+
return {
|
|
1813
|
+
id: entry.id,
|
|
1814
|
+
meshId: entry.meshId,
|
|
1815
|
+
status: entry.status,
|
|
1816
|
+
targetNodeId: entry.targetNodeId ?? null,
|
|
1817
|
+
targetSessionId: entry.targetSessionId ?? null,
|
|
1818
|
+
assignedNodeId: entry.assignedNodeId ?? null,
|
|
1819
|
+
assignedSessionId: entry.assignedSessionId ?? null,
|
|
1820
|
+
createdAt: entry.createdAt,
|
|
1821
|
+
updatedAt: entry.updatedAt,
|
|
1822
|
+
payload: JSON.stringify(entry)
|
|
1823
|
+
};
|
|
1824
|
+
}
|
|
1825
|
+
};
|
|
1826
|
+
}
|
|
1827
|
+
});
|
|
1828
|
+
|
|
1686
1829
|
// src/mesh/mesh-work-queue.ts
|
|
1687
1830
|
var mesh_work_queue_exports = {};
|
|
1688
1831
|
__export(mesh_work_queue_exports, {
|
|
1689
1832
|
ACTIVE_MESH_QUEUE_STATUSES: () => ACTIVE_MESH_QUEUE_STATUSES,
|
|
1690
1833
|
HISTORICAL_MESH_QUEUE_STATUSES: () => HISTORICAL_MESH_QUEUE_STATUSES,
|
|
1691
1834
|
MESH_TASK_MODES: () => MESH_TASK_MODES,
|
|
1835
|
+
__clearMeshQueueForTests: () => __clearMeshQueueForTests,
|
|
1836
|
+
__replaceMeshQueueForTests: () => __replaceMeshQueueForTests,
|
|
1837
|
+
__resetBeadsDBForTests: () => __resetBeadsDBForTests,
|
|
1692
1838
|
cancelTask: () => cancelTask,
|
|
1693
1839
|
claimNextTask: () => claimNextTask,
|
|
1694
1840
|
enqueueTask: () => enqueueTask,
|
|
1841
|
+
getMeshQueueRevision: () => getMeshQueueRevision,
|
|
1695
1842
|
getMeshQueueStats: () => getMeshQueueStats,
|
|
1696
1843
|
getQueue: () => getQueue,
|
|
1697
1844
|
normalizeMeshTaskMode: () => normalizeMeshTaskMode,
|
|
@@ -1727,53 +1874,14 @@ function validateMeshTaskModeRequest(mode, message) {
|
|
|
1727
1874
|
]
|
|
1728
1875
|
};
|
|
1729
1876
|
}
|
|
1730
|
-
function
|
|
1731
|
-
|
|
1732
|
-
return (0, import_path5.join)(getLedgerDir(), `${safe}.queue.json`);
|
|
1733
|
-
}
|
|
1734
|
-
function getLockPath(meshId) {
|
|
1735
|
-
const safe = meshId.replace(/[^a-zA-Z0-9_-]/g, "_");
|
|
1736
|
-
return (0, import_path5.join)(getLedgerDir(), `${safe}.queue.lock`);
|
|
1737
|
-
}
|
|
1738
|
-
function withQueueLock(meshId, fn) {
|
|
1739
|
-
const lockPath = getLockPath(meshId);
|
|
1740
|
-
let fd = -1;
|
|
1741
|
-
for (let i = 0; i < 10; i++) {
|
|
1742
|
-
try {
|
|
1743
|
-
fd = (0, import_fs5.openSync)(lockPath, "wx");
|
|
1744
|
-
break;
|
|
1745
|
-
} catch {
|
|
1746
|
-
const deadline = Date.now() + 30;
|
|
1747
|
-
while (Date.now() < deadline) {
|
|
1748
|
-
}
|
|
1749
|
-
}
|
|
1750
|
-
}
|
|
1751
|
-
try {
|
|
1752
|
-
return fn();
|
|
1753
|
-
} finally {
|
|
1754
|
-
if (fd !== -1) try {
|
|
1755
|
-
(0, import_fs5.closeSync)(fd);
|
|
1756
|
-
} catch {
|
|
1757
|
-
}
|
|
1758
|
-
try {
|
|
1759
|
-
(0, import_fs5.unlinkSync)(lockPath);
|
|
1760
|
-
} catch {
|
|
1761
|
-
}
|
|
1762
|
-
}
|
|
1877
|
+
function withQueueLock(_meshId, fn) {
|
|
1878
|
+
return BeadsDB.getInstance().transaction(fn);
|
|
1763
1879
|
}
|
|
1764
1880
|
function readQueue(meshId) {
|
|
1765
|
-
|
|
1766
|
-
if (!(0, import_fs5.existsSync)(path28)) return [];
|
|
1767
|
-
try {
|
|
1768
|
-
const content = (0, import_fs5.readFileSync)(path28, "utf-8");
|
|
1769
|
-
return JSON.parse(content);
|
|
1770
|
-
} catch {
|
|
1771
|
-
return [];
|
|
1772
|
-
}
|
|
1881
|
+
return BeadsDB.getInstance().getQueueEntries(meshId);
|
|
1773
1882
|
}
|
|
1774
1883
|
function writeQueue(meshId, queue) {
|
|
1775
|
-
|
|
1776
|
-
(0, import_fs5.writeFileSync)(path28, JSON.stringify(queue, null, 2), "utf-8");
|
|
1884
|
+
BeadsDB.getInstance().replaceQueue(meshId, queue);
|
|
1777
1885
|
}
|
|
1778
1886
|
function enqueueTask(meshId, message, opts) {
|
|
1779
1887
|
requireMeshHostQueueOwner(opts);
|
|
@@ -1807,6 +1915,9 @@ function getQueue(meshId, opts) {
|
|
|
1807
1915
|
}
|
|
1808
1916
|
return queue;
|
|
1809
1917
|
}
|
|
1918
|
+
function getMeshQueueRevision(meshId) {
|
|
1919
|
+
return BeadsDB.getInstance().getQueueRevision(meshId);
|
|
1920
|
+
}
|
|
1810
1921
|
function claimNextTask(meshId, nodeId, sessionId) {
|
|
1811
1922
|
return withQueueLock(meshId, () => {
|
|
1812
1923
|
const queue = readQueue(meshId);
|
|
@@ -1950,15 +2061,24 @@ function getMeshQueueStats(meshId) {
|
|
|
1950
2061
|
}))
|
|
1951
2062
|
};
|
|
1952
2063
|
}
|
|
1953
|
-
|
|
2064
|
+
function __replaceMeshQueueForTests(meshId, queue) {
|
|
2065
|
+
BeadsDB.getInstance().transaction(() => {
|
|
2066
|
+
BeadsDB.getInstance().replaceQueue(meshId, queue);
|
|
2067
|
+
});
|
|
2068
|
+
}
|
|
2069
|
+
function __clearMeshQueueForTests(meshId) {
|
|
2070
|
+
BeadsDB.getInstance().deleteQueue(meshId);
|
|
2071
|
+
}
|
|
2072
|
+
function __resetBeadsDBForTests() {
|
|
2073
|
+
BeadsDB.resetForTests();
|
|
2074
|
+
}
|
|
2075
|
+
var import_crypto5, ACTIVE_MESH_QUEUE_STATUSES, HISTORICAL_MESH_QUEUE_STATUSES, MESH_TASK_MODES, LIVE_DEBUG_READONLY_FORBIDDEN;
|
|
1954
2076
|
var init_mesh_work_queue = __esm({
|
|
1955
2077
|
"src/mesh/mesh-work-queue.ts"() {
|
|
1956
2078
|
"use strict";
|
|
1957
|
-
import_fs5 = require("fs");
|
|
1958
|
-
import_path5 = require("path");
|
|
1959
2079
|
import_crypto5 = require("crypto");
|
|
1960
|
-
init_mesh_ledger();
|
|
1961
2080
|
init_mesh_host_ownership();
|
|
2081
|
+
init_beads_db();
|
|
1962
2082
|
ACTIVE_MESH_QUEUE_STATUSES = ["pending", "assigned"];
|
|
1963
2083
|
HISTORICAL_MESH_QUEUE_STATUSES = ["completed", "failed", "cancelled"];
|
|
1964
2084
|
MESH_TASK_MODES = ["code_change", "validation", "live_debug_readonly", "launch_app", "convergence"];
|
|
@@ -2107,6 +2227,60 @@ var init_cli_detector = __esm({
|
|
|
2107
2227
|
}
|
|
2108
2228
|
});
|
|
2109
2229
|
|
|
2230
|
+
// src/logging/async-batch-writer.ts
|
|
2231
|
+
var fs2, AsyncBatchWriter;
|
|
2232
|
+
var init_async_batch_writer = __esm({
|
|
2233
|
+
"src/logging/async-batch-writer.ts"() {
|
|
2234
|
+
"use strict";
|
|
2235
|
+
fs2 = __toESM(require("fs"));
|
|
2236
|
+
AsyncBatchWriter = class {
|
|
2237
|
+
// Maps filePath -> string buffer
|
|
2238
|
+
static buffers = /* @__PURE__ */ new Map();
|
|
2239
|
+
static writePromises = /* @__PURE__ */ new Map();
|
|
2240
|
+
static flushTimer = null;
|
|
2241
|
+
/**
|
|
2242
|
+
* Queues data to be written to a file asynchronously in a batch.
|
|
2243
|
+
*/
|
|
2244
|
+
static write(filePath, data) {
|
|
2245
|
+
let buf = this.buffers.get(filePath);
|
|
2246
|
+
if (!buf) {
|
|
2247
|
+
buf = [];
|
|
2248
|
+
this.buffers.set(filePath, buf);
|
|
2249
|
+
}
|
|
2250
|
+
buf.push(data);
|
|
2251
|
+
if (!this.flushTimer) {
|
|
2252
|
+
this.flushTimer = setTimeout(() => {
|
|
2253
|
+
this.flushTimer = null;
|
|
2254
|
+
this.flushAll();
|
|
2255
|
+
}, 50);
|
|
2256
|
+
}
|
|
2257
|
+
}
|
|
2258
|
+
static async flushAll() {
|
|
2259
|
+
const entries = Array.from(this.buffers.entries());
|
|
2260
|
+
this.buffers.clear();
|
|
2261
|
+
for (const [filePath, buffer] of entries) {
|
|
2262
|
+
const dataToWrite = buffer.join("");
|
|
2263
|
+
const doWrite = async () => {
|
|
2264
|
+
try {
|
|
2265
|
+
const prevPromise = this.writePromises.get(filePath);
|
|
2266
|
+
if (prevPromise) await prevPromise;
|
|
2267
|
+
await fs2.promises.appendFile(filePath, dataToWrite, { encoding: "utf-8", mode: 384 });
|
|
2268
|
+
} catch {
|
|
2269
|
+
}
|
|
2270
|
+
};
|
|
2271
|
+
const writePromise = doWrite();
|
|
2272
|
+
this.writePromises.set(filePath, writePromise);
|
|
2273
|
+
writePromise.finally(() => {
|
|
2274
|
+
if (this.writePromises.get(filePath) === writePromise) {
|
|
2275
|
+
this.writePromises.delete(filePath);
|
|
2276
|
+
}
|
|
2277
|
+
});
|
|
2278
|
+
}
|
|
2279
|
+
}
|
|
2280
|
+
};
|
|
2281
|
+
}
|
|
2282
|
+
});
|
|
2283
|
+
|
|
2110
2284
|
// src/logging/logger.ts
|
|
2111
2285
|
function setLogLevel(level) {
|
|
2112
2286
|
currentLevel = level;
|
|
@@ -2134,7 +2308,7 @@ function checkDateRotation() {
|
|
|
2134
2308
|
}
|
|
2135
2309
|
function cleanOldLogs() {
|
|
2136
2310
|
try {
|
|
2137
|
-
const files =
|
|
2311
|
+
const files = fs3.readdirSync(LOG_DIR).filter((f) => f.startsWith("daemon-") && f.endsWith(".log"));
|
|
2138
2312
|
const cutoff = /* @__PURE__ */ new Date();
|
|
2139
2313
|
cutoff.setDate(cutoff.getDate() - MAX_LOG_DAYS);
|
|
2140
2314
|
const cutoffStr = cutoff.toISOString().slice(0, 10);
|
|
@@ -2142,7 +2316,7 @@ function cleanOldLogs() {
|
|
|
2142
2316
|
const dateMatch = file.match(/daemon-(\d{4}-\d{2}-\d{2})/);
|
|
2143
2317
|
if (dateMatch && dateMatch[1] < cutoffStr) {
|
|
2144
2318
|
try {
|
|
2145
|
-
|
|
2319
|
+
fs3.unlinkSync(path9.join(LOG_DIR, file));
|
|
2146
2320
|
} catch {
|
|
2147
2321
|
}
|
|
2148
2322
|
}
|
|
@@ -2152,14 +2326,14 @@ function cleanOldLogs() {
|
|
|
2152
2326
|
}
|
|
2153
2327
|
function rotateSizeIfNeeded() {
|
|
2154
2328
|
try {
|
|
2155
|
-
const stat2 =
|
|
2329
|
+
const stat2 = fs3.statSync(currentLogFile);
|
|
2156
2330
|
if (stat2.size > MAX_LOG_SIZE) {
|
|
2157
2331
|
const backup = currentLogFile.replace(".log", ".1.log");
|
|
2158
2332
|
try {
|
|
2159
|
-
|
|
2333
|
+
fs3.unlinkSync(backup);
|
|
2160
2334
|
} catch {
|
|
2161
2335
|
}
|
|
2162
|
-
|
|
2336
|
+
fs3.renameSync(currentLogFile, backup);
|
|
2163
2337
|
}
|
|
2164
2338
|
} catch {
|
|
2165
2339
|
}
|
|
@@ -2170,7 +2344,7 @@ function writeToFile(line) {
|
|
|
2170
2344
|
checkDateRotation();
|
|
2171
2345
|
rotateSizeIfNeeded();
|
|
2172
2346
|
}
|
|
2173
|
-
|
|
2347
|
+
AsyncBatchWriter.write(currentLogFile, line + "\n");
|
|
2174
2348
|
} catch {
|
|
2175
2349
|
}
|
|
2176
2350
|
}
|
|
@@ -2258,13 +2432,14 @@ function installGlobalInterceptor() {
|
|
|
2258
2432
|
writeToFile(`Log file: ${currentLogFile}`);
|
|
2259
2433
|
writeToFile(`Log level: ${currentLevel}`);
|
|
2260
2434
|
}
|
|
2261
|
-
var
|
|
2435
|
+
var fs3, path9, os3, LEVEL_NUM, LEVEL_LABEL, currentLevel, LOG_DIR, MAX_LOG_SIZE, MAX_LOG_DAYS, currentDate, currentLogFile, writeCount, RING_BUFFER_SIZE, ringBuffer, origConsoleLog, origConsoleError, origConsoleWarn, LOG, interceptorInstalled, LOG_PATH;
|
|
2262
2436
|
var init_logger = __esm({
|
|
2263
2437
|
"src/logging/logger.ts"() {
|
|
2264
2438
|
"use strict";
|
|
2265
|
-
|
|
2439
|
+
fs3 = __toESM(require("fs"));
|
|
2266
2440
|
path9 = __toESM(require("path"));
|
|
2267
2441
|
os3 = __toESM(require("os"));
|
|
2442
|
+
init_async_batch_writer();
|
|
2268
2443
|
LEVEL_NUM = { debug: 0, info: 1, warn: 2, error: 3 };
|
|
2269
2444
|
LEVEL_LABEL = { debug: "DBG", info: "INF", warn: "WRN", error: "ERR" };
|
|
2270
2445
|
currentLevel = "info";
|
|
@@ -2272,7 +2447,7 @@ var init_logger = __esm({
|
|
|
2272
2447
|
MAX_LOG_SIZE = 5 * 1024 * 1024;
|
|
2273
2448
|
MAX_LOG_DAYS = 7;
|
|
2274
2449
|
try {
|
|
2275
|
-
|
|
2450
|
+
fs3.mkdirSync(LOG_DIR, { recursive: true });
|
|
2276
2451
|
} catch {
|
|
2277
2452
|
}
|
|
2278
2453
|
currentDate = getDateStr();
|
|
@@ -2280,14 +2455,14 @@ var init_logger = __esm({
|
|
|
2280
2455
|
cleanOldLogs();
|
|
2281
2456
|
try {
|
|
2282
2457
|
const oldLog = path9.join(LOG_DIR, "daemon.log");
|
|
2283
|
-
if (
|
|
2284
|
-
const stat2 =
|
|
2458
|
+
if (fs3.existsSync(oldLog)) {
|
|
2459
|
+
const stat2 = fs3.statSync(oldLog);
|
|
2285
2460
|
const oldDate = stat2.mtime.toISOString().slice(0, 10);
|
|
2286
|
-
|
|
2461
|
+
fs3.renameSync(oldLog, path9.join(LOG_DIR, `daemon-${oldDate}.log`));
|
|
2287
2462
|
}
|
|
2288
2463
|
const oldLogBackup = path9.join(LOG_DIR, "daemon.log.old");
|
|
2289
|
-
if (
|
|
2290
|
-
|
|
2464
|
+
if (fs3.existsSync(oldLogBackup)) {
|
|
2465
|
+
fs3.unlinkSync(oldLogBackup);
|
|
2291
2466
|
}
|
|
2292
2467
|
} catch {
|
|
2293
2468
|
}
|
|
@@ -3630,8 +3805,8 @@ var init_pty_transport = __esm({
|
|
|
3630
3805
|
let cwd = options.cwd;
|
|
3631
3806
|
if (cwd) {
|
|
3632
3807
|
try {
|
|
3633
|
-
const
|
|
3634
|
-
const stat2 =
|
|
3808
|
+
const fs17 = require("fs");
|
|
3809
|
+
const stat2 = fs17.statSync(cwd);
|
|
3635
3810
|
if (!stat2.isDirectory()) cwd = os8.homedir();
|
|
3636
3811
|
} catch {
|
|
3637
3812
|
cwd = os8.homedir();
|
|
@@ -3731,27 +3906,35 @@ function findBinary(name) {
|
|
|
3731
3906
|
return path14.isAbsolute(expanded) ? expanded : path14.resolve(expanded);
|
|
3732
3907
|
}
|
|
3733
3908
|
const isWin = os9.platform() === "win32";
|
|
3734
|
-
|
|
3735
|
-
|
|
3736
|
-
|
|
3737
|
-
|
|
3738
|
-
|
|
3739
|
-
|
|
3740
|
-
|
|
3741
|
-
|
|
3742
|
-
|
|
3743
|
-
|
|
3909
|
+
const paths = (process.env.PATH || "").split(path14.delimiter);
|
|
3910
|
+
const exes = isWin ? [".exe", ".cmd", ".bat", ""] : [""];
|
|
3911
|
+
for (const p of paths) {
|
|
3912
|
+
if (!p) continue;
|
|
3913
|
+
for (const ext of exes) {
|
|
3914
|
+
const fullPath = path14.join(p, trimmed + ext);
|
|
3915
|
+
try {
|
|
3916
|
+
const fs17 = require("fs");
|
|
3917
|
+
if (fs17.existsSync(fullPath)) {
|
|
3918
|
+
const stat2 = fs17.statSync(fullPath);
|
|
3919
|
+
if (stat2.isFile() && (isWin || stat2.mode & 73)) {
|
|
3920
|
+
return fullPath;
|
|
3921
|
+
}
|
|
3922
|
+
}
|
|
3923
|
+
} catch {
|
|
3924
|
+
}
|
|
3925
|
+
}
|
|
3744
3926
|
}
|
|
3927
|
+
return isWin ? `${trimmed}.cmd` : trimmed;
|
|
3745
3928
|
}
|
|
3746
3929
|
function isScriptBinary(binaryPath) {
|
|
3747
3930
|
if (!path14.isAbsolute(binaryPath)) return false;
|
|
3748
3931
|
try {
|
|
3749
|
-
const
|
|
3750
|
-
const resolved =
|
|
3932
|
+
const fs17 = require("fs");
|
|
3933
|
+
const resolved = fs17.realpathSync(binaryPath);
|
|
3751
3934
|
const head = Buffer.alloc(8);
|
|
3752
|
-
const fd =
|
|
3753
|
-
|
|
3754
|
-
|
|
3935
|
+
const fd = fs17.openSync(resolved, "r");
|
|
3936
|
+
fs17.readSync(fd, head, 0, 8, 0);
|
|
3937
|
+
fs17.closeSync(fd);
|
|
3755
3938
|
let i = 0;
|
|
3756
3939
|
if (head[0] === 239 && head[1] === 187 && head[2] === 191) i = 3;
|
|
3757
3940
|
return head[i] === 35 && head[i + 1] === 33;
|
|
@@ -3762,12 +3945,12 @@ function isScriptBinary(binaryPath) {
|
|
|
3762
3945
|
function looksLikeMachOOrElf(filePath) {
|
|
3763
3946
|
if (!path14.isAbsolute(filePath)) return false;
|
|
3764
3947
|
try {
|
|
3765
|
-
const
|
|
3766
|
-
const resolved =
|
|
3948
|
+
const fs17 = require("fs");
|
|
3949
|
+
const resolved = fs17.realpathSync(filePath);
|
|
3767
3950
|
const buf = Buffer.alloc(8);
|
|
3768
|
-
const fd =
|
|
3769
|
-
|
|
3770
|
-
|
|
3951
|
+
const fd = fs17.openSync(resolved, "r");
|
|
3952
|
+
fs17.readSync(fd, buf, 0, 8, 0);
|
|
3953
|
+
fs17.closeSync(fd);
|
|
3771
3954
|
let i = 0;
|
|
3772
3955
|
if (buf[0] === 239 && buf[1] === 187 && buf[2] === 191) i = 3;
|
|
3773
3956
|
const b = buf.subarray(i);
|
|
@@ -3849,13 +4032,12 @@ function normalizeCliProviderForRuntime(raw) {
|
|
|
3849
4032
|
}
|
|
3850
4033
|
};
|
|
3851
4034
|
}
|
|
3852
|
-
var os9, path14,
|
|
4035
|
+
var os9, path14, TerminalTranscriptAccumulator, buildCliSpawnEnv;
|
|
3853
4036
|
var init_provider_cli_shared = __esm({
|
|
3854
4037
|
"src/cli-adapters/provider-cli-shared.ts"() {
|
|
3855
4038
|
"use strict";
|
|
3856
4039
|
os9 = __toESM(require("os"));
|
|
3857
4040
|
path14 = __toESM(require("path"));
|
|
3858
|
-
import_child_process4 = require("child_process");
|
|
3859
4041
|
init_spawn_env();
|
|
3860
4042
|
TerminalTranscriptAccumulator = class {
|
|
3861
4043
|
lines = [[]];
|
|
@@ -6459,6 +6641,7 @@ __export(index_exports, {
|
|
|
6459
6641
|
getLogLevel: () => getLogLevel,
|
|
6460
6642
|
getMesh: () => getMesh,
|
|
6461
6643
|
getMeshByRepo: () => getMeshByRepo,
|
|
6644
|
+
getMeshQueueRevision: () => getMeshQueueRevision,
|
|
6462
6645
|
getMeshQueueStats: () => getMeshQueueStats,
|
|
6463
6646
|
getNpmExecOptions: () => getNpmExecOptions,
|
|
6464
6647
|
getPendingMeshCoordinatorEvents: () => getPendingMeshCoordinatorEvents,
|
|
@@ -9339,9 +9522,11 @@ function resetState() {
|
|
|
9339
9522
|
|
|
9340
9523
|
// src/detection/ide-detector.ts
|
|
9341
9524
|
var import_child_process2 = require("child_process");
|
|
9525
|
+
var import_util = require("util");
|
|
9342
9526
|
var import_fs9 = require("fs");
|
|
9343
9527
|
var import_os2 = require("os");
|
|
9344
9528
|
var path10 = __toESM(require("path"));
|
|
9529
|
+
var execAsync2 = (0, import_util.promisify)(import_child_process2.exec);
|
|
9345
9530
|
var BUILTIN_IDE_DEFINITIONS = [];
|
|
9346
9531
|
var registeredIDEs = /* @__PURE__ */ new Map();
|
|
9347
9532
|
function registerIDEDefinition(def) {
|
|
@@ -9365,24 +9550,33 @@ function findCliCommand(command) {
|
|
|
9365
9550
|
const resolved = path10.isAbsolute(candidate) ? candidate : path10.resolve(candidate);
|
|
9366
9551
|
return (0, import_fs9.existsSync)(resolved) ? resolved : null;
|
|
9367
9552
|
}
|
|
9368
|
-
|
|
9369
|
-
|
|
9370
|
-
|
|
9371
|
-
|
|
9372
|
-
|
|
9373
|
-
|
|
9374
|
-
|
|
9375
|
-
|
|
9553
|
+
const isWin = (0, import_os2.platform)() === "win32";
|
|
9554
|
+
const paths = (process.env.PATH || "").split(isWin ? ";" : ":");
|
|
9555
|
+
const exes = isWin ? [".exe", ".cmd", ".bat", ""] : [""];
|
|
9556
|
+
for (const p of paths) {
|
|
9557
|
+
if (!p) continue;
|
|
9558
|
+
for (const ext of exes) {
|
|
9559
|
+
const fullPath = path10.join(p, trimmed + ext);
|
|
9560
|
+
try {
|
|
9561
|
+
if ((0, import_fs9.existsSync)(fullPath)) {
|
|
9562
|
+
const stat2 = (0, import_fs9.statSync)(fullPath);
|
|
9563
|
+
if (stat2.isFile() && (isWin || stat2.mode & 73)) {
|
|
9564
|
+
return fullPath;
|
|
9565
|
+
}
|
|
9566
|
+
}
|
|
9567
|
+
} catch {
|
|
9568
|
+
}
|
|
9569
|
+
}
|
|
9376
9570
|
}
|
|
9571
|
+
return null;
|
|
9377
9572
|
}
|
|
9378
|
-
function getIdeVersion(cliCommand) {
|
|
9573
|
+
async function getIdeVersion(cliCommand) {
|
|
9379
9574
|
try {
|
|
9380
|
-
const
|
|
9575
|
+
const { stdout } = await execAsync2(`"${cliCommand}" --version`, {
|
|
9381
9576
|
encoding: "utf-8",
|
|
9382
|
-
timeout: 1e4
|
|
9383
|
-
|
|
9384
|
-
|
|
9385
|
-
return result.split("\n")[0] || null;
|
|
9577
|
+
timeout: 1e4
|
|
9578
|
+
});
|
|
9579
|
+
return stdout.trim().split("\n")[0] || null;
|
|
9386
9580
|
} catch {
|
|
9387
9581
|
return null;
|
|
9388
9582
|
}
|
|
@@ -9430,7 +9624,7 @@ async function detectIDEs(providerLoader) {
|
|
|
9430
9624
|
}
|
|
9431
9625
|
}
|
|
9432
9626
|
const installed = os22 === "darwin" ? !!(resolvedCli || appPath) : !!resolvedCli;
|
|
9433
|
-
const version = resolvedCli ? getIdeVersion(resolvedCli) : null;
|
|
9627
|
+
const version = resolvedCli ? await getIdeVersion(resolvedCli) : null;
|
|
9434
9628
|
results.push({
|
|
9435
9629
|
id: def.id,
|
|
9436
9630
|
name: def.name,
|
|
@@ -9451,18 +9645,22 @@ init_cli_detector();
|
|
|
9451
9645
|
// src/system/host-memory.ts
|
|
9452
9646
|
var os4 = __toESM(require("os"));
|
|
9453
9647
|
var import_child_process3 = require("child_process");
|
|
9454
|
-
|
|
9455
|
-
|
|
9648
|
+
var import_util2 = require("util");
|
|
9649
|
+
var execAsync3 = (0, import_util2.promisify)(import_child_process3.exec);
|
|
9650
|
+
var cachedDarwinAvail = null;
|
|
9651
|
+
var darwinMemoryInterval = null;
|
|
9652
|
+
async function updateDarwinMemoryCache() {
|
|
9653
|
+
if (os4.platform() !== "darwin") return;
|
|
9456
9654
|
try {
|
|
9457
|
-
const
|
|
9655
|
+
const { stdout } = await execAsync3("vm_stat", {
|
|
9458
9656
|
encoding: "utf-8",
|
|
9459
9657
|
timeout: 4e3,
|
|
9460
9658
|
maxBuffer: 256 * 1024
|
|
9461
9659
|
});
|
|
9462
|
-
const pageSizeMatch =
|
|
9660
|
+
const pageSizeMatch = stdout.match(/page size of (\d+)\s*bytes/i);
|
|
9463
9661
|
const pageSize = pageSizeMatch ? parseInt(pageSizeMatch[1], 10) : 4096;
|
|
9464
9662
|
const counts = {};
|
|
9465
|
-
for (const line of
|
|
9663
|
+
for (const line of stdout.split("\n")) {
|
|
9466
9664
|
const m = line.match(/^\s*Pages\s+([^:]+):\s+([\d,]+)\s*\.?/);
|
|
9467
9665
|
if (!m) continue;
|
|
9468
9666
|
const key = m[1].trim().toLowerCase().replace(/\s+/g, "_");
|
|
@@ -9476,18 +9674,24 @@ function parseDarwinAvailableBytes(totalMem) {
|
|
|
9476
9674
|
const fileBacked = counts["file_backed"] ?? 0;
|
|
9477
9675
|
const availPages = free + inactive + speculative + purgeable + fileBacked;
|
|
9478
9676
|
const bytes = availPages * pageSize;
|
|
9479
|
-
|
|
9480
|
-
return Math.min(bytes, totalMem);
|
|
9677
|
+
cachedDarwinAvail = Number.isFinite(bytes) && bytes >= 0 ? Math.min(bytes, os4.totalmem()) : null;
|
|
9481
9678
|
} catch {
|
|
9482
|
-
return null;
|
|
9483
9679
|
}
|
|
9484
9680
|
}
|
|
9485
9681
|
function getHostMemorySnapshot() {
|
|
9682
|
+
if (os4.platform() === "darwin" && !darwinMemoryInterval) {
|
|
9683
|
+
updateDarwinMemoryCache();
|
|
9684
|
+
darwinMemoryInterval = setInterval(updateDarwinMemoryCache, 3e3);
|
|
9685
|
+
darwinMemoryInterval.unref();
|
|
9686
|
+
}
|
|
9486
9687
|
const totalMem = os4.totalmem();
|
|
9487
9688
|
const freeMem = os4.freemem();
|
|
9488
|
-
const
|
|
9489
|
-
|
|
9490
|
-
|
|
9689
|
+
const availableMem = os4.platform() === "darwin" ? cachedDarwinAvail ?? freeMem : freeMem;
|
|
9690
|
+
return {
|
|
9691
|
+
totalMem,
|
|
9692
|
+
freeMem,
|
|
9693
|
+
availableMem
|
|
9694
|
+
};
|
|
9491
9695
|
}
|
|
9492
9696
|
|
|
9493
9697
|
// src/session-host/runtime-surface.ts
|
|
@@ -11852,7 +12056,7 @@ ${cleanBody}`;
|
|
|
11852
12056
|
}
|
|
11853
12057
|
|
|
11854
12058
|
// src/config/chat-history.ts
|
|
11855
|
-
var
|
|
12059
|
+
var fs4 = __toESM(require("fs"));
|
|
11856
12060
|
var path11 = __toESM(require("path"));
|
|
11857
12061
|
var os5 = __toESM(require("os"));
|
|
11858
12062
|
var HISTORY_DIR = path11.join(os5.homedir(), ".adhdev", "history");
|
|
@@ -11972,8 +12176,8 @@ function buildSavedHistorySessionSummaryMapFromEntries(entries) {
|
|
|
11972
12176
|
function readPersistedSavedHistorySessionSummaries(dir) {
|
|
11973
12177
|
try {
|
|
11974
12178
|
const filePath = getSavedHistoryIndexFilePath(dir);
|
|
11975
|
-
if (!
|
|
11976
|
-
const raw = JSON.parse(
|
|
12179
|
+
if (!fs4.existsSync(filePath)) return null;
|
|
12180
|
+
const raw = JSON.parse(fs4.readFileSync(filePath, "utf-8"));
|
|
11977
12181
|
if (!raw || raw.version !== SAVED_HISTORY_INDEX_VERSION || !raw.sessions || typeof raw.sessions !== "object") {
|
|
11978
12182
|
return null;
|
|
11979
12183
|
}
|
|
@@ -12000,7 +12204,7 @@ function sanitizeHistoryFileSegment(value) {
|
|
|
12000
12204
|
}
|
|
12001
12205
|
function listHistoryFiles(dir, historySessionId) {
|
|
12002
12206
|
const sanitizedSessionId = historySessionId ? sanitizeHistoryFileSegment(historySessionId) : "";
|
|
12003
|
-
return
|
|
12207
|
+
return fs4.readdirSync(dir).filter((file) => {
|
|
12004
12208
|
if (!file.endsWith(".jsonl")) return false;
|
|
12005
12209
|
if (sanitizedSessionId) {
|
|
12006
12210
|
return file.startsWith(`${sanitizedSessionId}_`);
|
|
@@ -12018,7 +12222,7 @@ function extractSavedHistorySessionIdFromFile(file) {
|
|
|
12018
12222
|
function buildSavedHistoryFileSignatureMap(dir, files) {
|
|
12019
12223
|
return new Map(files.map((file) => {
|
|
12020
12224
|
try {
|
|
12021
|
-
const stat2 =
|
|
12225
|
+
const stat2 = fs4.statSync(path11.join(dir, file));
|
|
12022
12226
|
return [file, `${file}:${stat2.size}:${Math.trunc(stat2.mtimeMs)}`];
|
|
12023
12227
|
} catch {
|
|
12024
12228
|
return [file, `${file}:missing`];
|
|
@@ -12041,8 +12245,8 @@ function sleepBlocking(ms) {
|
|
|
12041
12245
|
function loadPersistedSavedHistoryIndexFromFile(dir) {
|
|
12042
12246
|
try {
|
|
12043
12247
|
const filePath = getSavedHistoryIndexFilePath(dir);
|
|
12044
|
-
if (!
|
|
12045
|
-
const raw = JSON.parse(
|
|
12248
|
+
if (!fs4.existsSync(filePath)) return /* @__PURE__ */ new Map();
|
|
12249
|
+
const raw = JSON.parse(fs4.readFileSync(filePath, "utf-8"));
|
|
12046
12250
|
if (!raw || raw.version !== SAVED_HISTORY_INDEX_VERSION || !raw.files || typeof raw.files !== "object") {
|
|
12047
12251
|
return /* @__PURE__ */ new Map();
|
|
12048
12252
|
}
|
|
@@ -12064,27 +12268,27 @@ function writePersistedSavedHistoryIndexFile(dir, entries) {
|
|
|
12064
12268
|
files: Object.fromEntries(entries.entries()),
|
|
12065
12269
|
sessions: buildSavedHistorySessionSummaryMapFromEntries(entries)
|
|
12066
12270
|
};
|
|
12067
|
-
|
|
12068
|
-
|
|
12271
|
+
fs4.writeFileSync(tempPath, JSON.stringify(payload), "utf-8");
|
|
12272
|
+
fs4.renameSync(tempPath, filePath);
|
|
12069
12273
|
}
|
|
12070
12274
|
function acquireSavedHistoryIndexLock(dir) {
|
|
12071
12275
|
const lockPath = getSavedHistoryIndexLockPath(dir);
|
|
12072
12276
|
const deadline = Date.now() + SAVED_HISTORY_INDEX_LOCK_WAIT_MS;
|
|
12073
12277
|
while (Date.now() <= deadline) {
|
|
12074
12278
|
try {
|
|
12075
|
-
|
|
12279
|
+
fs4.mkdirSync(lockPath);
|
|
12076
12280
|
return () => {
|
|
12077
12281
|
try {
|
|
12078
|
-
|
|
12282
|
+
fs4.rmSync(lockPath, { recursive: true, force: true });
|
|
12079
12283
|
} catch {
|
|
12080
12284
|
}
|
|
12081
12285
|
};
|
|
12082
12286
|
} catch (error) {
|
|
12083
12287
|
if (error?.code !== "EEXIST") return null;
|
|
12084
12288
|
try {
|
|
12085
|
-
const stat2 =
|
|
12289
|
+
const stat2 = fs4.statSync(lockPath);
|
|
12086
12290
|
if (Date.now() - stat2.mtimeMs > SAVED_HISTORY_INDEX_LOCK_STALE_MS) {
|
|
12087
|
-
|
|
12291
|
+
fs4.rmSync(lockPath, { recursive: true, force: true });
|
|
12088
12292
|
continue;
|
|
12089
12293
|
}
|
|
12090
12294
|
} catch {
|
|
@@ -12131,7 +12335,7 @@ function savePersistedSavedHistoryIndex(dir, entries) {
|
|
|
12131
12335
|
}
|
|
12132
12336
|
for (const file of Array.from(currentEntries.keys())) {
|
|
12133
12337
|
if (incomingFiles.has(file)) continue;
|
|
12134
|
-
if (!
|
|
12338
|
+
if (!fs4.existsSync(path11.join(dir, file))) {
|
|
12135
12339
|
currentEntries.delete(file);
|
|
12136
12340
|
}
|
|
12137
12341
|
}
|
|
@@ -12139,14 +12343,14 @@ function savePersistedSavedHistoryIndex(dir, entries) {
|
|
|
12139
12343
|
}
|
|
12140
12344
|
function invalidatePersistedSavedHistoryIndex(agentType, dir) {
|
|
12141
12345
|
try {
|
|
12142
|
-
|
|
12346
|
+
fs4.rmSync(getSavedHistoryIndexFilePath(dir), { force: true });
|
|
12143
12347
|
} catch {
|
|
12144
12348
|
}
|
|
12145
12349
|
savedHistorySessionCache.delete(agentType.replace(/[^a-zA-Z0-9_-]/g, "_"));
|
|
12146
12350
|
}
|
|
12147
12351
|
function buildSavedHistoryIndexFileSignature(dir) {
|
|
12148
12352
|
try {
|
|
12149
|
-
const stat2 =
|
|
12353
|
+
const stat2 = fs4.statSync(getSavedHistoryIndexFilePath(dir));
|
|
12150
12354
|
return `index:${stat2.size}:${Math.trunc(stat2.mtimeMs)}`;
|
|
12151
12355
|
} catch {
|
|
12152
12356
|
return "index:missing";
|
|
@@ -12154,10 +12358,10 @@ function buildSavedHistoryIndexFileSignature(dir) {
|
|
|
12154
12358
|
}
|
|
12155
12359
|
function historyDirectoryHasFilesNewerThanIndex(dir) {
|
|
12156
12360
|
try {
|
|
12157
|
-
const indexStat =
|
|
12361
|
+
const indexStat = fs4.statSync(getSavedHistoryIndexFilePath(dir));
|
|
12158
12362
|
const files = listHistoryFiles(dir);
|
|
12159
12363
|
for (const file of files) {
|
|
12160
|
-
const stat2 =
|
|
12364
|
+
const stat2 = fs4.statSync(path11.join(dir, file));
|
|
12161
12365
|
if (stat2.mtimeMs > indexStat.mtimeMs) return true;
|
|
12162
12366
|
}
|
|
12163
12367
|
return false;
|
|
@@ -12167,7 +12371,7 @@ function historyDirectoryHasFilesNewerThanIndex(dir) {
|
|
|
12167
12371
|
}
|
|
12168
12372
|
function buildSavedHistoryFileSignature(dir, file) {
|
|
12169
12373
|
try {
|
|
12170
|
-
const stat2 =
|
|
12374
|
+
const stat2 = fs4.statSync(path11.join(dir, file));
|
|
12171
12375
|
return `${file}:${stat2.size}:${Math.trunc(stat2.mtimeMs)}`;
|
|
12172
12376
|
} catch {
|
|
12173
12377
|
return `${file}:missing`;
|
|
@@ -12248,7 +12452,7 @@ function computeSavedHistoryFileSummary(dir, file) {
|
|
|
12248
12452
|
const historySessionId = extractSavedHistorySessionIdFromFile(file);
|
|
12249
12453
|
if (!historySessionId) return null;
|
|
12250
12454
|
const filePath = path11.join(dir, file);
|
|
12251
|
-
const content =
|
|
12455
|
+
const content = fs4.readFileSync(filePath, "utf-8");
|
|
12252
12456
|
const lines = content.split("\n").filter(Boolean);
|
|
12253
12457
|
let messageCount = 0;
|
|
12254
12458
|
let firstMessageAt = 0;
|
|
@@ -12309,7 +12513,7 @@ function scheduleSavedHistoryBackgroundRefresh(agentType, dir) {
|
|
|
12309
12513
|
savedHistoryBackgroundRefresh.add(key);
|
|
12310
12514
|
setTimeout(() => {
|
|
12311
12515
|
try {
|
|
12312
|
-
if (!
|
|
12516
|
+
if (!fs4.existsSync(dir)) return;
|
|
12313
12517
|
const files = listHistoryFiles(dir);
|
|
12314
12518
|
const fileSignatures = buildSavedHistoryFileSignatureMap(dir, files);
|
|
12315
12519
|
const persistedEntries = loadPersistedSavedHistoryIndex(dir);
|
|
@@ -12455,13 +12659,13 @@ var ChatHistoryWriter = class {
|
|
|
12455
12659
|
}
|
|
12456
12660
|
if (newMessages.length === 0) return;
|
|
12457
12661
|
const dir = path11.join(HISTORY_DIR, this.sanitize(agentType));
|
|
12458
|
-
|
|
12662
|
+
fs4.mkdirSync(dir, { recursive: true });
|
|
12459
12663
|
const date = (/* @__PURE__ */ new Date()).toISOString().slice(0, 10);
|
|
12460
12664
|
const filePrefix = effectiveHistoryKey ? `${this.sanitize(effectiveHistoryKey)}_` : "";
|
|
12461
12665
|
const fileName = `${filePrefix}${date}.jsonl`;
|
|
12462
12666
|
const filePath = path11.join(dir, fileName);
|
|
12463
12667
|
const lines = newMessages.map((m) => JSON.stringify(m)).join("\n") + "\n";
|
|
12464
|
-
|
|
12668
|
+
fs4.appendFileSync(filePath, lines, "utf-8");
|
|
12465
12669
|
updateSavedHistoryIndexForAppendedMessages(agentType, dir, fileName, effectiveHistoryKey, newMessages);
|
|
12466
12670
|
const prevCount = this.lastSeenCounts.get(dedupKey) || 0;
|
|
12467
12671
|
if (!historySessionId && messages.length < prevCount * 0.5 && prevCount > 3) {
|
|
@@ -12551,7 +12755,7 @@ var ChatHistoryWriter = class {
|
|
|
12551
12755
|
if (!id || !ws) return;
|
|
12552
12756
|
try {
|
|
12553
12757
|
const dir = path11.join(HISTORY_DIR, this.sanitize(agentType));
|
|
12554
|
-
|
|
12758
|
+
fs4.mkdirSync(dir, { recursive: true });
|
|
12555
12759
|
const date = (/* @__PURE__ */ new Date()).toISOString().slice(0, 10);
|
|
12556
12760
|
const fileName = `${this.sanitize(id)}_${date}.jsonl`;
|
|
12557
12761
|
const filePath = path11.join(dir, fileName);
|
|
@@ -12566,7 +12770,7 @@ var ChatHistoryWriter = class {
|
|
|
12566
12770
|
historySessionId: id,
|
|
12567
12771
|
workspace: ws
|
|
12568
12772
|
};
|
|
12569
|
-
|
|
12773
|
+
fs4.appendFileSync(filePath, JSON.stringify(record) + "\n", "utf-8");
|
|
12570
12774
|
updateSavedHistoryIndexForSessionStart(agentType, dir, fileName, id, ws);
|
|
12571
12775
|
} catch {
|
|
12572
12776
|
}
|
|
@@ -12601,14 +12805,14 @@ var ChatHistoryWriter = class {
|
|
|
12601
12805
|
this.lastSeenCounts.delete(fromDedupKey);
|
|
12602
12806
|
}
|
|
12603
12807
|
const dir = path11.join(HISTORY_DIR, this.sanitize(agentType));
|
|
12604
|
-
if (!
|
|
12808
|
+
if (!fs4.existsSync(dir)) return;
|
|
12605
12809
|
const fromPrefix = `${this.sanitize(fromId)}_`;
|
|
12606
12810
|
const toPrefix = `${this.sanitize(toId)}_`;
|
|
12607
|
-
const files =
|
|
12811
|
+
const files = fs4.readdirSync(dir).filter((file) => file.startsWith(fromPrefix) && file.endsWith(".jsonl"));
|
|
12608
12812
|
for (const file of files) {
|
|
12609
12813
|
const sourcePath = path11.join(dir, file);
|
|
12610
12814
|
const targetPath = path11.join(dir, `${toPrefix}${file.slice(fromPrefix.length)}`);
|
|
12611
|
-
const sourceLines =
|
|
12815
|
+
const sourceLines = fs4.readFileSync(sourcePath, "utf-8").split("\n").filter(Boolean);
|
|
12612
12816
|
const rewritten = sourceLines.map((line) => {
|
|
12613
12817
|
try {
|
|
12614
12818
|
const parsed = JSON.parse(line);
|
|
@@ -12622,16 +12826,16 @@ var ChatHistoryWriter = class {
|
|
|
12622
12826
|
}
|
|
12623
12827
|
}).filter((line) => !!line);
|
|
12624
12828
|
if (rewritten.length === 0) {
|
|
12625
|
-
|
|
12829
|
+
fs4.unlinkSync(sourcePath);
|
|
12626
12830
|
continue;
|
|
12627
12831
|
}
|
|
12628
|
-
const existing =
|
|
12832
|
+
const existing = fs4.existsSync(targetPath) ? new Set(fs4.readFileSync(targetPath, "utf-8").split("\n").filter(Boolean)) : /* @__PURE__ */ new Set();
|
|
12629
12833
|
const nextLines = rewritten.filter((line) => !existing.has(line));
|
|
12630
12834
|
if (nextLines.length > 0) {
|
|
12631
|
-
|
|
12835
|
+
fs4.appendFileSync(targetPath, `${nextLines.join("\n")}
|
|
12632
12836
|
`, "utf-8");
|
|
12633
12837
|
}
|
|
12634
|
-
|
|
12838
|
+
fs4.unlinkSync(sourcePath);
|
|
12635
12839
|
}
|
|
12636
12840
|
invalidatePersistedSavedHistoryIndex(agentType, dir);
|
|
12637
12841
|
} catch {
|
|
@@ -12642,13 +12846,13 @@ var ChatHistoryWriter = class {
|
|
|
12642
12846
|
if (!sessionId) return;
|
|
12643
12847
|
try {
|
|
12644
12848
|
const dir = path11.join(HISTORY_DIR, this.sanitize(agentType));
|
|
12645
|
-
if (!
|
|
12849
|
+
if (!fs4.existsSync(dir)) return;
|
|
12646
12850
|
const prefix = `${this.sanitize(sessionId)}_`;
|
|
12647
|
-
const files =
|
|
12851
|
+
const files = fs4.readdirSync(dir).filter((file) => file.startsWith(prefix) && file.endsWith(".jsonl")).sort();
|
|
12648
12852
|
const seen = /* @__PURE__ */ new Set();
|
|
12649
12853
|
for (const file of files) {
|
|
12650
12854
|
const filePath = path11.join(dir, file);
|
|
12651
|
-
const lines =
|
|
12855
|
+
const lines = fs4.readFileSync(filePath, "utf-8").split("\n").filter(Boolean);
|
|
12652
12856
|
const next = [];
|
|
12653
12857
|
for (const line of lines) {
|
|
12654
12858
|
let parsed = null;
|
|
@@ -12677,10 +12881,10 @@ var ChatHistoryWriter = class {
|
|
|
12677
12881
|
}
|
|
12678
12882
|
const collapsed = collapseReplayAssistantTurns(dedupedAdjacent, historyBehavior);
|
|
12679
12883
|
if (collapsed.length === 0) {
|
|
12680
|
-
|
|
12884
|
+
fs4.unlinkSync(filePath);
|
|
12681
12885
|
continue;
|
|
12682
12886
|
}
|
|
12683
|
-
|
|
12887
|
+
fs4.writeFileSync(filePath, `${collapsed.map((entry) => JSON.stringify(entry)).join("\n")}
|
|
12684
12888
|
`, "utf-8");
|
|
12685
12889
|
}
|
|
12686
12890
|
invalidatePersistedSavedHistoryIndex(agentType, dir);
|
|
@@ -12697,18 +12901,18 @@ var ChatHistoryWriter = class {
|
|
|
12697
12901
|
/** Delete history files older than 30 days */
|
|
12698
12902
|
async rotateOldFiles() {
|
|
12699
12903
|
try {
|
|
12700
|
-
if (!
|
|
12904
|
+
if (!fs4.existsSync(HISTORY_DIR)) return;
|
|
12701
12905
|
const cutoff = Date.now() - RETAIN_DAYS * 24 * 60 * 60 * 1e3;
|
|
12702
|
-
const agentDirs =
|
|
12906
|
+
const agentDirs = fs4.readdirSync(HISTORY_DIR, { withFileTypes: true }).filter((d) => d.isDirectory());
|
|
12703
12907
|
for (const dir of agentDirs) {
|
|
12704
12908
|
const dirPath = path11.join(HISTORY_DIR, dir.name);
|
|
12705
|
-
const files =
|
|
12909
|
+
const files = fs4.readdirSync(dirPath).filter((f) => f.endsWith(".jsonl") || f.endsWith(".terminal.log"));
|
|
12706
12910
|
let removedAny = false;
|
|
12707
12911
|
for (const file of files) {
|
|
12708
12912
|
const filePath = path11.join(dirPath, file);
|
|
12709
|
-
const stat2 =
|
|
12913
|
+
const stat2 = fs4.statSync(filePath);
|
|
12710
12914
|
if (stat2.mtimeMs < cutoff) {
|
|
12711
|
-
|
|
12915
|
+
fs4.unlinkSync(filePath);
|
|
12712
12916
|
removedAny = true;
|
|
12713
12917
|
}
|
|
12714
12918
|
}
|
|
@@ -12756,13 +12960,13 @@ function readChatHistory(agentType, offset = 0, limit = 30, historySessionId, ex
|
|
|
12756
12960
|
try {
|
|
12757
12961
|
const sanitized = agentType.replace(/[^a-zA-Z0-9_-]/g, "_");
|
|
12758
12962
|
const dir = path11.join(HISTORY_DIR, sanitized);
|
|
12759
|
-
if (!
|
|
12963
|
+
if (!fs4.existsSync(dir)) return { messages: [], hasMore: false };
|
|
12760
12964
|
const files = listHistoryFiles(dir, historySessionId);
|
|
12761
12965
|
const allMessages = [];
|
|
12762
12966
|
const seen = /* @__PURE__ */ new Set();
|
|
12763
12967
|
for (const file of files) {
|
|
12764
12968
|
const filePath = path11.join(dir, file);
|
|
12765
|
-
const content =
|
|
12969
|
+
const content = fs4.readFileSync(filePath, "utf-8");
|
|
12766
12970
|
const lines = content.trim().split("\n").filter(Boolean);
|
|
12767
12971
|
for (let i = 0; i < lines.length; i++) {
|
|
12768
12972
|
try {
|
|
@@ -12786,7 +12990,7 @@ function listSavedHistorySessions(agentType, options = {}, historyBehavior) {
|
|
|
12786
12990
|
try {
|
|
12787
12991
|
const sanitized = agentType.replace(/[^a-zA-Z0-9_-]/g, "_");
|
|
12788
12992
|
const dir = path11.join(HISTORY_DIR, sanitized);
|
|
12789
|
-
if (!
|
|
12993
|
+
if (!fs4.existsSync(dir)) {
|
|
12790
12994
|
savedHistorySessionCache.delete(sanitized);
|
|
12791
12995
|
return { sessions: [], hasMore: false };
|
|
12792
12996
|
}
|
|
@@ -12847,10 +13051,10 @@ function listSavedHistorySessions(agentType, options = {}, historyBehavior) {
|
|
|
12847
13051
|
function readExistingSessionStartRecord(agentType, historySessionId) {
|
|
12848
13052
|
try {
|
|
12849
13053
|
const dir = path11.join(HISTORY_DIR, agentType);
|
|
12850
|
-
if (!
|
|
13054
|
+
if (!fs4.existsSync(dir)) return null;
|
|
12851
13055
|
const files = listHistoryFiles(dir, historySessionId).sort();
|
|
12852
13056
|
for (const file of files) {
|
|
12853
|
-
const lines =
|
|
13057
|
+
const lines = fs4.readFileSync(path11.join(dir, file), "utf-8").split("\n").filter(Boolean);
|
|
12854
13058
|
for (const line of lines) {
|
|
12855
13059
|
try {
|
|
12856
13060
|
const parsed = JSON.parse(line);
|
|
@@ -12871,16 +13075,16 @@ function rewriteCanonicalSavedHistory(agentType, historySessionId, records) {
|
|
|
12871
13075
|
if (records.length === 0) return false;
|
|
12872
13076
|
try {
|
|
12873
13077
|
const dir = path11.join(HISTORY_DIR, agentType);
|
|
12874
|
-
|
|
13078
|
+
fs4.mkdirSync(dir, { recursive: true });
|
|
12875
13079
|
const prefix = `${historySessionId.replace(/[^a-zA-Z0-9_-]/g, "_")}_`;
|
|
12876
|
-
for (const file of
|
|
13080
|
+
for (const file of fs4.readdirSync(dir)) {
|
|
12877
13081
|
if (file.startsWith(prefix) && file.endsWith(".jsonl")) {
|
|
12878
|
-
|
|
13082
|
+
fs4.unlinkSync(path11.join(dir, file));
|
|
12879
13083
|
}
|
|
12880
13084
|
}
|
|
12881
13085
|
const targetDate = new Date(records[records.length - 1].receivedAt || Date.now()).toISOString().slice(0, 10);
|
|
12882
13086
|
const filePath = path11.join(dir, `${prefix}${targetDate}.jsonl`);
|
|
12883
|
-
|
|
13087
|
+
fs4.writeFileSync(filePath, `${records.map((record) => JSON.stringify(record)).join("\n")}
|
|
12884
13088
|
`, "utf-8");
|
|
12885
13089
|
invalidatePersistedSavedHistoryIndex(agentType, dir);
|
|
12886
13090
|
savedHistorySessionCache.delete(agentType.replace(/[^a-zA-Z0-9_-]/g, "_"));
|
|
@@ -12988,7 +13192,7 @@ function buildNativeSessionSummary(agentType, historySessionId, records, sourceP
|
|
|
12988
13192
|
if (visible.length === 0) return null;
|
|
12989
13193
|
let sourceMtimeMs = 0;
|
|
12990
13194
|
try {
|
|
12991
|
-
sourceMtimeMs =
|
|
13195
|
+
sourceMtimeMs = fs4.statSync(sourcePath).mtimeMs;
|
|
12992
13196
|
} catch {
|
|
12993
13197
|
}
|
|
12994
13198
|
const firstMessageAt = visible[0]?.receivedAt || sourceMtimeMs || Date.now();
|
|
@@ -13761,6 +13965,19 @@ function formatAutoApprovalMessage(modalMessage, buttonLabel) {
|
|
|
13761
13965
|
}
|
|
13762
13966
|
|
|
13763
13967
|
// src/providers/ide-provider-instance.ts
|
|
13968
|
+
async function withTimeout(promise, timeoutMs, label) {
|
|
13969
|
+
let timer = null;
|
|
13970
|
+
try {
|
|
13971
|
+
return await Promise.race([
|
|
13972
|
+
promise,
|
|
13973
|
+
new Promise((_, reject) => {
|
|
13974
|
+
timer = setTimeout(() => reject(new Error(`${label} timed out after ${timeoutMs}ms`)), timeoutMs);
|
|
13975
|
+
})
|
|
13976
|
+
]);
|
|
13977
|
+
} finally {
|
|
13978
|
+
if (timer) clearTimeout(timer);
|
|
13979
|
+
}
|
|
13980
|
+
}
|
|
13764
13981
|
var IdeProviderInstance = class {
|
|
13765
13982
|
type;
|
|
13766
13983
|
category = "ide";
|
|
@@ -13985,7 +14202,7 @@ var IdeProviderInstance = class {
|
|
|
13985
14202
|
if (webviewScript) {
|
|
13986
14203
|
const matchText = this.provider.webviewMatchText;
|
|
13987
14204
|
const matchFn = matchText ? (body) => body.includes(matchText) : void 0;
|
|
13988
|
-
const webviewRaw = await cdp.evaluateInWebviewFrame(webviewScript, matchFn);
|
|
14205
|
+
const webviewRaw = await withTimeout(cdp.evaluateInWebviewFrame(webviewScript, matchFn), 3e4, "evaluateInWebviewFrame");
|
|
13989
14206
|
if (webviewRaw) {
|
|
13990
14207
|
raw = typeof webviewRaw === "string" ? (() => {
|
|
13991
14208
|
try {
|
|
@@ -14000,7 +14217,7 @@ var IdeProviderInstance = class {
|
|
|
14000
14217
|
if (!raw) {
|
|
14001
14218
|
const readChatScript = this.getReadChatScript();
|
|
14002
14219
|
if (!readChatScript) return;
|
|
14003
|
-
raw = await cdp.evaluate(readChatScript, 3e4);
|
|
14220
|
+
raw = await withTimeout(cdp.evaluate(readChatScript, 3e4), 3e4, "evaluate.readChatScript");
|
|
14004
14221
|
if (typeof raw === "string") {
|
|
14005
14222
|
try {
|
|
14006
14223
|
raw = JSON.parse(raw);
|
|
@@ -14311,7 +14528,7 @@ ${effect.notification.body || ""}`.trim();
|
|
|
14311
14528
|
now
|
|
14312
14529
|
);
|
|
14313
14530
|
LOG.info("IdeInstance", `[IdeInstance:${this.type}] autoApprove: executing resolveAction for "${targetButton}"`);
|
|
14314
|
-
let rawResult = await cdp.evaluate(script, 1e4);
|
|
14531
|
+
let rawResult = await withTimeout(cdp.evaluate(script, 1e4), 1e4, "evaluate.autoApprove");
|
|
14315
14532
|
if (typeof rawResult === "string") {
|
|
14316
14533
|
try {
|
|
14317
14534
|
rawResult = JSON.parse(rawResult);
|
|
@@ -15380,7 +15597,7 @@ function resolveLegacyProviderScript(fn, scriptName, params) {
|
|
|
15380
15597
|
}
|
|
15381
15598
|
|
|
15382
15599
|
// src/commands/chat-commands.ts
|
|
15383
|
-
var
|
|
15600
|
+
var fs5 = __toESM(require("fs"));
|
|
15384
15601
|
var os6 = __toESM(require("os"));
|
|
15385
15602
|
var path12 = __toESM(require("path"));
|
|
15386
15603
|
var import_node_crypto = require("crypto");
|
|
@@ -15953,11 +16170,11 @@ function buildChatDebugBundleSummary(bundle) {
|
|
|
15953
16170
|
function storeChatDebugBundleOnDaemon(bundle, targetSessionId) {
|
|
15954
16171
|
const bundleId = createChatDebugBundleId(targetSessionId);
|
|
15955
16172
|
const dir = getChatDebugBundleDir();
|
|
15956
|
-
|
|
16173
|
+
fs5.mkdirSync(dir, { recursive: true });
|
|
15957
16174
|
const savedPath = path12.join(dir, `${bundleId}.json`);
|
|
15958
16175
|
const json = `${JSON.stringify(bundle, null, 2)}
|
|
15959
16176
|
`;
|
|
15960
|
-
|
|
16177
|
+
fs5.writeFileSync(savedPath, json, { encoding: "utf8", mode: 384 });
|
|
15961
16178
|
return { bundleId, savedPath, sizeBytes: Buffer.byteLength(json, "utf8") };
|
|
15962
16179
|
}
|
|
15963
16180
|
function isDaemonFileDebugDelivery(args) {
|
|
@@ -17120,7 +17337,7 @@ async function handleResolveAction(h, args) {
|
|
|
17120
17337
|
}
|
|
17121
17338
|
|
|
17122
17339
|
// src/commands/cdp-commands.ts
|
|
17123
|
-
var
|
|
17340
|
+
var fs6 = __toESM(require("fs"));
|
|
17124
17341
|
var path13 = __toESM(require("path"));
|
|
17125
17342
|
var os7 = __toESM(require("os"));
|
|
17126
17343
|
var KEY_TO_VK = {
|
|
@@ -17393,7 +17610,7 @@ function resolveSafePath(requestedPath) {
|
|
|
17393
17610
|
return path13.resolve(inputPath);
|
|
17394
17611
|
}
|
|
17395
17612
|
function listDirectoryEntriesSafe(dirPath) {
|
|
17396
|
-
const entries =
|
|
17613
|
+
const entries = fs6.readdirSync(dirPath, { withFileTypes: true });
|
|
17397
17614
|
const files = [];
|
|
17398
17615
|
for (const entry of entries) {
|
|
17399
17616
|
const entryPath = path13.join(dirPath, entry.name);
|
|
@@ -17405,14 +17622,14 @@ function listDirectoryEntriesSafe(dirPath) {
|
|
|
17405
17622
|
if (entry.isFile()) {
|
|
17406
17623
|
let size;
|
|
17407
17624
|
try {
|
|
17408
|
-
size =
|
|
17625
|
+
size = fs6.statSync(entryPath).size;
|
|
17409
17626
|
} catch {
|
|
17410
17627
|
size = void 0;
|
|
17411
17628
|
}
|
|
17412
17629
|
files.push({ name: entry.name, type: "file", size });
|
|
17413
17630
|
continue;
|
|
17414
17631
|
}
|
|
17415
|
-
const stat2 =
|
|
17632
|
+
const stat2 = fs6.statSync(entryPath);
|
|
17416
17633
|
files.push({
|
|
17417
17634
|
name: entry.name,
|
|
17418
17635
|
type: stat2.isDirectory() ? "directory" : "file",
|
|
@@ -17430,7 +17647,7 @@ function listWindowsDriveEntries(excludePath) {
|
|
|
17430
17647
|
const letter = String.fromCharCode(code);
|
|
17431
17648
|
const root = `${letter}:\\`;
|
|
17432
17649
|
try {
|
|
17433
|
-
if (!
|
|
17650
|
+
if (!fs6.existsSync(root)) continue;
|
|
17434
17651
|
if (excluded && root.toLowerCase() === excluded) continue;
|
|
17435
17652
|
drives.push({ name: `${letter}:`, type: "directory", path: root });
|
|
17436
17653
|
} catch {
|
|
@@ -17441,7 +17658,7 @@ function listWindowsDriveEntries(excludePath) {
|
|
|
17441
17658
|
async function handleFileRead(h, args) {
|
|
17442
17659
|
try {
|
|
17443
17660
|
const filePath = resolveSafePath(args?.path);
|
|
17444
|
-
const content =
|
|
17661
|
+
const content = fs6.readFileSync(filePath, "utf-8");
|
|
17445
17662
|
return { success: true, content, path: filePath };
|
|
17446
17663
|
} catch (e) {
|
|
17447
17664
|
return { success: false, error: e.message };
|
|
@@ -17450,8 +17667,8 @@ async function handleFileRead(h, args) {
|
|
|
17450
17667
|
async function handleFileWrite(h, args) {
|
|
17451
17668
|
try {
|
|
17452
17669
|
const filePath = resolveSafePath(args?.path);
|
|
17453
|
-
|
|
17454
|
-
|
|
17670
|
+
fs6.mkdirSync(path13.dirname(filePath), { recursive: true });
|
|
17671
|
+
fs6.writeFileSync(filePath, args?.content || "", "utf-8");
|
|
17455
17672
|
return { success: true, path: filePath };
|
|
17456
17673
|
} catch (e) {
|
|
17457
17674
|
return { success: false, error: e.message };
|
|
@@ -18577,7 +18794,7 @@ var os13 = __toESM(require("os"));
|
|
|
18577
18794
|
var path18 = __toESM(require("path"));
|
|
18578
18795
|
var crypto4 = __toESM(require("crypto"));
|
|
18579
18796
|
var import_fs10 = require("fs");
|
|
18580
|
-
var
|
|
18797
|
+
var import_child_process5 = require("child_process");
|
|
18581
18798
|
var import_chalk = __toESM(require("chalk"));
|
|
18582
18799
|
init_provider_cli_adapter();
|
|
18583
18800
|
init_cli_detector();
|
|
@@ -18587,7 +18804,7 @@ init_config();
|
|
|
18587
18804
|
var os12 = __toESM(require("os"));
|
|
18588
18805
|
var path16 = __toESM(require("path"));
|
|
18589
18806
|
var crypto3 = __toESM(require("crypto"));
|
|
18590
|
-
var
|
|
18807
|
+
var fs7 = __toESM(require("fs"));
|
|
18591
18808
|
var import_node_module = require("module");
|
|
18592
18809
|
init_provider_cli_adapter();
|
|
18593
18810
|
init_logger();
|
|
@@ -18646,9 +18863,9 @@ function materializeImageDataPart(part, index, dir) {
|
|
|
18646
18863
|
if (!part.data) return null;
|
|
18647
18864
|
const rawData = part.data.includes(",") ? part.data.split(",").pop() || "" : part.data;
|
|
18648
18865
|
if (!rawData) return null;
|
|
18649
|
-
|
|
18866
|
+
fs7.mkdirSync(dir, { recursive: true });
|
|
18650
18867
|
const filePath = path16.join(dir, safeInputImageBasename(index, part.mimeType));
|
|
18651
|
-
|
|
18868
|
+
fs7.writeFileSync(filePath, Buffer.from(rawData, "base64"));
|
|
18652
18869
|
cleanupStaleMaterializedImages(dir);
|
|
18653
18870
|
return filePath;
|
|
18654
18871
|
}
|
|
@@ -18660,14 +18877,14 @@ function cleanupStaleMaterializedImages(dir) {
|
|
|
18660
18877
|
if (now - lastMaterializedImageCleanupAt < MATERIALIZED_IMAGE_CLEANUP_INTERVAL_MS) return;
|
|
18661
18878
|
lastMaterializedImageCleanupAt = now;
|
|
18662
18879
|
try {
|
|
18663
|
-
const entries =
|
|
18880
|
+
const entries = fs7.readdirSync(dir);
|
|
18664
18881
|
for (const entry of entries) {
|
|
18665
18882
|
if (!entry.startsWith("adhdev-input-image-")) continue;
|
|
18666
18883
|
const fullPath = path16.join(dir, entry);
|
|
18667
18884
|
try {
|
|
18668
|
-
const stat2 =
|
|
18885
|
+
const stat2 = fs7.statSync(fullPath);
|
|
18669
18886
|
if (now - stat2.mtimeMs > MATERIALIZED_IMAGE_MAX_AGE_MS) {
|
|
18670
|
-
|
|
18887
|
+
fs7.unlinkSync(fullPath);
|
|
18671
18888
|
}
|
|
18672
18889
|
} catch {
|
|
18673
18890
|
}
|
|
@@ -18906,7 +19123,7 @@ var CliProviderInstance = class {
|
|
|
18906
19123
|
const resolvedDbPath = probe.dbPath.replace(/^~/, os12.homedir());
|
|
18907
19124
|
const now = Date.now();
|
|
18908
19125
|
if (this.cachedSqliteDbMissingUntil > now) return null;
|
|
18909
|
-
if (!
|
|
19126
|
+
if (!fs7.existsSync(resolvedDbPath)) {
|
|
18910
19127
|
this.cachedSqliteDbMissingUntil = now + 1e4;
|
|
18911
19128
|
return null;
|
|
18912
19129
|
}
|
|
@@ -19822,7 +20039,7 @@ ${effect.notification.body || ""}`.trim();
|
|
|
19822
20039
|
};
|
|
19823
20040
|
addDir(this.workingDir);
|
|
19824
20041
|
try {
|
|
19825
|
-
addDir(
|
|
20042
|
+
addDir(fs7.realpathSync.native(this.workingDir));
|
|
19826
20043
|
} catch {
|
|
19827
20044
|
}
|
|
19828
20045
|
return Array.from(dirs);
|
|
@@ -19861,7 +20078,7 @@ ${effect.notification.body || ""}`.trim();
|
|
|
19861
20078
|
// src/providers/acp-provider-instance.ts
|
|
19862
20079
|
var path17 = __toESM(require("path"));
|
|
19863
20080
|
var import_stream = require("stream");
|
|
19864
|
-
var
|
|
20081
|
+
var import_child_process4 = require("child_process");
|
|
19865
20082
|
var import_sdk = require("@agentclientprotocol/sdk");
|
|
19866
20083
|
init_logger();
|
|
19867
20084
|
function getPromptCapabilityFlags(agentCapabilities) {
|
|
@@ -20378,7 +20595,7 @@ var AcpProviderInstance = class {
|
|
|
20378
20595
|
this.errorMessage = null;
|
|
20379
20596
|
this.errorReason = null;
|
|
20380
20597
|
this.stderrBuffer = [];
|
|
20381
|
-
this.process = (0,
|
|
20598
|
+
this.process = (0, import_child_process4.spawn)(command, args, {
|
|
20382
20599
|
cwd: this.workingDir,
|
|
20383
20600
|
env,
|
|
20384
20601
|
stdio: ["pipe", "pipe", "pipe"],
|
|
@@ -21105,7 +21322,7 @@ function commandExists(command) {
|
|
|
21105
21322
|
return (0, import_fs10.existsSync)(expandExecutable(trimmed));
|
|
21106
21323
|
}
|
|
21107
21324
|
try {
|
|
21108
|
-
(0,
|
|
21325
|
+
(0, import_child_process5.execFileSync)(process.platform === "win32" ? "where" : "which", [trimmed], {
|
|
21109
21326
|
stdio: "ignore",
|
|
21110
21327
|
...process.platform === "win32" ? { windowsHide: true } : {}
|
|
21111
21328
|
});
|
|
@@ -21914,13 +22131,13 @@ Run 'adhdev doctor' for detailed diagnostics.`
|
|
|
21914
22131
|
};
|
|
21915
22132
|
|
|
21916
22133
|
// src/launch.ts
|
|
21917
|
-
var
|
|
22134
|
+
var import_child_process6 = require("child_process");
|
|
21918
22135
|
var net = __toESM(require("net"));
|
|
21919
22136
|
var os15 = __toESM(require("os"));
|
|
21920
22137
|
var path20 = __toESM(require("path"));
|
|
21921
22138
|
|
|
21922
22139
|
// src/providers/provider-loader.ts
|
|
21923
|
-
var
|
|
22140
|
+
var fs8 = __toESM(require("fs"));
|
|
21924
22141
|
var path19 = __toESM(require("path"));
|
|
21925
22142
|
var os14 = __toESM(require("os"));
|
|
21926
22143
|
var chokidar = __toESM(require("chokidar"));
|
|
@@ -22273,9 +22490,9 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
22273
22490
|
static siblingStderrLogged = /* @__PURE__ */ new Set();
|
|
22274
22491
|
static looksLikeProviderRoot(candidate) {
|
|
22275
22492
|
try {
|
|
22276
|
-
if (!
|
|
22493
|
+
if (!fs8.existsSync(candidate) || !fs8.statSync(candidate).isDirectory()) return false;
|
|
22277
22494
|
return ["ide", "extension", "cli", "acp"].some(
|
|
22278
|
-
(category) =>
|
|
22495
|
+
(category) => fs8.existsSync(path19.join(candidate, category))
|
|
22279
22496
|
);
|
|
22280
22497
|
} catch {
|
|
22281
22498
|
return false;
|
|
@@ -22283,7 +22500,7 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
22283
22500
|
}
|
|
22284
22501
|
static hasProviderRootMarker(candidate) {
|
|
22285
22502
|
try {
|
|
22286
|
-
return
|
|
22503
|
+
return fs8.existsSync(path19.join(candidate, _ProviderLoader.SIBLING_MARKER_FILE));
|
|
22287
22504
|
} catch {
|
|
22288
22505
|
return false;
|
|
22289
22506
|
}
|
|
@@ -22445,7 +22662,7 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
22445
22662
|
this.providers.clear();
|
|
22446
22663
|
this.providerAvailability.clear();
|
|
22447
22664
|
let upstreamCount = 0;
|
|
22448
|
-
if (!this.disableUpstream &&
|
|
22665
|
+
if (!this.disableUpstream && fs8.existsSync(this.upstreamDir)) {
|
|
22449
22666
|
upstreamCount = this.loadDir(this.upstreamDir);
|
|
22450
22667
|
if (upstreamCount > 0) {
|
|
22451
22668
|
this.log(`Loaded ${upstreamCount} upstream providers (auto-updated)`);
|
|
@@ -22453,7 +22670,7 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
22453
22670
|
} else if (this.disableUpstream) {
|
|
22454
22671
|
this.log("Upstream loading disabled (sourceMode=no-upstream)");
|
|
22455
22672
|
}
|
|
22456
|
-
if (
|
|
22673
|
+
if (fs8.existsSync(this.userDir)) {
|
|
22457
22674
|
const userCount = this.loadDir(this.userDir, [".upstream"]);
|
|
22458
22675
|
if (userCount > 0) {
|
|
22459
22676
|
this.log(`Loaded ${userCount} user custom providers (never auto-updated)`);
|
|
@@ -22468,10 +22685,10 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
22468
22685
|
* Check if upstream directory exists and has providers.
|
|
22469
22686
|
*/
|
|
22470
22687
|
hasUpstream() {
|
|
22471
|
-
if (!
|
|
22688
|
+
if (!fs8.existsSync(this.upstreamDir)) return false;
|
|
22472
22689
|
try {
|
|
22473
|
-
return
|
|
22474
|
-
(d) =>
|
|
22690
|
+
return fs8.readdirSync(this.upstreamDir).some(
|
|
22691
|
+
(d) => fs8.statSync(path19.join(this.upstreamDir, d)).isDirectory()
|
|
22475
22692
|
);
|
|
22476
22693
|
} catch {
|
|
22477
22694
|
return false;
|
|
@@ -22969,7 +23186,7 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
22969
23186
|
resolved._resolvedScriptsSource = `compatibility:${entry.ideVersion}`;
|
|
22970
23187
|
if (providerDir) {
|
|
22971
23188
|
const fullDir = path19.join(providerDir, entry.scriptDir);
|
|
22972
|
-
resolved._resolvedScriptsPath =
|
|
23189
|
+
resolved._resolvedScriptsPath = fs8.existsSync(path19.join(fullDir, "scripts.js")) ? path19.join(fullDir, "scripts.js") : fullDir;
|
|
22973
23190
|
}
|
|
22974
23191
|
matched = true;
|
|
22975
23192
|
}
|
|
@@ -22985,7 +23202,7 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
22985
23202
|
resolved._resolvedScriptsSource = "defaultScriptDir:version_miss";
|
|
22986
23203
|
if (providerDir) {
|
|
22987
23204
|
const fullDir = path19.join(providerDir, base.defaultScriptDir);
|
|
22988
|
-
resolved._resolvedScriptsPath =
|
|
23205
|
+
resolved._resolvedScriptsPath = fs8.existsSync(path19.join(fullDir, "scripts.js")) ? path19.join(fullDir, "scripts.js") : fullDir;
|
|
22989
23206
|
}
|
|
22990
23207
|
}
|
|
22991
23208
|
resolved._versionWarning = `Version ${currentVersion} not in compatibility matrix. Using default scripts.`;
|
|
@@ -23003,7 +23220,7 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23003
23220
|
resolved._resolvedScriptsSource = `versions:${range}`;
|
|
23004
23221
|
if (providerDir) {
|
|
23005
23222
|
const fullDir = path19.join(providerDir, dirOverride);
|
|
23006
|
-
resolved._resolvedScriptsPath =
|
|
23223
|
+
resolved._resolvedScriptsPath = fs8.existsSync(path19.join(fullDir, "scripts.js")) ? path19.join(fullDir, "scripts.js") : fullDir;
|
|
23007
23224
|
}
|
|
23008
23225
|
}
|
|
23009
23226
|
} else if (override.scripts) {
|
|
@@ -23020,7 +23237,7 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23020
23237
|
resolved._resolvedScriptsSource = "defaultScriptDir:no_version";
|
|
23021
23238
|
if (providerDir) {
|
|
23022
23239
|
const fullDir = path19.join(providerDir, base.defaultScriptDir);
|
|
23023
|
-
resolved._resolvedScriptsPath =
|
|
23240
|
+
resolved._resolvedScriptsPath = fs8.existsSync(path19.join(fullDir, "scripts.js")) ? path19.join(fullDir, "scripts.js") : fullDir;
|
|
23024
23241
|
}
|
|
23025
23242
|
}
|
|
23026
23243
|
}
|
|
@@ -23053,14 +23270,14 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23053
23270
|
return null;
|
|
23054
23271
|
}
|
|
23055
23272
|
const dir = path19.join(providerDir, scriptDir);
|
|
23056
|
-
if (!
|
|
23273
|
+
if (!fs8.existsSync(dir)) {
|
|
23057
23274
|
this.log(` [loadScriptsFromDir] ${type}: dir not found: ${dir}`);
|
|
23058
23275
|
return null;
|
|
23059
23276
|
}
|
|
23060
23277
|
const cached = this.scriptsCache.get(dir);
|
|
23061
23278
|
if (cached) return cached;
|
|
23062
23279
|
const scriptsJs = path19.join(dir, "scripts.js");
|
|
23063
|
-
if (
|
|
23280
|
+
if (fs8.existsSync(scriptsJs)) {
|
|
23064
23281
|
try {
|
|
23065
23282
|
delete require.cache[require.resolve(scriptsJs)];
|
|
23066
23283
|
const loaded = require(scriptsJs);
|
|
@@ -23081,9 +23298,9 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23081
23298
|
watch() {
|
|
23082
23299
|
this.stopWatch();
|
|
23083
23300
|
const watchDir = (dir) => {
|
|
23084
|
-
if (!
|
|
23301
|
+
if (!fs8.existsSync(dir)) {
|
|
23085
23302
|
try {
|
|
23086
|
-
|
|
23303
|
+
fs8.mkdirSync(dir, { recursive: true });
|
|
23087
23304
|
} catch {
|
|
23088
23305
|
return;
|
|
23089
23306
|
}
|
|
@@ -23096,13 +23313,17 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23096
23313
|
ignoreInitial: true,
|
|
23097
23314
|
awaitWriteFinish: { stabilityThreshold: 200, pollInterval: 50 }
|
|
23098
23315
|
});
|
|
23316
|
+
let reloadTimer = null;
|
|
23099
23317
|
const handleChange = (filePath) => {
|
|
23100
23318
|
if (/[\/\\]fixtures[\/\\]/.test(filePath)) {
|
|
23101
23319
|
return;
|
|
23102
23320
|
}
|
|
23103
23321
|
if (filePath.endsWith(".js") || filePath.endsWith(".json")) {
|
|
23104
|
-
|
|
23105
|
-
|
|
23322
|
+
if (reloadTimer) clearTimeout(reloadTimer);
|
|
23323
|
+
reloadTimer = setTimeout(() => {
|
|
23324
|
+
this.log(`File changed: ${path19.basename(filePath)}, reloading...`);
|
|
23325
|
+
this.reload();
|
|
23326
|
+
}, 300);
|
|
23106
23327
|
}
|
|
23107
23328
|
};
|
|
23108
23329
|
watcher.on("add", handleChange).on("change", handleChange).on("unlink", handleChange);
|
|
@@ -23155,13 +23376,15 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23155
23376
|
return { updated: false };
|
|
23156
23377
|
}
|
|
23157
23378
|
const https = require("https");
|
|
23158
|
-
const {
|
|
23379
|
+
const { exec: exec7 } = require("child_process");
|
|
23380
|
+
const { promisify: promisify6 } = require("util");
|
|
23381
|
+
const execAsync5 = promisify6(exec7);
|
|
23159
23382
|
const metaPath = path19.join(this.upstreamDir, _ProviderLoader.META_FILE);
|
|
23160
23383
|
let prevEtag = "";
|
|
23161
23384
|
let prevTimestamp = 0;
|
|
23162
23385
|
try {
|
|
23163
|
-
if (
|
|
23164
|
-
const meta = JSON.parse(
|
|
23386
|
+
if (fs8.existsSync(metaPath)) {
|
|
23387
|
+
const meta = JSON.parse(fs8.readFileSync(metaPath, "utf-8"));
|
|
23165
23388
|
prevEtag = meta.etag || "";
|
|
23166
23389
|
prevTimestamp = meta.timestamp || 0;
|
|
23167
23390
|
}
|
|
@@ -23219,36 +23442,36 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23219
23442
|
const tmpTar = path19.join(os14.tmpdir(), `adhdev-providers-${Date.now()}.tar.gz`);
|
|
23220
23443
|
const tmpExtract = path19.join(os14.tmpdir(), `adhdev-providers-extract-${Date.now()}`);
|
|
23221
23444
|
await this.downloadFile(_ProviderLoader.GITHUB_TARBALL_URL, tmpTar);
|
|
23222
|
-
|
|
23223
|
-
|
|
23224
|
-
const extracted =
|
|
23445
|
+
fs8.mkdirSync(tmpExtract, { recursive: true });
|
|
23446
|
+
await execAsync5(`tar -xzf "${tmpTar}" -C "${tmpExtract}"`, { timeout: 3e4 });
|
|
23447
|
+
const extracted = fs8.readdirSync(tmpExtract);
|
|
23225
23448
|
const rootDir = extracted.find(
|
|
23226
|
-
(d) =>
|
|
23449
|
+
(d) => fs8.statSync(path19.join(tmpExtract, d)).isDirectory() && d.startsWith("adhdev-providers")
|
|
23227
23450
|
);
|
|
23228
23451
|
if (!rootDir) throw new Error("Unexpected tarball structure");
|
|
23229
23452
|
const sourceDir = path19.join(tmpExtract, rootDir);
|
|
23230
23453
|
const backupDir = this.upstreamDir + ".bak";
|
|
23231
|
-
if (
|
|
23232
|
-
if (
|
|
23233
|
-
|
|
23454
|
+
if (fs8.existsSync(this.upstreamDir)) {
|
|
23455
|
+
if (fs8.existsSync(backupDir)) fs8.rmSync(backupDir, { recursive: true, force: true });
|
|
23456
|
+
fs8.renameSync(this.upstreamDir, backupDir);
|
|
23234
23457
|
}
|
|
23235
23458
|
try {
|
|
23236
23459
|
this.copyDirRecursive(sourceDir, this.upstreamDir);
|
|
23237
23460
|
this.writeMeta(metaPath, etag || `ts-${Date.now()}`, Date.now());
|
|
23238
|
-
if (
|
|
23461
|
+
if (fs8.existsSync(backupDir)) fs8.rmSync(backupDir, { recursive: true, force: true });
|
|
23239
23462
|
} catch (e) {
|
|
23240
|
-
if (
|
|
23241
|
-
if (
|
|
23242
|
-
|
|
23463
|
+
if (fs8.existsSync(backupDir)) {
|
|
23464
|
+
if (fs8.existsSync(this.upstreamDir)) fs8.rmSync(this.upstreamDir, { recursive: true, force: true });
|
|
23465
|
+
fs8.renameSync(backupDir, this.upstreamDir);
|
|
23243
23466
|
}
|
|
23244
23467
|
throw e;
|
|
23245
23468
|
}
|
|
23246
23469
|
try {
|
|
23247
|
-
|
|
23470
|
+
fs8.rmSync(tmpTar, { force: true });
|
|
23248
23471
|
} catch {
|
|
23249
23472
|
}
|
|
23250
23473
|
try {
|
|
23251
|
-
|
|
23474
|
+
fs8.rmSync(tmpExtract, { recursive: true, force: true });
|
|
23252
23475
|
} catch {
|
|
23253
23476
|
}
|
|
23254
23477
|
const upstreamCount = this.countProviders(this.upstreamDir);
|
|
@@ -23280,7 +23503,7 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23280
23503
|
reject(new Error(`HTTP ${res.statusCode}`));
|
|
23281
23504
|
return;
|
|
23282
23505
|
}
|
|
23283
|
-
const ws =
|
|
23506
|
+
const ws = fs8.createWriteStream(destPath);
|
|
23284
23507
|
res.pipe(ws);
|
|
23285
23508
|
ws.on("finish", () => {
|
|
23286
23509
|
ws.close();
|
|
@@ -23299,22 +23522,22 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23299
23522
|
}
|
|
23300
23523
|
/** Recursive directory copy */
|
|
23301
23524
|
copyDirRecursive(src, dest) {
|
|
23302
|
-
|
|
23303
|
-
for (const entry of
|
|
23525
|
+
fs8.mkdirSync(dest, { recursive: true });
|
|
23526
|
+
for (const entry of fs8.readdirSync(src, { withFileTypes: true })) {
|
|
23304
23527
|
const srcPath = path19.join(src, entry.name);
|
|
23305
23528
|
const destPath = path19.join(dest, entry.name);
|
|
23306
23529
|
if (entry.isDirectory()) {
|
|
23307
23530
|
this.copyDirRecursive(srcPath, destPath);
|
|
23308
23531
|
} else {
|
|
23309
|
-
|
|
23532
|
+
fs8.copyFileSync(srcPath, destPath);
|
|
23310
23533
|
}
|
|
23311
23534
|
}
|
|
23312
23535
|
}
|
|
23313
23536
|
/** .meta.json save */
|
|
23314
23537
|
writeMeta(metaPath, etag, timestamp) {
|
|
23315
23538
|
try {
|
|
23316
|
-
|
|
23317
|
-
|
|
23539
|
+
fs8.mkdirSync(path19.dirname(metaPath), { recursive: true });
|
|
23540
|
+
fs8.writeFileSync(metaPath, JSON.stringify({
|
|
23318
23541
|
etag,
|
|
23319
23542
|
timestamp,
|
|
23320
23543
|
lastCheck: new Date(timestamp).toISOString(),
|
|
@@ -23325,11 +23548,11 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23325
23548
|
}
|
|
23326
23549
|
/** Count provider files (provider.js or provider.json) */
|
|
23327
23550
|
countProviders(dir) {
|
|
23328
|
-
if (!
|
|
23551
|
+
if (!fs8.existsSync(dir)) return 0;
|
|
23329
23552
|
let count = 0;
|
|
23330
23553
|
const scan = (d) => {
|
|
23331
23554
|
try {
|
|
23332
|
-
for (const entry of
|
|
23555
|
+
for (const entry of fs8.readdirSync(d, { withFileTypes: true })) {
|
|
23333
23556
|
if (entry.isDirectory()) scan(path19.join(d, entry.name));
|
|
23334
23557
|
else if (entry.name === "provider.json") count++;
|
|
23335
23558
|
}
|
|
@@ -23556,18 +23779,18 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23556
23779
|
const cat = provider.category;
|
|
23557
23780
|
const searchRoots = this.getProviderRoots();
|
|
23558
23781
|
for (const root of searchRoots) {
|
|
23559
|
-
if (!
|
|
23782
|
+
if (!fs8.existsSync(root)) continue;
|
|
23560
23783
|
const candidate = this.getProviderDir(root, cat, type);
|
|
23561
|
-
if (
|
|
23784
|
+
if (fs8.existsSync(path19.join(candidate, "provider.json"))) return candidate;
|
|
23562
23785
|
const catDir = path19.join(root, cat);
|
|
23563
|
-
if (
|
|
23786
|
+
if (fs8.existsSync(catDir)) {
|
|
23564
23787
|
try {
|
|
23565
|
-
for (const entry of
|
|
23788
|
+
for (const entry of fs8.readdirSync(catDir, { withFileTypes: true })) {
|
|
23566
23789
|
if (!entry.isDirectory()) continue;
|
|
23567
23790
|
const jsonPath = path19.join(catDir, entry.name, "provider.json");
|
|
23568
|
-
if (
|
|
23791
|
+
if (fs8.existsSync(jsonPath)) {
|
|
23569
23792
|
try {
|
|
23570
|
-
const data = JSON.parse(
|
|
23793
|
+
const data = JSON.parse(fs8.readFileSync(jsonPath, "utf-8"));
|
|
23571
23794
|
if (data.type === type) return path19.join(catDir, entry.name);
|
|
23572
23795
|
} catch {
|
|
23573
23796
|
}
|
|
@@ -23586,7 +23809,7 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23586
23809
|
*/
|
|
23587
23810
|
buildScriptWrappersFromDir(dir) {
|
|
23588
23811
|
const scriptsJs = path19.join(dir, "scripts.js");
|
|
23589
|
-
if (
|
|
23812
|
+
if (fs8.existsSync(scriptsJs)) {
|
|
23590
23813
|
try {
|
|
23591
23814
|
delete require.cache[require.resolve(scriptsJs)];
|
|
23592
23815
|
return require(scriptsJs);
|
|
@@ -23596,13 +23819,13 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23596
23819
|
const toCamel = (name) => name.replace(/_([a-z])/g, (_, c) => c.toUpperCase());
|
|
23597
23820
|
const result = {};
|
|
23598
23821
|
try {
|
|
23599
|
-
for (const file of
|
|
23822
|
+
for (const file of fs8.readdirSync(dir)) {
|
|
23600
23823
|
if (!file.endsWith(".js")) continue;
|
|
23601
23824
|
const scriptName = toCamel(file.replace(".js", ""));
|
|
23602
23825
|
const filePath = path19.join(dir, file);
|
|
23603
23826
|
result[scriptName] = (...args) => {
|
|
23604
23827
|
try {
|
|
23605
|
-
let content =
|
|
23828
|
+
let content = fs8.readFileSync(filePath, "utf-8");
|
|
23606
23829
|
if (args[0] && typeof args[0] === "object") {
|
|
23607
23830
|
for (const [key, val] of Object.entries(args[0])) {
|
|
23608
23831
|
let v = val;
|
|
@@ -23648,12 +23871,12 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23648
23871
|
* Structure: dir/category/agent-name/provider.{json,js}
|
|
23649
23872
|
*/
|
|
23650
23873
|
loadDir(dir, excludeDirs) {
|
|
23651
|
-
if (!
|
|
23874
|
+
if (!fs8.existsSync(dir)) return 0;
|
|
23652
23875
|
let count = 0;
|
|
23653
23876
|
const scan = (d) => {
|
|
23654
23877
|
let entries;
|
|
23655
23878
|
try {
|
|
23656
|
-
entries =
|
|
23879
|
+
entries = fs8.readdirSync(d, { withFileTypes: true });
|
|
23657
23880
|
} catch {
|
|
23658
23881
|
return;
|
|
23659
23882
|
}
|
|
@@ -23661,7 +23884,7 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23661
23884
|
if (hasJson) {
|
|
23662
23885
|
const jsonPath = path19.join(d, "provider.json");
|
|
23663
23886
|
try {
|
|
23664
|
-
const raw =
|
|
23887
|
+
const raw = fs8.readFileSync(jsonPath, "utf-8");
|
|
23665
23888
|
const mod = JSON.parse(raw);
|
|
23666
23889
|
if (typeof mod.extensionIdPattern === "string") {
|
|
23667
23890
|
const flags = mod.extensionIdPattern_flags || "";
|
|
@@ -23681,7 +23904,7 @@ var ProviderLoader = class _ProviderLoader {
|
|
|
23681
23904
|
} else {
|
|
23682
23905
|
const hasCompatibility = Array.isArray(normalizedProvider.compatibility);
|
|
23683
23906
|
const scriptsPath = path19.join(d, "scripts.js");
|
|
23684
|
-
if (!hasCompatibility &&
|
|
23907
|
+
if (!hasCompatibility && fs8.existsSync(scriptsPath)) {
|
|
23685
23908
|
try {
|
|
23686
23909
|
delete require.cache[require.resolve(scriptsPath)];
|
|
23687
23910
|
const scripts = require(scriptsPath);
|
|
@@ -23786,6 +24009,14 @@ function findMacAppProcessPids(psOutput, appPaths) {
|
|
|
23786
24009
|
}
|
|
23787
24010
|
|
|
23788
24011
|
// src/launch.ts
|
|
24012
|
+
async function execQuiet(command, options = {}) {
|
|
24013
|
+
return new Promise((resolve16) => {
|
|
24014
|
+
(0, import_child_process6.exec)(command, options, (error, stdout) => {
|
|
24015
|
+
if (error) return resolve16("");
|
|
24016
|
+
resolve16(stdout.toString());
|
|
24017
|
+
});
|
|
24018
|
+
});
|
|
24019
|
+
}
|
|
23789
24020
|
var _providerLoader = null;
|
|
23790
24021
|
function getProviderLoader() {
|
|
23791
24022
|
if (!_providerLoader) {
|
|
@@ -23824,11 +24055,11 @@ function escapeForAppleScript(value) {
|
|
|
23824
24055
|
function getIdePathCandidates(ideId) {
|
|
23825
24056
|
return getProviderLoader().getIdePathCandidates(ideId);
|
|
23826
24057
|
}
|
|
23827
|
-
function getMacAppProcessPids(ideId) {
|
|
24058
|
+
async function getMacAppProcessPids(ideId) {
|
|
23828
24059
|
const appPaths = getIdePathCandidates(ideId);
|
|
23829
24060
|
if (appPaths.length === 0) return [];
|
|
23830
24061
|
try {
|
|
23831
|
-
const output =
|
|
24062
|
+
const output = await execQuiet("ps axww -o pid=,args=", {
|
|
23832
24063
|
encoding: "utf-8",
|
|
23833
24064
|
timeout: 3e3,
|
|
23834
24065
|
stdio: ["pipe", "pipe", "pipe"]
|
|
@@ -23838,8 +24069,8 @@ function getMacAppProcessPids(ideId) {
|
|
|
23838
24069
|
return [];
|
|
23839
24070
|
}
|
|
23840
24071
|
}
|
|
23841
|
-
function killMacAppPathProcesses(ideId, signal) {
|
|
23842
|
-
const pids = getMacAppProcessPids(ideId);
|
|
24072
|
+
async function killMacAppPathProcesses(ideId, signal) {
|
|
24073
|
+
const pids = await getMacAppProcessPids(ideId);
|
|
23843
24074
|
let signalled = false;
|
|
23844
24075
|
for (const pid of pids) {
|
|
23845
24076
|
try {
|
|
@@ -23902,68 +24133,68 @@ async function killIdeProcess(ideId) {
|
|
|
23902
24133
|
try {
|
|
23903
24134
|
if (plat === "darwin" && appName) {
|
|
23904
24135
|
try {
|
|
23905
|
-
|
|
24136
|
+
await execQuiet(`osascript -e 'tell application "${escapeForAppleScript(appName)}" to quit' 2>/dev/null`, {
|
|
23906
24137
|
timeout: 5e3
|
|
23907
24138
|
});
|
|
23908
24139
|
} catch {
|
|
23909
24140
|
try {
|
|
23910
|
-
|
|
24141
|
+
await execQuiet(`pkill -x "${appName}" 2>/dev/null`, { timeout: 5e3 });
|
|
23911
24142
|
} catch {
|
|
23912
24143
|
}
|
|
23913
24144
|
}
|
|
23914
|
-
killMacAppPathProcesses(ideId, "SIGTERM");
|
|
24145
|
+
await killMacAppPathProcesses(ideId, "SIGTERM");
|
|
23915
24146
|
} else if (plat === "win32" && winProcesses) {
|
|
23916
24147
|
for (const proc of winProcesses) {
|
|
23917
24148
|
try {
|
|
23918
|
-
|
|
24149
|
+
await execQuiet(`taskkill /IM "${proc}" /F 2>nul`, { timeout: 5e3 });
|
|
23919
24150
|
} catch {
|
|
23920
24151
|
}
|
|
23921
24152
|
}
|
|
23922
24153
|
try {
|
|
23923
24154
|
const exeName = winProcesses[0].replace(".exe", "");
|
|
23924
|
-
|
|
24155
|
+
await execQuiet(`powershell -Command "Get-Process -Name '${exeName}' -ErrorAction SilentlyContinue | Stop-Process -Force"`, {
|
|
23925
24156
|
timeout: 1e4
|
|
23926
24157
|
});
|
|
23927
24158
|
} catch {
|
|
23928
24159
|
}
|
|
23929
24160
|
} else {
|
|
23930
24161
|
try {
|
|
23931
|
-
|
|
24162
|
+
await execQuiet(`pkill -f "${ideId}" 2>/dev/null`);
|
|
23932
24163
|
} catch {
|
|
23933
24164
|
}
|
|
23934
24165
|
}
|
|
23935
24166
|
for (let i = 0; i < 30; i++) {
|
|
23936
24167
|
await new Promise((r) => setTimeout(r, 500));
|
|
23937
|
-
if (!isIdeRunning(ideId)) return true;
|
|
24168
|
+
if (!await isIdeRunning(ideId)) return true;
|
|
23938
24169
|
}
|
|
23939
24170
|
if (plat === "darwin" && appName) {
|
|
23940
24171
|
try {
|
|
23941
|
-
|
|
24172
|
+
await execQuiet(`pkill -9 -x "${appName}" 2>/dev/null`, { timeout: 5e3 });
|
|
23942
24173
|
} catch {
|
|
23943
24174
|
}
|
|
23944
|
-
killMacAppPathProcesses(ideId, "SIGKILL");
|
|
24175
|
+
await killMacAppPathProcesses(ideId, "SIGKILL");
|
|
23945
24176
|
} else if (plat === "win32" && winProcesses) {
|
|
23946
24177
|
for (const proc of winProcesses) {
|
|
23947
24178
|
try {
|
|
23948
|
-
|
|
24179
|
+
await execQuiet(`taskkill /IM "${proc}" /F 2>nul`);
|
|
23949
24180
|
} catch {
|
|
23950
24181
|
}
|
|
23951
24182
|
}
|
|
23952
24183
|
}
|
|
23953
24184
|
await new Promise((r) => setTimeout(r, 2e3));
|
|
23954
|
-
return !isIdeRunning(ideId);
|
|
24185
|
+
return !await isIdeRunning(ideId);
|
|
23955
24186
|
} catch {
|
|
23956
24187
|
return false;
|
|
23957
24188
|
}
|
|
23958
24189
|
}
|
|
23959
|
-
function isIdeRunning(ideId) {
|
|
24190
|
+
async function isIdeRunning(ideId) {
|
|
23960
24191
|
const plat = os15.platform();
|
|
23961
24192
|
try {
|
|
23962
24193
|
if (plat === "darwin") {
|
|
23963
24194
|
const appName = getMacAppIdentifiers()[ideId];
|
|
23964
|
-
if (!appName) return getMacAppProcessPids(ideId).length > 0;
|
|
24195
|
+
if (!appName) return (await getMacAppProcessPids(ideId)).length > 0;
|
|
23965
24196
|
try {
|
|
23966
|
-
const result =
|
|
24197
|
+
const result = await execQuiet(`pgrep -x "${appName}" 2>/dev/null`, {
|
|
23967
24198
|
encoding: "utf-8",
|
|
23968
24199
|
timeout: 3e3
|
|
23969
24200
|
});
|
|
@@ -23971,7 +24202,7 @@ function isIdeRunning(ideId) {
|
|
|
23971
24202
|
} catch {
|
|
23972
24203
|
}
|
|
23973
24204
|
try {
|
|
23974
|
-
const result =
|
|
24205
|
+
const result = await execQuiet(
|
|
23975
24206
|
`osascript -e 'tell application "System Events" to count (every process whose name is "${escapeForAppleScript(appName)}")'`,
|
|
23976
24207
|
{
|
|
23977
24208
|
encoding: "utf-8",
|
|
@@ -23982,20 +24213,20 @@ function isIdeRunning(ideId) {
|
|
|
23982
24213
|
if (Number.parseInt(result.trim() || "0", 10) > 0) return true;
|
|
23983
24214
|
} catch {
|
|
23984
24215
|
}
|
|
23985
|
-
return getMacAppProcessPids(ideId).length > 0;
|
|
24216
|
+
return (await getMacAppProcessPids(ideId)).length > 0;
|
|
23986
24217
|
} else if (plat === "win32") {
|
|
23987
24218
|
const winProcesses = getWinProcessNames()[ideId];
|
|
23988
24219
|
if (!winProcesses) return false;
|
|
23989
24220
|
for (const proc of winProcesses) {
|
|
23990
24221
|
try {
|
|
23991
|
-
const result =
|
|
24222
|
+
const result = await execQuiet(`tasklist /FI "IMAGENAME eq ${proc}" /NH 2>nul`, { encoding: "utf-8" });
|
|
23992
24223
|
if (result.includes(proc)) return true;
|
|
23993
24224
|
} catch {
|
|
23994
24225
|
}
|
|
23995
24226
|
}
|
|
23996
24227
|
try {
|
|
23997
24228
|
const exeName = winProcesses[0].replace(".exe", "");
|
|
23998
|
-
const result =
|
|
24229
|
+
const result = await execQuiet(
|
|
23999
24230
|
`powershell -Command "(Get-Process -Name '${exeName}' -ErrorAction SilentlyContinue).Count"`,
|
|
24000
24231
|
{ encoding: "utf-8", timeout: 5e3 }
|
|
24001
24232
|
);
|
|
@@ -24004,20 +24235,20 @@ function isIdeRunning(ideId) {
|
|
|
24004
24235
|
}
|
|
24005
24236
|
return false;
|
|
24006
24237
|
} else {
|
|
24007
|
-
const result =
|
|
24238
|
+
const result = await execQuiet(`pgrep -f "${ideId}" 2>/dev/null`, { encoding: "utf-8" });
|
|
24008
24239
|
return result.trim().length > 0;
|
|
24009
24240
|
}
|
|
24010
24241
|
} catch {
|
|
24011
24242
|
return false;
|
|
24012
24243
|
}
|
|
24013
24244
|
}
|
|
24014
|
-
function detectCurrentWorkspace(ideId) {
|
|
24245
|
+
async function detectCurrentWorkspace(ideId) {
|
|
24015
24246
|
const plat = os15.platform();
|
|
24016
24247
|
if (plat === "darwin") {
|
|
24017
24248
|
try {
|
|
24018
24249
|
const appName = getMacAppIdentifiers()[ideId];
|
|
24019
24250
|
if (!appName) return void 0;
|
|
24020
|
-
const result =
|
|
24251
|
+
const result = await execQuiet(
|
|
24021
24252
|
`lsof -c "${appName}" 2>/dev/null | grep cwd | head -1 | awk '{print $NF}'`,
|
|
24022
24253
|
{ encoding: "utf-8", timeout: 3e3 }
|
|
24023
24254
|
);
|
|
@@ -24027,7 +24258,7 @@ function detectCurrentWorkspace(ideId) {
|
|
|
24027
24258
|
}
|
|
24028
24259
|
} else if (plat === "win32") {
|
|
24029
24260
|
try {
|
|
24030
|
-
const
|
|
24261
|
+
const fs17 = require("fs");
|
|
24031
24262
|
const appNameMap = getMacAppIdentifiers();
|
|
24032
24263
|
const appName = appNameMap[ideId];
|
|
24033
24264
|
if (appName) {
|
|
@@ -24036,8 +24267,8 @@ function detectCurrentWorkspace(ideId) {
|
|
|
24036
24267
|
appName,
|
|
24037
24268
|
"storage.json"
|
|
24038
24269
|
);
|
|
24039
|
-
if (
|
|
24040
|
-
const data = JSON.parse(
|
|
24270
|
+
if (fs17.existsSync(storagePath)) {
|
|
24271
|
+
const data = JSON.parse(fs17.readFileSync(storagePath, "utf-8"));
|
|
24041
24272
|
const workspaces = data?.openedPathsList?.workspaces3 || data?.openedPathsList?.entries || [];
|
|
24042
24273
|
if (workspaces.length > 0) {
|
|
24043
24274
|
const recent = workspaces[0];
|
|
@@ -24104,8 +24335,8 @@ async function launchWithCdp(options = {}) {
|
|
|
24104
24335
|
};
|
|
24105
24336
|
}
|
|
24106
24337
|
}
|
|
24107
|
-
const alreadyRunning = isIdeRunning(targetIde.id);
|
|
24108
|
-
const workspace = options.workspace || (alreadyRunning ? detectCurrentWorkspace(targetIde.id) : void 0);
|
|
24338
|
+
const alreadyRunning = await isIdeRunning(targetIde.id);
|
|
24339
|
+
const workspace = options.workspace || (alreadyRunning ? await detectCurrentWorkspace(targetIde.id) : void 0);
|
|
24109
24340
|
if (alreadyRunning) {
|
|
24110
24341
|
const killed = await killIdeProcess(targetIde.id);
|
|
24111
24342
|
if (!killed) {
|
|
@@ -24180,10 +24411,10 @@ async function launchMacOS(ide, port, workspace, newWindow) {
|
|
|
24180
24411
|
const canUseAppLauncher = !!appName;
|
|
24181
24412
|
const useAppLauncher = preferredMethod === "app" ? canUseAppLauncher : preferredMethod === "cli" ? false : !canUseCli && canUseAppLauncher;
|
|
24182
24413
|
if (!useAppLauncher && ide.cliCommand) {
|
|
24183
|
-
(0,
|
|
24414
|
+
(0, import_child_process6.spawn)(ide.cliCommand, args, { detached: true, stdio: "ignore", windowsHide: true }).unref();
|
|
24184
24415
|
} else if (appName) {
|
|
24185
24416
|
const openArgs = ["-a", appName, "--args", ...args];
|
|
24186
|
-
(0,
|
|
24417
|
+
(0, import_child_process6.spawn)("open", openArgs, { detached: true, stdio: "ignore" }).unref();
|
|
24187
24418
|
} else {
|
|
24188
24419
|
throw new Error(`No app identifier or CLI for ${ide.displayName}`);
|
|
24189
24420
|
}
|
|
@@ -24209,7 +24440,7 @@ async function launchLinux(ide, port, workspace, newWindow) {
|
|
|
24209
24440
|
const args = ["--remote-debugging-port=" + port];
|
|
24210
24441
|
if (newWindow) args.push("--new-window");
|
|
24211
24442
|
if (workspace) args.push(workspace);
|
|
24212
|
-
(0,
|
|
24443
|
+
(0, import_child_process6.spawn)(cli, args, { detached: true, stdio: "ignore", windowsHide: true }).unref();
|
|
24213
24444
|
}
|
|
24214
24445
|
function getAvailableIdeIds() {
|
|
24215
24446
|
return getProviderLoader().getAvailableIdeTypes();
|
|
@@ -24221,14 +24452,14 @@ init_cli_detector();
|
|
|
24221
24452
|
init_logger();
|
|
24222
24453
|
|
|
24223
24454
|
// src/logging/command-log.ts
|
|
24224
|
-
var
|
|
24455
|
+
var fs9 = __toESM(require("fs"));
|
|
24225
24456
|
var path21 = __toESM(require("path"));
|
|
24226
24457
|
var os16 = __toESM(require("os"));
|
|
24227
24458
|
var LOG_DIR2 = process.platform === "win32" ? path21.join(process.env.LOCALAPPDATA || process.env.APPDATA || path21.join(os16.homedir(), "AppData", "Local"), "adhdev", "logs") : process.platform === "darwin" ? path21.join(os16.homedir(), "Library", "Logs", "adhdev") : path21.join(os16.homedir(), ".local", "share", "adhdev", "logs");
|
|
24228
24459
|
var MAX_FILE_SIZE = 5 * 1024 * 1024;
|
|
24229
24460
|
var MAX_DAYS = 7;
|
|
24230
24461
|
try {
|
|
24231
|
-
|
|
24462
|
+
fs9.mkdirSync(LOG_DIR2, { recursive: true });
|
|
24232
24463
|
} catch {
|
|
24233
24464
|
}
|
|
24234
24465
|
var SENSITIVE_KEYS = /* @__PURE__ */ new Set([
|
|
@@ -24274,7 +24505,7 @@ function checkRotation() {
|
|
|
24274
24505
|
}
|
|
24275
24506
|
function cleanOldFiles() {
|
|
24276
24507
|
try {
|
|
24277
|
-
const files =
|
|
24508
|
+
const files = fs9.readdirSync(LOG_DIR2).filter((f) => f.startsWith("commands-") && f.endsWith(".jsonl"));
|
|
24278
24509
|
const cutoff = /* @__PURE__ */ new Date();
|
|
24279
24510
|
cutoff.setDate(cutoff.getDate() - MAX_DAYS);
|
|
24280
24511
|
const cutoffStr = cutoff.toISOString().slice(0, 10);
|
|
@@ -24282,7 +24513,7 @@ function cleanOldFiles() {
|
|
|
24282
24513
|
const dateMatch = file.match(/commands-(\d{4}-\d{2}-\d{2})/);
|
|
24283
24514
|
if (dateMatch && dateMatch[1] < cutoffStr) {
|
|
24284
24515
|
try {
|
|
24285
|
-
|
|
24516
|
+
fs9.unlinkSync(path21.join(LOG_DIR2, file));
|
|
24286
24517
|
} catch {
|
|
24287
24518
|
}
|
|
24288
24519
|
}
|
|
@@ -24292,14 +24523,14 @@ function cleanOldFiles() {
|
|
|
24292
24523
|
}
|
|
24293
24524
|
function checkSize() {
|
|
24294
24525
|
try {
|
|
24295
|
-
const stat2 =
|
|
24526
|
+
const stat2 = fs9.statSync(currentFile);
|
|
24296
24527
|
if (stat2.size > MAX_FILE_SIZE) {
|
|
24297
24528
|
const backup = currentFile.replace(".jsonl", ".1.jsonl");
|
|
24298
24529
|
try {
|
|
24299
|
-
|
|
24530
|
+
fs9.unlinkSync(backup);
|
|
24300
24531
|
} catch {
|
|
24301
24532
|
}
|
|
24302
|
-
|
|
24533
|
+
fs9.renameSync(currentFile, backup);
|
|
24303
24534
|
}
|
|
24304
24535
|
} catch {
|
|
24305
24536
|
}
|
|
@@ -24332,14 +24563,14 @@ function logCommand(entry) {
|
|
|
24332
24563
|
...entry.error ? { err: entry.error } : {},
|
|
24333
24564
|
...entry.durationMs !== void 0 ? { ms: entry.durationMs } : {}
|
|
24334
24565
|
});
|
|
24335
|
-
|
|
24566
|
+
fs9.appendFileSync(currentFile, line + "\n");
|
|
24336
24567
|
} catch {
|
|
24337
24568
|
}
|
|
24338
24569
|
}
|
|
24339
24570
|
function getRecentCommands(count = 50) {
|
|
24340
24571
|
try {
|
|
24341
|
-
if (!
|
|
24342
|
-
const content =
|
|
24572
|
+
if (!fs9.existsSync(currentFile)) return [];
|
|
24573
|
+
const content = fs9.readFileSync(currentFile, "utf-8");
|
|
24343
24574
|
const lines = content.trim().split("\n").filter(Boolean);
|
|
24344
24575
|
return lines.slice(-count).map((line) => {
|
|
24345
24576
|
try {
|
|
@@ -24369,14 +24600,11 @@ var yaml2 = __toESM(require("js-yaml"));
|
|
|
24369
24600
|
init_logger();
|
|
24370
24601
|
|
|
24371
24602
|
// src/commands/mesh-coordinator.ts
|
|
24372
|
-
var import_node_child_process3 = require("child_process");
|
|
24373
24603
|
var import_node_crypto2 = require("crypto");
|
|
24374
|
-
var import_node_fs3 = require("fs");
|
|
24375
|
-
var import_node_module2 = require("module");
|
|
24376
24604
|
var os17 = __toESM(require("os"));
|
|
24377
24605
|
var import_node_path = require("path");
|
|
24378
24606
|
var DEFAULT_SERVER_NAME = "adhdev-mesh";
|
|
24379
|
-
var DEFAULT_ADHDEV_MCP_COMMAND = "adhdev
|
|
24607
|
+
var DEFAULT_ADHDEV_MCP_COMMAND = "adhdev";
|
|
24380
24608
|
var HERMES_CLI_TYPE = "hermes-cli";
|
|
24381
24609
|
var HERMES_MCP_CONFIG_PATH = "~/.hermes/config.yaml";
|
|
24382
24610
|
function isHermesProvider(provider, cliType) {
|
|
@@ -24386,8 +24614,7 @@ function isHermesProvider(provider, cliType) {
|
|
|
24386
24614
|
function resolveHermesMeshCoordinatorSetup(options) {
|
|
24387
24615
|
const mcpServer = resolveAdhdevMcpServerLaunch({
|
|
24388
24616
|
meshId: options.meshId,
|
|
24389
|
-
|
|
24390
|
-
adhdevMcpEntryPath: options.adhdevMcpEntryPath,
|
|
24617
|
+
adhdevMcpCommand: options.adhdevMcpCommand,
|
|
24391
24618
|
adhdevMcpTransport: options.adhdevMcpTransport,
|
|
24392
24619
|
adhdevMcpPort: options.adhdevMcpPort
|
|
24393
24620
|
});
|
|
@@ -24418,7 +24645,7 @@ function createHermesManualMeshCoordinatorSetup(meshId, workspace) {
|
|
|
24418
24645
|
requiresRestart: true,
|
|
24419
24646
|
instructions: "Hermes CLI does not auto-import repo-local .mcp.json. Add this MCP server to Hermes config under mcp_servers, then start a fresh Hermes session.",
|
|
24420
24647
|
template: renderMeshCoordinatorTemplate(
|
|
24421
|
-
"mcp_servers:\n {{serverName}}:\n command: {{adhdevMcpCommand}}\n args:\n - --repo-mesh\n - {{meshId}}\n enabled: true\n",
|
|
24648
|
+
"mcp_servers:\n {{serverName}}:\n command: {{adhdevMcpCommand}}\n args:\n - mcp\n - --mode\n - ipc\n - --repo-mesh\n - {{meshId}}\n enabled: true\n",
|
|
24422
24649
|
{
|
|
24423
24650
|
meshId,
|
|
24424
24651
|
workspace,
|
|
@@ -24455,8 +24682,7 @@ function resolveMeshCoordinatorSetup(options) {
|
|
|
24455
24682
|
}
|
|
24456
24683
|
const mcpServer = resolveAdhdevMcpServerLaunch({
|
|
24457
24684
|
meshId,
|
|
24458
|
-
|
|
24459
|
-
adhdevMcpEntryPath: options.adhdevMcpEntryPath,
|
|
24685
|
+
adhdevMcpCommand: options.adhdevMcpCommand,
|
|
24460
24686
|
adhdevMcpTransport: options.adhdevMcpTransport,
|
|
24461
24687
|
adhdevMcpPort: options.adhdevMcpPort
|
|
24462
24688
|
});
|
|
@@ -24528,19 +24754,19 @@ function resolveMcpConfigPath(configPath, workspace) {
|
|
|
24528
24754
|
return (0, import_node_path.join)(workspace, trimmed);
|
|
24529
24755
|
}
|
|
24530
24756
|
function resolveAdhdevMcpServerLaunch(options) {
|
|
24531
|
-
const
|
|
24532
|
-
if (!entryPath) return null;
|
|
24533
|
-
const nodeExecutable = resolveMcpNodeExecutable(options.nodeExecutable);
|
|
24534
|
-
if (!nodeExecutable) return null;
|
|
24757
|
+
const command = resolveAdhdevCommand(options.adhdevMcpCommand);
|
|
24535
24758
|
const transport = resolveMcpTransport(options.adhdevMcpTransport);
|
|
24536
|
-
const args = [
|
|
24759
|
+
const args = ["mcp", "--mode", transport, "--repo-mesh", options.meshId];
|
|
24537
24760
|
const port = resolveMcpPort(options.adhdevMcpPort);
|
|
24538
24761
|
if (port !== void 0) args.push("--port", String(port));
|
|
24539
24762
|
return {
|
|
24540
|
-
command
|
|
24763
|
+
command,
|
|
24541
24764
|
args
|
|
24542
24765
|
};
|
|
24543
24766
|
}
|
|
24767
|
+
function resolveAdhdevCommand(explicitCommand) {
|
|
24768
|
+
return explicitCommand?.trim() || process.env.ADHDEV_COORDINATOR_MCP_COMMAND?.trim() || DEFAULT_ADHDEV_MCP_COMMAND;
|
|
24769
|
+
}
|
|
24544
24770
|
function resolveMcpTransport(explicitTransport) {
|
|
24545
24771
|
if (explicitTransport === "local" || explicitTransport === "ipc") return explicitTransport;
|
|
24546
24772
|
const envTransport = process.env.ADHDEV_COORDINATOR_MCP_TRANSPORT?.trim();
|
|
@@ -24553,109 +24779,6 @@ function resolveMcpPort(explicitPort) {
|
|
|
24553
24779
|
const parsed = Number(raw);
|
|
24554
24780
|
return Number.isInteger(parsed) && parsed > 0 ? parsed : void 0;
|
|
24555
24781
|
}
|
|
24556
|
-
function resolveMcpNodeExecutable(explicitExecutable) {
|
|
24557
|
-
const explicit = explicitExecutable?.trim();
|
|
24558
|
-
if (explicit) return explicit;
|
|
24559
|
-
const candidates = [];
|
|
24560
|
-
const addCandidate = (candidate) => {
|
|
24561
|
-
const trimmed = candidate?.trim();
|
|
24562
|
-
if (!trimmed) return;
|
|
24563
|
-
const normalized = normalizeExistingPath(trimmed) || trimmed;
|
|
24564
|
-
if (!candidates.includes(normalized)) candidates.push(normalized);
|
|
24565
|
-
};
|
|
24566
|
-
addCandidate(process.env.ADHDEV_MCP_NODE_EXECUTABLE);
|
|
24567
|
-
addCandidate(process.env.ADHDEV_NODE_EXECUTABLE);
|
|
24568
|
-
addCandidate(process.env.npm_node_execpath);
|
|
24569
|
-
addNodeCandidatesFromPath(process.env.PATH, addCandidate);
|
|
24570
|
-
addNodeCandidatesFromNvm(os17.homedir(), addCandidate);
|
|
24571
|
-
addCandidate("/opt/homebrew/bin/node");
|
|
24572
|
-
addCandidate("/usr/local/bin/node");
|
|
24573
|
-
addCandidate("/usr/bin/node");
|
|
24574
|
-
addCandidate(process.execPath);
|
|
24575
|
-
for (const candidate of candidates) {
|
|
24576
|
-
if (nodeRuntimeSupportsWebSocket(candidate)) return candidate;
|
|
24577
|
-
}
|
|
24578
|
-
return null;
|
|
24579
|
-
}
|
|
24580
|
-
function addNodeCandidatesFromPath(pathValue, addCandidate) {
|
|
24581
|
-
for (const entry of (pathValue || "").split(":")) {
|
|
24582
|
-
const dir = entry.trim();
|
|
24583
|
-
if (!dir) continue;
|
|
24584
|
-
addCandidate((0, import_node_path.join)(dir, "node"));
|
|
24585
|
-
}
|
|
24586
|
-
}
|
|
24587
|
-
function addNodeCandidatesFromNvm(homeDir, addCandidate) {
|
|
24588
|
-
const versionsDir = (0, import_node_path.join)(homeDir, ".nvm", "versions", "node");
|
|
24589
|
-
try {
|
|
24590
|
-
const versionDirs = (0, import_node_fs3.readdirSync)(versionsDir, { withFileTypes: true }).filter((entry) => entry.isDirectory()).map((entry) => entry.name).sort(compareNodeVersionNamesDescending);
|
|
24591
|
-
for (const versionDir of versionDirs) {
|
|
24592
|
-
addCandidate((0, import_node_path.join)(versionsDir, versionDir, "bin", "node"));
|
|
24593
|
-
}
|
|
24594
|
-
} catch {
|
|
24595
|
-
}
|
|
24596
|
-
}
|
|
24597
|
-
function compareNodeVersionNamesDescending(a, b) {
|
|
24598
|
-
const parse = (value) => value.replace(/^v/, "").split(".").map((part) => Number.parseInt(part, 10) || 0);
|
|
24599
|
-
const left = parse(a);
|
|
24600
|
-
const right = parse(b);
|
|
24601
|
-
for (let i = 0; i < Math.max(left.length, right.length); i++) {
|
|
24602
|
-
const diff = (right[i] || 0) - (left[i] || 0);
|
|
24603
|
-
if (diff !== 0) return diff;
|
|
24604
|
-
}
|
|
24605
|
-
return b.localeCompare(a);
|
|
24606
|
-
}
|
|
24607
|
-
function nodeRuntimeSupportsWebSocket(nodeExecutable) {
|
|
24608
|
-
try {
|
|
24609
|
-
(0, import_node_child_process3.execFileSync)(nodeExecutable, ["-e", "process.exit(typeof WebSocket === 'function' ? 0 : 42)"], {
|
|
24610
|
-
stdio: "ignore",
|
|
24611
|
-
timeout: 3e3
|
|
24612
|
-
});
|
|
24613
|
-
return true;
|
|
24614
|
-
} catch {
|
|
24615
|
-
return false;
|
|
24616
|
-
}
|
|
24617
|
-
}
|
|
24618
|
-
function resolveAdhdevMcpEntryPath(explicitPath) {
|
|
24619
|
-
const explicit = explicitPath?.trim();
|
|
24620
|
-
if (explicit) return normalizeExistingPath(explicit) || explicit;
|
|
24621
|
-
const envPath = process.env.ADHDEV_MCP_SERVER_PATH?.trim();
|
|
24622
|
-
if (envPath) return normalizeExistingPath(envPath) || envPath;
|
|
24623
|
-
const candidates = [];
|
|
24624
|
-
const addCandidate = (candidate) => {
|
|
24625
|
-
if (!candidates.includes(candidate)) candidates.push(candidate);
|
|
24626
|
-
};
|
|
24627
|
-
const addPackagedCandidates = (baseFile) => {
|
|
24628
|
-
if (!baseFile) return;
|
|
24629
|
-
const realBase = normalizeExistingPath(baseFile) || baseFile;
|
|
24630
|
-
const dir = (0, import_node_path.dirname)(realBase);
|
|
24631
|
-
addCandidate((0, import_node_path.resolve)(dir, "../vendor/mcp-server/index.js"));
|
|
24632
|
-
addCandidate((0, import_node_path.resolve)(dir, "../../vendor/mcp-server/index.js"));
|
|
24633
|
-
addCandidate((0, import_node_path.resolve)(dir, "../../../vendor/mcp-server/index.js"));
|
|
24634
|
-
addCandidate((0, import_node_path.resolve)(dir, "../../mcp-server/dist/index.js"));
|
|
24635
|
-
addCandidate((0, import_node_path.resolve)(dir, "../../../mcp-server/dist/index.js"));
|
|
24636
|
-
};
|
|
24637
|
-
addPackagedCandidates(process.argv[1]);
|
|
24638
|
-
for (const candidate of candidates) {
|
|
24639
|
-
const normalized = normalizeExistingPath(candidate);
|
|
24640
|
-
if (normalized) return normalized;
|
|
24641
|
-
}
|
|
24642
|
-
try {
|
|
24643
|
-
const requireBase = process.argv[1] ? normalizeExistingPath(process.argv[1]) || process.argv[1] : (0, import_node_path.join)(process.cwd(), "adhdev-daemon.js");
|
|
24644
|
-
const req = (0, import_node_module2.createRequire)(requireBase);
|
|
24645
|
-
const resolvedModule = req.resolve("@adhdev/mcp-server");
|
|
24646
|
-
return normalizeExistingPath(resolvedModule) || resolvedModule;
|
|
24647
|
-
} catch {
|
|
24648
|
-
return null;
|
|
24649
|
-
}
|
|
24650
|
-
}
|
|
24651
|
-
function normalizeExistingPath(filePath) {
|
|
24652
|
-
try {
|
|
24653
|
-
if (!(0, import_node_fs3.existsSync)(filePath)) return null;
|
|
24654
|
-
return import_node_fs3.realpathSync.native(filePath);
|
|
24655
|
-
} catch {
|
|
24656
|
-
return null;
|
|
24657
|
-
}
|
|
24658
|
-
}
|
|
24659
24782
|
|
|
24660
24783
|
// src/commands/router.ts
|
|
24661
24784
|
init_mesh_events();
|
|
@@ -24975,23 +25098,23 @@ function buildStatusSnapshot(options) {
|
|
|
24975
25098
|
}
|
|
24976
25099
|
|
|
24977
25100
|
// src/commands/upgrade-helper.ts
|
|
25101
|
+
var import_child_process7 = require("child_process");
|
|
24978
25102
|
var import_child_process8 = require("child_process");
|
|
24979
|
-
var
|
|
24980
|
-
var fs9 = __toESM(require("fs"));
|
|
25103
|
+
var fs10 = __toESM(require("fs"));
|
|
24981
25104
|
var os19 = __toESM(require("os"));
|
|
24982
25105
|
var path22 = __toESM(require("path"));
|
|
24983
25106
|
var UPGRADE_HELPER_ENV = "ADHDEV_DAEMON_UPGRADE_HELPER";
|
|
24984
25107
|
function getUpgradeLogPath() {
|
|
24985
25108
|
const home = os19.homedir();
|
|
24986
25109
|
const dir = path22.join(home, ".adhdev");
|
|
24987
|
-
|
|
25110
|
+
fs10.mkdirSync(dir, { recursive: true });
|
|
24988
25111
|
return path22.join(dir, "daemon-upgrade.log");
|
|
24989
25112
|
}
|
|
24990
25113
|
function appendUpgradeLog(message) {
|
|
24991
25114
|
const line = `[${(/* @__PURE__ */ new Date()).toISOString()}] ${message}
|
|
24992
25115
|
`;
|
|
24993
25116
|
try {
|
|
24994
|
-
|
|
25117
|
+
fs10.appendFileSync(getUpgradeLogPath(), line, "utf8");
|
|
24995
25118
|
} catch {
|
|
24996
25119
|
}
|
|
24997
25120
|
}
|
|
@@ -24999,12 +25122,12 @@ function resolveSiblingNpmInvocation(nodeExecutable, platform10 = process.platfo
|
|
|
24999
25122
|
const binDir = path22.dirname(nodeExecutable);
|
|
25000
25123
|
if (platform10 === "win32") {
|
|
25001
25124
|
const npmCliPath = path22.join(binDir, "node_modules", "npm", "bin", "npm-cli.js");
|
|
25002
|
-
if (
|
|
25125
|
+
if (fs10.existsSync(npmCliPath)) {
|
|
25003
25126
|
return { executable: nodeExecutable, argsPrefix: [npmCliPath], execOptions: getNpmExecOptions(platform10) };
|
|
25004
25127
|
}
|
|
25005
25128
|
for (const candidate of ["npm.exe", "npm"]) {
|
|
25006
25129
|
const candidatePath = path22.join(binDir, candidate);
|
|
25007
|
-
if (
|
|
25130
|
+
if (fs10.existsSync(candidatePath)) {
|
|
25008
25131
|
return { executable: candidatePath, argsPrefix: [], execOptions: getNpmExecOptions(platform10) };
|
|
25009
25132
|
}
|
|
25010
25133
|
}
|
|
@@ -25012,7 +25135,7 @@ function resolveSiblingNpmInvocation(nodeExecutable, platform10 = process.platfo
|
|
|
25012
25135
|
}
|
|
25013
25136
|
for (const candidate of ["npm"]) {
|
|
25014
25137
|
const candidatePath = path22.join(binDir, candidate);
|
|
25015
|
-
if (
|
|
25138
|
+
if (fs10.existsSync(candidatePath)) {
|
|
25016
25139
|
return { executable: candidatePath, argsPrefix: [], execOptions: getNpmExecOptions(platform10) };
|
|
25017
25140
|
}
|
|
25018
25141
|
}
|
|
@@ -25022,12 +25145,12 @@ function findCurrentPackageRoot(currentCliPath, packageName) {
|
|
|
25022
25145
|
if (!currentCliPath) return null;
|
|
25023
25146
|
let resolvedPath = currentCliPath;
|
|
25024
25147
|
try {
|
|
25025
|
-
resolvedPath =
|
|
25148
|
+
resolvedPath = fs10.realpathSync.native(currentCliPath);
|
|
25026
25149
|
} catch {
|
|
25027
25150
|
}
|
|
25028
25151
|
let currentDir = resolvedPath;
|
|
25029
25152
|
try {
|
|
25030
|
-
if (
|
|
25153
|
+
if (fs10.statSync(resolvedPath).isFile()) {
|
|
25031
25154
|
currentDir = path22.dirname(resolvedPath);
|
|
25032
25155
|
}
|
|
25033
25156
|
} catch {
|
|
@@ -25036,8 +25159,8 @@ function findCurrentPackageRoot(currentCliPath, packageName) {
|
|
|
25036
25159
|
while (true) {
|
|
25037
25160
|
const packageJsonPath = path22.join(currentDir, "package.json");
|
|
25038
25161
|
try {
|
|
25039
|
-
if (
|
|
25040
|
-
const parsed = JSON.parse(
|
|
25162
|
+
if (fs10.existsSync(packageJsonPath)) {
|
|
25163
|
+
const parsed = JSON.parse(fs10.readFileSync(packageJsonPath, "utf8"));
|
|
25041
25164
|
if (parsed?.name === packageName) {
|
|
25042
25165
|
const normalized = currentDir.replace(/\\/g, "/");
|
|
25043
25166
|
return normalized.includes("/node_modules/") ? currentDir : null;
|
|
@@ -25095,7 +25218,7 @@ function getNpmExecOptions(platform10 = process.platform) {
|
|
|
25095
25218
|
}
|
|
25096
25219
|
function execNpmCommandSync(args, options = {}, surface) {
|
|
25097
25220
|
const execOptions = surface?.execOptions || getNpmExecOptions();
|
|
25098
|
-
return (0,
|
|
25221
|
+
return (0, import_child_process7.execFileSync)(
|
|
25099
25222
|
surface?.npmExecutable || "npm",
|
|
25100
25223
|
[...surface?.npmArgsPrefix || [], ...args],
|
|
25101
25224
|
{
|
|
@@ -25108,7 +25231,7 @@ function execNpmCommandSync(args, options = {}, surface) {
|
|
|
25108
25231
|
function killPid(pid) {
|
|
25109
25232
|
try {
|
|
25110
25233
|
if (process.platform === "win32") {
|
|
25111
|
-
(0,
|
|
25234
|
+
(0, import_child_process7.execFileSync)("taskkill", ["/PID", String(pid), "/T", "/F"], { stdio: "ignore", windowsHide: true });
|
|
25112
25235
|
} else {
|
|
25113
25236
|
process.kill(pid, "SIGTERM");
|
|
25114
25237
|
}
|
|
@@ -25120,7 +25243,7 @@ function killPid(pid) {
|
|
|
25120
25243
|
function getWindowsProcessCommandLine(pid) {
|
|
25121
25244
|
const pidFilter = `ProcessId=${pid}`;
|
|
25122
25245
|
try {
|
|
25123
|
-
const psOut = (0,
|
|
25246
|
+
const psOut = (0, import_child_process7.execFileSync)("powershell.exe", [
|
|
25124
25247
|
"-NoProfile",
|
|
25125
25248
|
"-NonInteractive",
|
|
25126
25249
|
"-ExecutionPolicy",
|
|
@@ -25132,7 +25255,7 @@ function getWindowsProcessCommandLine(pid) {
|
|
|
25132
25255
|
} catch {
|
|
25133
25256
|
}
|
|
25134
25257
|
try {
|
|
25135
|
-
const wmicOut = (0,
|
|
25258
|
+
const wmicOut = (0, import_child_process7.execFileSync)("wmic", [
|
|
25136
25259
|
"process",
|
|
25137
25260
|
"where",
|
|
25138
25261
|
pidFilter,
|
|
@@ -25148,7 +25271,7 @@ function getProcessCommandLine(pid) {
|
|
|
25148
25271
|
if (!Number.isFinite(pid) || pid <= 0) return null;
|
|
25149
25272
|
if (process.platform === "win32") return getWindowsProcessCommandLine(pid);
|
|
25150
25273
|
try {
|
|
25151
|
-
const text = (0,
|
|
25274
|
+
const text = (0, import_child_process7.execFileSync)("ps", ["-o", "command=", "-p", String(pid)], {
|
|
25152
25275
|
encoding: "utf8",
|
|
25153
25276
|
timeout: 3e3,
|
|
25154
25277
|
stdio: ["ignore", "pipe", "ignore"]
|
|
@@ -25176,8 +25299,8 @@ async function waitForPidExit(pid, timeoutMs) {
|
|
|
25176
25299
|
function stopSessionHostProcesses(appName) {
|
|
25177
25300
|
const pidFile = path22.join(os19.homedir(), ".adhdev", `${appName}-session-host.pid`);
|
|
25178
25301
|
try {
|
|
25179
|
-
if (
|
|
25180
|
-
const pid = Number.parseInt(
|
|
25302
|
+
if (fs10.existsSync(pidFile)) {
|
|
25303
|
+
const pid = Number.parseInt(fs10.readFileSync(pidFile, "utf8").trim(), 10);
|
|
25181
25304
|
if (Number.isFinite(pid) && pid !== process.pid && isManagedSessionHostPid(pid)) {
|
|
25182
25305
|
killPid(pid);
|
|
25183
25306
|
}
|
|
@@ -25185,7 +25308,7 @@ function stopSessionHostProcesses(appName) {
|
|
|
25185
25308
|
} catch {
|
|
25186
25309
|
} finally {
|
|
25187
25310
|
try {
|
|
25188
|
-
|
|
25311
|
+
fs10.unlinkSync(pidFile);
|
|
25189
25312
|
} catch {
|
|
25190
25313
|
}
|
|
25191
25314
|
}
|
|
@@ -25193,7 +25316,7 @@ function stopSessionHostProcesses(appName) {
|
|
|
25193
25316
|
function removeDaemonPidFile() {
|
|
25194
25317
|
const pidFile = path22.join(os19.homedir(), ".adhdev", "daemon.pid");
|
|
25195
25318
|
try {
|
|
25196
|
-
|
|
25319
|
+
fs10.unlinkSync(pidFile);
|
|
25197
25320
|
} catch {
|
|
25198
25321
|
}
|
|
25199
25322
|
}
|
|
@@ -25211,30 +25334,30 @@ function cleanupStaleGlobalInstallDirs(pkgName, surface) {
|
|
|
25211
25334
|
if (pkgName.startsWith("@")) {
|
|
25212
25335
|
const [scope, name] = pkgName.split("/");
|
|
25213
25336
|
const scopeDir = path22.join(npmRoot, scope);
|
|
25214
|
-
if (!
|
|
25215
|
-
for (const entry of
|
|
25337
|
+
if (!fs10.existsSync(scopeDir)) return;
|
|
25338
|
+
for (const entry of fs10.readdirSync(scopeDir)) {
|
|
25216
25339
|
if (!entry.startsWith(`.${name}-`)) continue;
|
|
25217
|
-
|
|
25340
|
+
fs10.rmSync(path22.join(scopeDir, entry), { recursive: true, force: true });
|
|
25218
25341
|
appendUpgradeLog(`Removed stale scoped staging dir: ${path22.join(scopeDir, entry)}`);
|
|
25219
25342
|
}
|
|
25220
25343
|
} else {
|
|
25221
|
-
for (const entry of
|
|
25344
|
+
for (const entry of fs10.readdirSync(npmRoot)) {
|
|
25222
25345
|
if (!entry.startsWith(`.${pkgName}-`)) continue;
|
|
25223
|
-
|
|
25346
|
+
fs10.rmSync(path22.join(npmRoot, entry), { recursive: true, force: true });
|
|
25224
25347
|
appendUpgradeLog(`Removed stale staging dir: ${path22.join(npmRoot, entry)}`);
|
|
25225
25348
|
}
|
|
25226
25349
|
}
|
|
25227
|
-
if (
|
|
25228
|
-
for (const entry of
|
|
25350
|
+
if (fs10.existsSync(binDir)) {
|
|
25351
|
+
for (const entry of fs10.readdirSync(binDir)) {
|
|
25229
25352
|
if (!Array.from(binNames).some((name) => entry.startsWith(`.${name}-`))) continue;
|
|
25230
|
-
|
|
25353
|
+
fs10.rmSync(path22.join(binDir, entry), { recursive: true, force: true });
|
|
25231
25354
|
appendUpgradeLog(`Removed stale bin staging entry: ${path22.join(binDir, entry)}`);
|
|
25232
25355
|
}
|
|
25233
25356
|
}
|
|
25234
25357
|
}
|
|
25235
25358
|
function spawnDetachedDaemonUpgradeHelper(payload) {
|
|
25236
25359
|
const env = { ...process.env, [UPGRADE_HELPER_ENV]: JSON.stringify(payload) };
|
|
25237
|
-
const child = (0,
|
|
25360
|
+
const child = (0, import_child_process8.spawn)(process.execPath, process.argv.slice(1), {
|
|
25238
25361
|
detached: true,
|
|
25239
25362
|
stdio: "ignore",
|
|
25240
25363
|
windowsHide: true,
|
|
@@ -25264,7 +25387,7 @@ async function runDaemonUpgradeHelper(payload) {
|
|
|
25264
25387
|
cleanupStaleGlobalInstallDirs(payload.packageName, installCommand.surface);
|
|
25265
25388
|
const spec = `${payload.packageName}@${payload.targetVersion || "latest"}`;
|
|
25266
25389
|
appendUpgradeLog(`Installing ${spec}`);
|
|
25267
|
-
const installOutput = (0,
|
|
25390
|
+
const installOutput = (0, import_child_process7.execFileSync)(
|
|
25268
25391
|
installCommand.command,
|
|
25269
25392
|
installCommand.args,
|
|
25270
25393
|
{
|
|
@@ -25286,7 +25409,7 @@ async function runDaemonUpgradeHelper(payload) {
|
|
|
25286
25409
|
const env = { ...process.env };
|
|
25287
25410
|
delete env[UPGRADE_HELPER_ENV];
|
|
25288
25411
|
appendUpgradeLog(`Restarting daemon with args: ${restartArgv.join(" ")}`);
|
|
25289
|
-
const child = (0,
|
|
25412
|
+
const child = (0, import_child_process8.spawn)(process.execPath, restartArgv, {
|
|
25290
25413
|
detached: true,
|
|
25291
25414
|
stdio: "ignore",
|
|
25292
25415
|
windowsHide: true,
|
|
@@ -25313,9 +25436,10 @@ async function maybeRunDaemonUpgradeHelperFromEnv() {
|
|
|
25313
25436
|
}
|
|
25314
25437
|
|
|
25315
25438
|
// src/commands/router.ts
|
|
25439
|
+
init_mesh_work_queue();
|
|
25316
25440
|
var import_os3 = require("os");
|
|
25317
25441
|
var import_path8 = require("path");
|
|
25318
|
-
var
|
|
25442
|
+
var fs11 = __toESM(require("fs"));
|
|
25319
25443
|
var CHANNEL_NPM_TAG = { stable: "latest", preview: "next" };
|
|
25320
25444
|
var CHANNEL_SERVER_URL = {
|
|
25321
25445
|
stable: "https://api.adhf.dev",
|
|
@@ -25959,7 +26083,7 @@ async function hydrateInlineMeshDirectTruth(args) {
|
|
|
25959
26083
|
if (!isSelfNode && daemonId) unavailableNodeIds.push(nodeId);
|
|
25960
26084
|
continue;
|
|
25961
26085
|
}
|
|
25962
|
-
if (
|
|
26086
|
+
if (fs11.existsSync(workspace)) {
|
|
25963
26087
|
try {
|
|
25964
26088
|
const localGit = await getGitRepoStatus(workspace, { timeoutMs: 1e4, refreshUpstream: true });
|
|
25965
26089
|
if (localGit?.isGitRepo) {
|
|
@@ -26126,14 +26250,14 @@ function recordMeshRefineStage(stages, stage, status, startedAt, details) {
|
|
|
26126
26250
|
});
|
|
26127
26251
|
}
|
|
26128
26252
|
async function computeGitPatchId(cwd, fromRef, toRef) {
|
|
26129
|
-
const { execFileSync:
|
|
26130
|
-
const diff =
|
|
26253
|
+
const { execFileSync: execFileSync3 } = await import("child_process");
|
|
26254
|
+
const diff = execFileSync3("git", ["diff", "--patch", "--full-index", fromRef, toRef], {
|
|
26131
26255
|
cwd,
|
|
26132
26256
|
encoding: "utf8",
|
|
26133
26257
|
maxBuffer: REFINE_PATCH_EQUIVALENCE_OUTPUT_LIMIT_BYTES
|
|
26134
26258
|
});
|
|
26135
26259
|
if (!diff.trim()) return "";
|
|
26136
|
-
const patchId =
|
|
26260
|
+
const patchId = execFileSync3("git", ["patch-id", "--stable"], {
|
|
26137
26261
|
cwd,
|
|
26138
26262
|
input: diff,
|
|
26139
26263
|
encoding: "utf8",
|
|
@@ -26144,8 +26268,8 @@ async function computeGitPatchId(cwd, fromRef, toRef) {
|
|
|
26144
26268
|
async function runMeshRefinePatchEquivalenceGate(repoRoot, baseHead, branchHead) {
|
|
26145
26269
|
const startedAt = Date.now();
|
|
26146
26270
|
try {
|
|
26147
|
-
const { execFileSync:
|
|
26148
|
-
const git = (args) =>
|
|
26271
|
+
const { execFileSync: execFileSync3 } = await import("child_process");
|
|
26272
|
+
const git = (args) => execFileSync3("git", args, {
|
|
26149
26273
|
cwd: repoRoot,
|
|
26150
26274
|
encoding: "utf8",
|
|
26151
26275
|
maxBuffer: REFINE_PATCH_EQUIVALENCE_OUTPUT_LIMIT_BYTES
|
|
@@ -26198,8 +26322,8 @@ async function runMeshRefineSubmoduleReachabilityGate(repoRoot, mergedTree) {
|
|
|
26198
26322
|
const entries = [];
|
|
26199
26323
|
try {
|
|
26200
26324
|
const { execFile: execFile3 } = await import("child_process");
|
|
26201
|
-
const { promisify:
|
|
26202
|
-
const execFileAsync3 =
|
|
26325
|
+
const { promisify: promisify6 } = await import("util");
|
|
26326
|
+
const execFileAsync3 = promisify6(execFile3);
|
|
26203
26327
|
const runGit2 = async (cwd, args) => {
|
|
26204
26328
|
const { stdout } = await execFileAsync3("git", args, {
|
|
26205
26329
|
cwd,
|
|
@@ -26223,7 +26347,7 @@ async function runMeshRefineSubmoduleReachabilityGate(repoRoot, mergedTree) {
|
|
|
26223
26347
|
reachable: false
|
|
26224
26348
|
};
|
|
26225
26349
|
try {
|
|
26226
|
-
if (!
|
|
26350
|
+
if (!fs11.existsSync(submodulePath)) {
|
|
26227
26351
|
entry.error = `Submodule checkout missing at ${gitlink.path}`;
|
|
26228
26352
|
entries.push(entry);
|
|
26229
26353
|
continue;
|
|
@@ -26289,8 +26413,8 @@ function buildMeshRefineValidationPlan(mesh, workspace) {
|
|
|
26289
26413
|
}
|
|
26290
26414
|
async function runMeshRefineValidationGate(mesh, workspace) {
|
|
26291
26415
|
const { execFile: execFile3 } = await import("child_process");
|
|
26292
|
-
const { promisify:
|
|
26293
|
-
const execFileAsync3 =
|
|
26416
|
+
const { promisify: promisify6 } = await import("util");
|
|
26417
|
+
const execFileAsync3 = promisify6(execFile3);
|
|
26294
26418
|
const selection = resolveMeshRefineValidationPlan(mesh, workspace);
|
|
26295
26419
|
const summary = {
|
|
26296
26420
|
status: "skipped",
|
|
@@ -26380,9 +26504,9 @@ function resolveHermesUserHome() {
|
|
|
26380
26504
|
function loadHermesCoordinatorBaseConfig(targetConfigPath) {
|
|
26381
26505
|
const sourceHome = resolveHermesUserHome();
|
|
26382
26506
|
const sourceConfigPath = (0, import_path8.join)(sourceHome, "config.yaml");
|
|
26383
|
-
if (!
|
|
26507
|
+
if (!fs11.existsSync(sourceConfigPath)) return { config: {}, sourceHome, sourceConfigPath };
|
|
26384
26508
|
if ((0, import_path8.resolve)(sourceConfigPath) === (0, import_path8.resolve)(targetConfigPath)) return { config: {}, sourceHome, sourceConfigPath };
|
|
26385
|
-
const parsed = parseMeshCoordinatorMcpConfig(
|
|
26509
|
+
const parsed = parseMeshCoordinatorMcpConfig(fs11.readFileSync(sourceConfigPath, "utf-8"), "hermes_config_yaml");
|
|
26386
26510
|
const { mcp_servers: _mcpServers, ...baseConfig } = parsed;
|
|
26387
26511
|
return { config: baseConfig, sourceHome, sourceConfigPath };
|
|
26388
26512
|
}
|
|
@@ -26419,9 +26543,9 @@ function copyHermesCoordinatorCredentialFiles(sourceHome, targetHome) {
|
|
|
26419
26543
|
for (const fileName of [".env", "auth.json"]) {
|
|
26420
26544
|
const sourcePath = (0, import_path8.join)(sourceHome, fileName);
|
|
26421
26545
|
const targetPath = (0, import_path8.join)(targetHome, fileName);
|
|
26422
|
-
if (!
|
|
26546
|
+
if (!fs11.existsSync(sourcePath)) continue;
|
|
26423
26547
|
try {
|
|
26424
|
-
|
|
26548
|
+
fs11.copyFileSync(sourcePath, targetPath);
|
|
26425
26549
|
} catch (error) {
|
|
26426
26550
|
LOG.warn("MeshCoordinator", `Could not copy Hermes ${fileName} into isolated coordinator home: ${error?.message || error}`);
|
|
26427
26551
|
}
|
|
@@ -26634,6 +26758,7 @@ var DaemonCommandRouter = class {
|
|
|
26634
26758
|
getCachedAggregateMeshStatus(meshId, mesh, options) {
|
|
26635
26759
|
const cached = this.aggregateMeshStatusCache.get(meshId);
|
|
26636
26760
|
if (!cached?.snapshot || cached.snapshot.success !== true || !Array.isArray(cached.snapshot.nodes)) return null;
|
|
26761
|
+
if (cached.queueRevision !== getMeshQueueRevision(meshId)) return null;
|
|
26637
26762
|
let snapshot = this.cloneJsonValue(cached.snapshot);
|
|
26638
26763
|
snapshot = this.hydrateCachedAggregateMeshStatusFromInline(snapshot, mesh, options);
|
|
26639
26764
|
if (shouldRefreshStalePendingAggregate(snapshot, options)) return null;
|
|
@@ -26671,7 +26796,7 @@ var DaemonCommandRouter = class {
|
|
|
26671
26796
|
returnedAt: new Date(builtAt).toISOString()
|
|
26672
26797
|
}
|
|
26673
26798
|
};
|
|
26674
|
-
this.aggregateMeshStatusCache.set(meshId, { builtAt, snapshot: this.cloneJsonValue(next) });
|
|
26799
|
+
this.aggregateMeshStatusCache.set(meshId, { builtAt, snapshot: this.cloneJsonValue(next), queueRevision: getMeshQueueRevision(meshId) });
|
|
26675
26800
|
return next;
|
|
26676
26801
|
}
|
|
26677
26802
|
getCachedInlineMesh(meshId, inlineMesh) {
|
|
@@ -26774,13 +26899,13 @@ var DaemonCommandRouter = class {
|
|
|
26774
26899
|
recoveryHint: "Inspect the mesh node record before removing it, or remove stale metadata manually only after confirming no managed worktree remains."
|
|
26775
26900
|
};
|
|
26776
26901
|
}
|
|
26777
|
-
const worktreeExists =
|
|
26902
|
+
const worktreeExists = fs11.existsSync(workspace);
|
|
26778
26903
|
const sourceNode = args.node?.clonedFromNodeId ? args.mesh?.nodes?.find((n) => n.id === args.node.clonedFromNodeId || n.nodeId === args.node.clonedFromNodeId) : args.mesh?.nodes?.find((n) => !n.isLocalWorktree);
|
|
26779
26904
|
const repoRoot = typeof sourceNode?.repoRoot === "string" && sourceNode.repoRoot.trim() ? sourceNode.repoRoot.trim() : typeof sourceNode?.workspace === "string" && sourceNode.workspace.trim() ? sourceNode.workspace.trim() : "";
|
|
26780
26905
|
if (!worktreeExists) {
|
|
26781
26906
|
return { success: true, skipped: true, removedPath: workspace, repoRoot: repoRoot || void 0, reason: "worktree_path_missing" };
|
|
26782
26907
|
}
|
|
26783
|
-
if (!repoRoot || !
|
|
26908
|
+
if (!repoRoot || !fs11.existsSync(repoRoot)) {
|
|
26784
26909
|
return {
|
|
26785
26910
|
success: false,
|
|
26786
26911
|
code: "mesh_worktree_cleanup_missing_source_repo",
|
|
@@ -26800,7 +26925,7 @@ var DaemonCommandRouter = class {
|
|
|
26800
26925
|
const normalizePath = (value) => {
|
|
26801
26926
|
const resolved = (0, import_path8.resolve)(value);
|
|
26802
26927
|
try {
|
|
26803
|
-
return
|
|
26928
|
+
return fs11.realpathSync(resolved);
|
|
26804
26929
|
} catch {
|
|
26805
26930
|
return resolved;
|
|
26806
26931
|
}
|
|
@@ -26873,8 +26998,8 @@ var DaemonCommandRouter = class {
|
|
|
26873
26998
|
return { allow: true, status: metadataStatus, source: "node_branch_convergence" };
|
|
26874
26999
|
}
|
|
26875
27000
|
const { execFile: execFile3 } = await import("child_process");
|
|
26876
|
-
const { promisify:
|
|
26877
|
-
const execFileAsync3 =
|
|
27001
|
+
const { promisify: promisify6 } = await import("util");
|
|
27002
|
+
const execFileAsync3 = promisify6(execFile3);
|
|
26878
27003
|
const runGit2 = async (gitArgs, cwd) => {
|
|
26879
27004
|
const { stdout } = await execFileAsync3("git", gitArgs, {
|
|
26880
27005
|
cwd,
|
|
@@ -27284,8 +27409,8 @@ var DaemonCommandRouter = class {
|
|
|
27284
27409
|
const repoRoot = sourceNode?.repoRoot || sourceNode?.workspace;
|
|
27285
27410
|
if (!repoRoot) return { success: false, error: "Source node repoRoot not found", refineStages };
|
|
27286
27411
|
const { execFile: execFile3 } = await import("child_process");
|
|
27287
|
-
const { promisify:
|
|
27288
|
-
const execFileAsync3 =
|
|
27412
|
+
const { promisify: promisify6 } = await import("util");
|
|
27413
|
+
const execFileAsync3 = promisify6(execFile3);
|
|
27289
27414
|
const resolveStarted = Date.now();
|
|
27290
27415
|
const { stdout: branchStdout } = await execFileAsync3("git", ["branch", "--show-current"], { cwd: node.workspace, encoding: "utf8" });
|
|
27291
27416
|
const branch = branchStdout.trim();
|
|
@@ -27594,8 +27719,8 @@ var DaemonCommandRouter = class {
|
|
|
27594
27719
|
if (sinceTs > 0) {
|
|
27595
27720
|
return { success: true, logs: [], totalBuffered: 0 };
|
|
27596
27721
|
}
|
|
27597
|
-
if (
|
|
27598
|
-
const content =
|
|
27722
|
+
if (fs11.existsSync(LOG_PATH)) {
|
|
27723
|
+
const content = fs11.readFileSync(LOG_PATH, "utf-8");
|
|
27599
27724
|
const allLines = content.split("\n");
|
|
27600
27725
|
const recent = allLines.slice(-count).join("\n");
|
|
27601
27726
|
return { success: true, logs: recent, totalLines: allLines.length };
|
|
@@ -29018,7 +29143,7 @@ ${block2}`);
|
|
|
29018
29143
|
workspace
|
|
29019
29144
|
};
|
|
29020
29145
|
}
|
|
29021
|
-
const { existsSync:
|
|
29146
|
+
const { existsSync: existsSync26, readFileSync: readFileSync19, writeFileSync: writeFileSync14, copyFileSync: copyFileSync4, mkdirSync: mkdirSync18 } = await import("fs");
|
|
29022
29147
|
const { dirname: dirname9 } = await import("path");
|
|
29023
29148
|
const mcpConfigPath = coordinatorSetup.configPath;
|
|
29024
29149
|
const hermesManualFallback = cliType === "hermes-cli" && configFormat === "hermes_config_yaml" ? createHermesManualMeshCoordinatorSetup(meshId, workspace) : null;
|
|
@@ -29054,14 +29179,14 @@ ${block2}`);
|
|
|
29054
29179
|
};
|
|
29055
29180
|
}
|
|
29056
29181
|
try {
|
|
29057
|
-
|
|
29182
|
+
mkdirSync18(dirname9(mcpConfigPath), { recursive: true });
|
|
29058
29183
|
} catch (error) {
|
|
29059
29184
|
const message = `Could not prepare MCP config path for automatic setup: ${error?.message || error}`;
|
|
29060
29185
|
LOG.error("MeshCoordinator", message);
|
|
29061
29186
|
if (hermesManualFallback) return returnManualFallback(message);
|
|
29062
29187
|
return { success: false, code: "mesh_coordinator_config_write_failed", error: message, meshId, cliType, workspace };
|
|
29063
29188
|
}
|
|
29064
|
-
const hadExistingMcpConfig =
|
|
29189
|
+
const hadExistingMcpConfig = existsSync26(mcpConfigPath);
|
|
29065
29190
|
let existingMcpConfig = hermesBaseConfig?.config || {};
|
|
29066
29191
|
if (hermesBaseConfig) {
|
|
29067
29192
|
copyHermesCoordinatorCredentialFiles(hermesBaseConfig.sourceHome, dirname9(mcpConfigPath));
|
|
@@ -29091,7 +29216,7 @@ ${block2}`);
|
|
|
29091
29216
|
}
|
|
29092
29217
|
};
|
|
29093
29218
|
try {
|
|
29094
|
-
|
|
29219
|
+
writeFileSync14(mcpConfigPath, serializeMeshCoordinatorMcpConfig(mcpConfig, configFormat), "utf-8");
|
|
29095
29220
|
} catch (error) {
|
|
29096
29221
|
const message = `Could not write MCP config for automatic setup: ${error?.message || error}`;
|
|
29097
29222
|
LOG.error("MeshCoordinator", message);
|
|
@@ -29319,7 +29444,7 @@ ${block2}`);
|
|
|
29319
29444
|
}
|
|
29320
29445
|
}
|
|
29321
29446
|
if (workspace) {
|
|
29322
|
-
if (!
|
|
29447
|
+
if (!fs11.existsSync(workspace)) {
|
|
29323
29448
|
const inlineTransitGit = buildInlineMeshTransitGitStatus(node);
|
|
29324
29449
|
let remoteProbeApplied = false;
|
|
29325
29450
|
if (inlineTransitGit) {
|
|
@@ -29528,7 +29653,7 @@ ${block2}`);
|
|
|
29528
29653
|
}
|
|
29529
29654
|
}
|
|
29530
29655
|
if (killProcess) {
|
|
29531
|
-
const running = isIdeRunning(ideType);
|
|
29656
|
+
const running = await isIdeRunning(ideType);
|
|
29532
29657
|
if (running) {
|
|
29533
29658
|
LOG.info("StopIDE", `Killing IDE process: ${ideType}`);
|
|
29534
29659
|
const killed = await killIdeProcess(ideType);
|
|
@@ -29554,6 +29679,8 @@ var DaemonStatusReporter = class {
|
|
|
29554
29679
|
lastStatusSentAt = 0;
|
|
29555
29680
|
statusPendingThrottle = false;
|
|
29556
29681
|
lastP2PStatusHash = "";
|
|
29682
|
+
lastP2PStatusSentAt = 0;
|
|
29683
|
+
p2pDebounceTimer = null;
|
|
29557
29684
|
lastServerStatusHash = "";
|
|
29558
29685
|
lastStatusSummary = "";
|
|
29559
29686
|
statusTimer = null;
|
|
@@ -29805,7 +29932,18 @@ var DaemonStatusReporter = class {
|
|
|
29805
29932
|
})() : { ...hashTarget, sessions };
|
|
29806
29933
|
const h = this.simpleHash(JSON.stringify(hashPayload));
|
|
29807
29934
|
if (h !== this.lastP2PStatusHash) {
|
|
29935
|
+
const now = Date.now();
|
|
29936
|
+
if (this.lastP2PStatusSentAt && now - this.lastP2PStatusSentAt < 500) {
|
|
29937
|
+
if (!this.p2pDebounceTimer) {
|
|
29938
|
+
this.p2pDebounceTimer = setTimeout(() => {
|
|
29939
|
+
this.p2pDebounceTimer = null;
|
|
29940
|
+
this.sendUnifiedStatusReport({ reason: "p2p_debounce" });
|
|
29941
|
+
}, 500);
|
|
29942
|
+
}
|
|
29943
|
+
return false;
|
|
29944
|
+
}
|
|
29808
29945
|
this.lastP2PStatusHash = h;
|
|
29946
|
+
this.lastP2PStatusSentAt = now;
|
|
29809
29947
|
this.deps.p2p?.sendStatus(payload);
|
|
29810
29948
|
return true;
|
|
29811
29949
|
}
|
|
@@ -31140,11 +31278,11 @@ var ProviderInstanceManager = class {
|
|
|
31140
31278
|
};
|
|
31141
31279
|
|
|
31142
31280
|
// src/providers/version-archive.ts
|
|
31143
|
-
var
|
|
31281
|
+
var fs12 = __toESM(require("fs"));
|
|
31144
31282
|
var path23 = __toESM(require("path"));
|
|
31145
31283
|
var os20 = __toESM(require("os"));
|
|
31146
|
-
var import_child_process10 = require("child_process");
|
|
31147
31284
|
var import_os4 = require("os");
|
|
31285
|
+
var import_child_process9 = require("child_process");
|
|
31148
31286
|
var ARCHIVE_PATH = path23.join(os20.homedir(), ".adhdev", "version-history.json");
|
|
31149
31287
|
var MAX_ENTRIES_PER_PROVIDER = 20;
|
|
31150
31288
|
var VersionArchive = class {
|
|
@@ -31154,8 +31292,8 @@ var VersionArchive = class {
|
|
|
31154
31292
|
}
|
|
31155
31293
|
load() {
|
|
31156
31294
|
try {
|
|
31157
|
-
if (
|
|
31158
|
-
this.history = JSON.parse(
|
|
31295
|
+
if (fs12.existsSync(ARCHIVE_PATH)) {
|
|
31296
|
+
this.history = JSON.parse(fs12.readFileSync(ARCHIVE_PATH, "utf-8"));
|
|
31159
31297
|
}
|
|
31160
31298
|
} catch {
|
|
31161
31299
|
this.history = {};
|
|
@@ -31192,27 +31330,43 @@ var VersionArchive = class {
|
|
|
31192
31330
|
}
|
|
31193
31331
|
save() {
|
|
31194
31332
|
try {
|
|
31195
|
-
|
|
31196
|
-
|
|
31333
|
+
fs12.mkdirSync(path23.dirname(ARCHIVE_PATH), { recursive: true });
|
|
31334
|
+
fs12.writeFileSync(ARCHIVE_PATH, JSON.stringify(this.history, null, 2));
|
|
31197
31335
|
} catch {
|
|
31198
31336
|
}
|
|
31199
31337
|
}
|
|
31200
31338
|
};
|
|
31201
|
-
function runCommand(cmd, timeout = 1e4) {
|
|
31202
|
-
|
|
31203
|
-
|
|
31339
|
+
async function runCommand(cmd, timeout = 1e4) {
|
|
31340
|
+
return new Promise((resolve16) => {
|
|
31341
|
+
(0, import_child_process9.exec)(cmd, {
|
|
31204
31342
|
encoding: "utf-8",
|
|
31205
|
-
timeout
|
|
31206
|
-
|
|
31207
|
-
|
|
31208
|
-
|
|
31209
|
-
|
|
31210
|
-
}
|
|
31343
|
+
timeout
|
|
31344
|
+
}, (error, stdout) => {
|
|
31345
|
+
if (error) return resolve16(null);
|
|
31346
|
+
resolve16(stdout.trim());
|
|
31347
|
+
});
|
|
31348
|
+
});
|
|
31211
31349
|
}
|
|
31212
31350
|
function findBinary2(name) {
|
|
31213
|
-
const
|
|
31214
|
-
const
|
|
31215
|
-
|
|
31351
|
+
const isWin = (0, import_os4.platform)() === "win32";
|
|
31352
|
+
const paths = (process.env.PATH || "").split(isWin ? ";" : ":");
|
|
31353
|
+
const exes = isWin ? [".exe", ".cmd", ".bat", ""] : [""];
|
|
31354
|
+
for (const p of paths) {
|
|
31355
|
+
if (!p) continue;
|
|
31356
|
+
for (const ext of exes) {
|
|
31357
|
+
const fullPath = path23.join(p, name + ext);
|
|
31358
|
+
try {
|
|
31359
|
+
if (fs12.existsSync(fullPath)) {
|
|
31360
|
+
const stat2 = fs12.statSync(fullPath);
|
|
31361
|
+
if (stat2.isFile() && (isWin || stat2.mode & 73)) {
|
|
31362
|
+
return fullPath;
|
|
31363
|
+
}
|
|
31364
|
+
}
|
|
31365
|
+
} catch {
|
|
31366
|
+
}
|
|
31367
|
+
}
|
|
31368
|
+
}
|
|
31369
|
+
return null;
|
|
31216
31370
|
}
|
|
31217
31371
|
function parseVersion2(raw) {
|
|
31218
31372
|
const match = raw.match(/v?(\d+\.\d+(?:\.\d+)?(?:-[a-zA-Z0-9.]+)?)/);
|
|
@@ -31234,13 +31388,13 @@ function getPlatformVersionCommand(versionCommand, currentOs) {
|
|
|
31234
31388
|
}
|
|
31235
31389
|
return void 0;
|
|
31236
31390
|
}
|
|
31237
|
-
function getVersion(binary, versionCommand) {
|
|
31391
|
+
async function getVersion(binary, versionCommand) {
|
|
31238
31392
|
if (versionCommand) {
|
|
31239
|
-
const raw = runCommand(versionCommand);
|
|
31393
|
+
const raw = await runCommand(versionCommand);
|
|
31240
31394
|
return raw ? parseVersion2(raw) : null;
|
|
31241
31395
|
}
|
|
31242
31396
|
for (const flag of ["--version", "-V", "-v"]) {
|
|
31243
|
-
const raw = runCommand(`"${binary}" ${flag}`);
|
|
31397
|
+
const raw = await runCommand(`"${binary}" ${flag}`);
|
|
31244
31398
|
if (raw && raw.length < 500) return parseVersion2(raw);
|
|
31245
31399
|
}
|
|
31246
31400
|
return null;
|
|
@@ -31250,18 +31404,18 @@ function checkPathExists2(paths) {
|
|
|
31250
31404
|
if (p.includes("*")) {
|
|
31251
31405
|
const home = os20.homedir();
|
|
31252
31406
|
const resolved = p.replace(/\*/g, home.split(path23.sep).pop() || "");
|
|
31253
|
-
if (
|
|
31407
|
+
if (fs12.existsSync(resolved)) return resolved;
|
|
31254
31408
|
} else {
|
|
31255
|
-
if (
|
|
31409
|
+
if (fs12.existsSync(p)) return p;
|
|
31256
31410
|
}
|
|
31257
31411
|
}
|
|
31258
31412
|
return null;
|
|
31259
31413
|
}
|
|
31260
|
-
function getMacAppVersion(appPath) {
|
|
31414
|
+
async function getMacAppVersion(appPath) {
|
|
31261
31415
|
if ((0, import_os4.platform)() !== "darwin" || !appPath.endsWith(".app")) return null;
|
|
31262
31416
|
const plistPath = path23.join(appPath, "Contents", "Info.plist");
|
|
31263
|
-
if (!
|
|
31264
|
-
const raw = runCommand(`/usr/libexec/PlistBuddy -c "Print CFBundleShortVersionString" "${plistPath}"`);
|
|
31417
|
+
if (!fs12.existsSync(plistPath)) return null;
|
|
31418
|
+
const raw = await runCommand(`/usr/libexec/PlistBuddy -c "Print CFBundleShortVersionString" "${plistPath}"`);
|
|
31265
31419
|
return raw || null;
|
|
31266
31420
|
}
|
|
31267
31421
|
async function detectAllVersions(loader, archive) {
|
|
@@ -31286,16 +31440,16 @@ async function detectAllVersions(loader, archive) {
|
|
|
31286
31440
|
let resolvedBin = cliBin;
|
|
31287
31441
|
if (!resolvedBin && appPath && currentOs === "darwin") {
|
|
31288
31442
|
const bundled = path23.join(appPath, "Contents", "Resources", "app", "bin", provider.cli || "");
|
|
31289
|
-
if (provider.cli &&
|
|
31443
|
+
if (provider.cli && fs12.existsSync(bundled)) resolvedBin = bundled;
|
|
31290
31444
|
}
|
|
31291
31445
|
info.installed = !!(appPath || resolvedBin);
|
|
31292
31446
|
info.path = appPath || null;
|
|
31293
31447
|
info.binary = resolvedBin || null;
|
|
31294
31448
|
if (resolvedBin) {
|
|
31295
|
-
info.version = getVersion(resolvedBin, versionCommand);
|
|
31449
|
+
info.version = await getVersion(resolvedBin, versionCommand);
|
|
31296
31450
|
}
|
|
31297
31451
|
if (!info.version && appPath) {
|
|
31298
|
-
info.version = getMacAppVersion(appPath);
|
|
31452
|
+
info.version = await getMacAppVersion(appPath);
|
|
31299
31453
|
}
|
|
31300
31454
|
} else if (provider.category === "cli" || provider.category === "acp") {
|
|
31301
31455
|
const bin = provider.binary || provider.spawn?.command || provider.cli || provider.type;
|
|
@@ -31303,7 +31457,7 @@ async function detectAllVersions(loader, archive) {
|
|
|
31303
31457
|
info.installed = !!binPath;
|
|
31304
31458
|
info.binary = binPath || null;
|
|
31305
31459
|
if (binPath) {
|
|
31306
|
-
info.version = getVersion(binPath, versionCommand);
|
|
31460
|
+
info.version = await getVersion(binPath, versionCommand);
|
|
31307
31461
|
}
|
|
31308
31462
|
} else if (provider.category === "extension") {
|
|
31309
31463
|
info.installed = false;
|
|
@@ -31325,7 +31479,7 @@ async function detectAllVersions(loader, archive) {
|
|
|
31325
31479
|
|
|
31326
31480
|
// src/daemon/dev-server.ts
|
|
31327
31481
|
var http2 = __toESM(require("http"));
|
|
31328
|
-
var
|
|
31482
|
+
var fs16 = __toESM(require("fs"));
|
|
31329
31483
|
var path27 = __toESM(require("path"));
|
|
31330
31484
|
init_config();
|
|
31331
31485
|
|
|
@@ -31676,7 +31830,7 @@ async (params) => {
|
|
|
31676
31830
|
init_logger();
|
|
31677
31831
|
|
|
31678
31832
|
// src/daemon/dev-cdp-handlers.ts
|
|
31679
|
-
var
|
|
31833
|
+
var fs13 = __toESM(require("fs"));
|
|
31680
31834
|
var path24 = __toESM(require("path"));
|
|
31681
31835
|
init_logger();
|
|
31682
31836
|
async function handleCdpEvaluate(ctx, req, res) {
|
|
@@ -31857,17 +32011,17 @@ async function handleScriptHints(ctx, type, _req, res) {
|
|
|
31857
32011
|
}
|
|
31858
32012
|
let scriptsPath = "";
|
|
31859
32013
|
const directScripts = path24.join(dir, "scripts.js");
|
|
31860
|
-
if (
|
|
32014
|
+
if (fs13.existsSync(directScripts)) {
|
|
31861
32015
|
scriptsPath = directScripts;
|
|
31862
32016
|
} else {
|
|
31863
32017
|
const scriptsDir = path24.join(dir, "scripts");
|
|
31864
|
-
if (
|
|
31865
|
-
const versions =
|
|
31866
|
-
return
|
|
32018
|
+
if (fs13.existsSync(scriptsDir)) {
|
|
32019
|
+
const versions = fs13.readdirSync(scriptsDir).filter((d) => {
|
|
32020
|
+
return fs13.statSync(path24.join(scriptsDir, d)).isDirectory();
|
|
31867
32021
|
}).sort().reverse();
|
|
31868
32022
|
for (const ver of versions) {
|
|
31869
32023
|
const p = path24.join(scriptsDir, ver, "scripts.js");
|
|
31870
|
-
if (
|
|
32024
|
+
if (fs13.existsSync(p)) {
|
|
31871
32025
|
scriptsPath = p;
|
|
31872
32026
|
break;
|
|
31873
32027
|
}
|
|
@@ -31879,7 +32033,7 @@ async function handleScriptHints(ctx, type, _req, res) {
|
|
|
31879
32033
|
return;
|
|
31880
32034
|
}
|
|
31881
32035
|
try {
|
|
31882
|
-
const source =
|
|
32036
|
+
const source = fs13.readFileSync(scriptsPath, "utf-8");
|
|
31883
32037
|
const hints = {};
|
|
31884
32038
|
const funcRegex = /module\.exports\.(\w+)\s*=\s*function\s+\w+\s*\(params\)/g;
|
|
31885
32039
|
let match;
|
|
@@ -32694,7 +32848,7 @@ async function handleDomContext(ctx, type, req, res) {
|
|
|
32694
32848
|
}
|
|
32695
32849
|
|
|
32696
32850
|
// src/daemon/dev-cli-debug.ts
|
|
32697
|
-
var
|
|
32851
|
+
var fs14 = __toESM(require("fs"));
|
|
32698
32852
|
var path25 = __toESM(require("path"));
|
|
32699
32853
|
function slugifyFixtureName(value) {
|
|
32700
32854
|
const normalized = String(value || "").trim().toLowerCase().replace(/[^a-z0-9._-]+/g, "-").replace(/^-+|-+$/g, "");
|
|
@@ -32710,10 +32864,10 @@ function getCliFixtureDir(ctx, type) {
|
|
|
32710
32864
|
function readCliFixture(ctx, type, name) {
|
|
32711
32865
|
const fixtureDir = getCliFixtureDir(ctx, type);
|
|
32712
32866
|
const filePath = path25.join(fixtureDir, `${name}.json`);
|
|
32713
|
-
if (!
|
|
32867
|
+
if (!fs14.existsSync(filePath)) {
|
|
32714
32868
|
throw new Error(`Fixture not found: ${filePath}`);
|
|
32715
32869
|
}
|
|
32716
|
-
return JSON.parse(
|
|
32870
|
+
return JSON.parse(fs14.readFileSync(filePath, "utf-8"));
|
|
32717
32871
|
}
|
|
32718
32872
|
function getExerciseTranscriptText(result) {
|
|
32719
32873
|
const parts = [];
|
|
@@ -33449,7 +33603,7 @@ async function handleCliFixtureCapture(ctx, req, res) {
|
|
|
33449
33603
|
return;
|
|
33450
33604
|
}
|
|
33451
33605
|
const fixtureDir = getCliFixtureDir(ctx, type);
|
|
33452
|
-
|
|
33606
|
+
fs14.mkdirSync(fixtureDir, { recursive: true });
|
|
33453
33607
|
const name = slugifyFixtureName(String(body?.name || `${type}-${Date.now()}`));
|
|
33454
33608
|
const result = await runCliExerciseInternal(ctx, { ...request, type });
|
|
33455
33609
|
const fixture = {
|
|
@@ -33477,7 +33631,7 @@ async function handleCliFixtureCapture(ctx, req, res) {
|
|
|
33477
33631
|
notes: typeof body?.notes === "string" ? body.notes : void 0
|
|
33478
33632
|
};
|
|
33479
33633
|
const filePath = path25.join(fixtureDir, `${name}.json`);
|
|
33480
|
-
|
|
33634
|
+
fs14.writeFileSync(filePath, JSON.stringify(fixture, null, 2));
|
|
33481
33635
|
ctx.json(res, 200, {
|
|
33482
33636
|
saved: true,
|
|
33483
33637
|
name,
|
|
@@ -33495,14 +33649,14 @@ async function handleCliFixtureCapture(ctx, req, res) {
|
|
|
33495
33649
|
async function handleCliFixtureList(ctx, type, _req, res) {
|
|
33496
33650
|
try {
|
|
33497
33651
|
const fixtureDir = getCliFixtureDir(ctx, type);
|
|
33498
|
-
if (!
|
|
33652
|
+
if (!fs14.existsSync(fixtureDir)) {
|
|
33499
33653
|
ctx.json(res, 200, { fixtures: [], count: 0 });
|
|
33500
33654
|
return;
|
|
33501
33655
|
}
|
|
33502
|
-
const fixtures =
|
|
33656
|
+
const fixtures = fs14.readdirSync(fixtureDir).filter((file) => file.endsWith(".json")).sort((a, b) => b.localeCompare(a, void 0, { numeric: true, sensitivity: "base" })).map((file) => {
|
|
33503
33657
|
const fullPath = path25.join(fixtureDir, file);
|
|
33504
33658
|
try {
|
|
33505
|
-
const raw = JSON.parse(
|
|
33659
|
+
const raw = JSON.parse(fs14.readFileSync(fullPath, "utf-8"));
|
|
33506
33660
|
return {
|
|
33507
33661
|
name: raw.name || file.replace(/\.json$/i, ""),
|
|
33508
33662
|
path: fullPath,
|
|
@@ -33635,7 +33789,7 @@ async function handleCliRaw(ctx, req, res) {
|
|
|
33635
33789
|
}
|
|
33636
33790
|
|
|
33637
33791
|
// src/daemon/dev-auto-implement.ts
|
|
33638
|
-
var
|
|
33792
|
+
var fs15 = __toESM(require("fs"));
|
|
33639
33793
|
var path26 = __toESM(require("path"));
|
|
33640
33794
|
var os21 = __toESM(require("os"));
|
|
33641
33795
|
function getAutoImplPid(ctx) {
|
|
@@ -33683,10 +33837,10 @@ function resolveAutoImplReference(ctx, category, requestedReference, targetType)
|
|
|
33683
33837
|
return fallback?.type || null;
|
|
33684
33838
|
}
|
|
33685
33839
|
function getLatestScriptVersionDir(scriptsDir) {
|
|
33686
|
-
if (!
|
|
33687
|
-
const versions =
|
|
33840
|
+
if (!fs15.existsSync(scriptsDir)) return null;
|
|
33841
|
+
const versions = fs15.readdirSync(scriptsDir).filter((d) => {
|
|
33688
33842
|
try {
|
|
33689
|
-
return
|
|
33843
|
+
return fs15.statSync(path26.join(scriptsDir, d)).isDirectory();
|
|
33690
33844
|
} catch {
|
|
33691
33845
|
return false;
|
|
33692
33846
|
}
|
|
@@ -33708,13 +33862,13 @@ function resolveAutoImplWritableProviderDir(ctx, category, type, requestedDir) {
|
|
|
33708
33862
|
if (!sourceDir) {
|
|
33709
33863
|
return { dir: null, reason: `Provider source directory not found for '${type}'` };
|
|
33710
33864
|
}
|
|
33711
|
-
if (!
|
|
33712
|
-
|
|
33713
|
-
|
|
33865
|
+
if (!fs15.existsSync(desiredDir)) {
|
|
33866
|
+
fs15.mkdirSync(path26.dirname(desiredDir), { recursive: true });
|
|
33867
|
+
fs15.cpSync(sourceDir, desiredDir, { recursive: true });
|
|
33714
33868
|
ctx.log(`Auto-implement writable copy created: ${desiredDir}`);
|
|
33715
33869
|
}
|
|
33716
33870
|
const providerJson = path26.join(desiredDir, "provider.json");
|
|
33717
|
-
if (!
|
|
33871
|
+
if (!fs15.existsSync(providerJson)) {
|
|
33718
33872
|
return { dir: null, reason: `provider.json not found in writable provider directory: ${desiredDir}` };
|
|
33719
33873
|
}
|
|
33720
33874
|
return { dir: desiredDir };
|
|
@@ -33722,15 +33876,15 @@ function resolveAutoImplWritableProviderDir(ctx, category, type, requestedDir) {
|
|
|
33722
33876
|
function loadAutoImplReferenceScripts(ctx, referenceType) {
|
|
33723
33877
|
if (!referenceType) return {};
|
|
33724
33878
|
const refDir = ctx.findProviderDir(referenceType);
|
|
33725
|
-
if (!refDir || !
|
|
33879
|
+
if (!refDir || !fs15.existsSync(refDir)) return {};
|
|
33726
33880
|
const referenceScripts = {};
|
|
33727
33881
|
const scriptsDir = path26.join(refDir, "scripts");
|
|
33728
33882
|
const latestDir = getLatestScriptVersionDir(scriptsDir);
|
|
33729
33883
|
if (!latestDir) return referenceScripts;
|
|
33730
|
-
for (const file of
|
|
33884
|
+
for (const file of fs15.readdirSync(latestDir)) {
|
|
33731
33885
|
if (!file.endsWith(".js")) continue;
|
|
33732
33886
|
try {
|
|
33733
|
-
referenceScripts[file] =
|
|
33887
|
+
referenceScripts[file] = fs15.readFileSync(path26.join(latestDir, file), "utf-8");
|
|
33734
33888
|
} catch {
|
|
33735
33889
|
}
|
|
33736
33890
|
}
|
|
@@ -33839,15 +33993,15 @@ async function handleAutoImplement(ctx, type, req, res) {
|
|
|
33839
33993
|
const referenceScripts = loadAutoImplReferenceScripts(ctx, resolvedReference);
|
|
33840
33994
|
const prompt = buildAutoImplPrompt(ctx, type, provider, providerDir, functions, domContext, referenceScripts, comment, resolvedReference, verification);
|
|
33841
33995
|
const tmpDir = path26.join(os21.tmpdir(), "adhdev-autoimpl");
|
|
33842
|
-
if (!
|
|
33996
|
+
if (!fs15.existsSync(tmpDir)) fs15.mkdirSync(tmpDir, { recursive: true });
|
|
33843
33997
|
const promptFile = path26.join(tmpDir, `prompt-${type}-${Date.now()}.md`);
|
|
33844
|
-
|
|
33998
|
+
fs15.writeFileSync(promptFile, prompt, "utf-8");
|
|
33845
33999
|
ctx.log(`Auto-implement prompt written to ${promptFile} (${prompt.length} chars)`);
|
|
33846
34000
|
const agentProvider = ctx.providerLoader.resolve(agent) || ctx.providerLoader.getMeta(agent);
|
|
33847
34001
|
const spawn4 = agentProvider?.spawn;
|
|
33848
34002
|
if (!spawn4?.command) {
|
|
33849
34003
|
try {
|
|
33850
|
-
|
|
34004
|
+
fs15.unlinkSync(promptFile);
|
|
33851
34005
|
} catch {
|
|
33852
34006
|
}
|
|
33853
34007
|
ctx.json(res, 400, { error: `Agent '${agent}' has no spawn config. Select a CLI provider with a spawn configuration.` });
|
|
@@ -33949,7 +34103,7 @@ async function handleAutoImplement(ctx, type, req, res) {
|
|
|
33949
34103
|
} catch {
|
|
33950
34104
|
}
|
|
33951
34105
|
try {
|
|
33952
|
-
|
|
34106
|
+
fs15.unlinkSync(promptFile);
|
|
33953
34107
|
} catch {
|
|
33954
34108
|
}
|
|
33955
34109
|
ctx.log(`Auto-implement (ACP) ${success ? "completed" : "failed"}: ${type} (exit: ${code})`);
|
|
@@ -34175,7 +34329,7 @@ async function handleAutoImplement(ctx, type, req, res) {
|
|
|
34175
34329
|
}
|
|
34176
34330
|
});
|
|
34177
34331
|
try {
|
|
34178
|
-
|
|
34332
|
+
fs15.unlinkSync(promptFile);
|
|
34179
34333
|
} catch {
|
|
34180
34334
|
}
|
|
34181
34335
|
ctx.log(`Auto-implement ${success ? "completed" : "failed"}: ${type} (exit: ${code})${verificationSummary ? ` verify=${verificationSummary.pass ? "pass" : "fail"}` : ""}`);
|
|
@@ -34280,10 +34434,10 @@ function buildAutoImplPrompt(ctx, type, provider, providerDir, functions, domCon
|
|
|
34280
34434
|
lines.push("## \u270F\uFE0F Target Files (EDIT THESE)");
|
|
34281
34435
|
lines.push("These are the ONLY files you are allowed to modify. Replace the TODO stubs with working implementations.");
|
|
34282
34436
|
lines.push("");
|
|
34283
|
-
for (const file of
|
|
34437
|
+
for (const file of fs15.readdirSync(latestScriptsDir)) {
|
|
34284
34438
|
if (file.endsWith(".js") && targetFileNames.has(file)) {
|
|
34285
34439
|
try {
|
|
34286
|
-
const content =
|
|
34440
|
+
const content = fs15.readFileSync(path26.join(latestScriptsDir, file), "utf-8");
|
|
34287
34441
|
lines.push(`### \`${file}\` \u270F\uFE0F EDIT`);
|
|
34288
34442
|
lines.push("```javascript");
|
|
34289
34443
|
lines.push(content);
|
|
@@ -34293,14 +34447,14 @@ function buildAutoImplPrompt(ctx, type, provider, providerDir, functions, domCon
|
|
|
34293
34447
|
}
|
|
34294
34448
|
}
|
|
34295
34449
|
}
|
|
34296
|
-
const refFiles =
|
|
34450
|
+
const refFiles = fs15.readdirSync(latestScriptsDir).filter((f) => f.endsWith(".js") && !targetFileNames.has(f));
|
|
34297
34451
|
if (refFiles.length > 0) {
|
|
34298
34452
|
lines.push("## \u{1F512} Other Scripts (REFERENCE ONLY \u2014 DO NOT EDIT)");
|
|
34299
34453
|
lines.push("These files are shown for context only. Do NOT modify them under any circumstances.");
|
|
34300
34454
|
lines.push("");
|
|
34301
34455
|
for (const file of refFiles) {
|
|
34302
34456
|
try {
|
|
34303
|
-
const content =
|
|
34457
|
+
const content = fs15.readFileSync(path26.join(latestScriptsDir, file), "utf-8");
|
|
34304
34458
|
lines.push(`### \`${file}\` \u{1F512}`);
|
|
34305
34459
|
lines.push("```javascript");
|
|
34306
34460
|
lines.push(content);
|
|
@@ -34345,7 +34499,7 @@ function buildAutoImplPrompt(ctx, type, provider, providerDir, functions, domCon
|
|
|
34345
34499
|
const loadGuide = (name) => {
|
|
34346
34500
|
try {
|
|
34347
34501
|
const p = path26.join(docsDir, name);
|
|
34348
|
-
if (
|
|
34502
|
+
if (fs15.existsSync(p)) return fs15.readFileSync(p, "utf-8");
|
|
34349
34503
|
} catch {
|
|
34350
34504
|
}
|
|
34351
34505
|
return null;
|
|
@@ -34589,11 +34743,11 @@ function buildCliAutoImplPrompt(ctx, type, provider, providerDir, functions, ref
|
|
|
34589
34743
|
lines.push("## \u270F\uFE0F Target Files (EDIT THESE)");
|
|
34590
34744
|
lines.push("These are the ONLY files you are allowed to modify. Replace TODO or heuristic-only logic with working PTY-aware implementations.");
|
|
34591
34745
|
lines.push("");
|
|
34592
|
-
for (const file of
|
|
34746
|
+
for (const file of fs15.readdirSync(latestScriptsDir)) {
|
|
34593
34747
|
if (!file.endsWith(".js")) continue;
|
|
34594
34748
|
if (!targetFileNames.has(file)) continue;
|
|
34595
34749
|
try {
|
|
34596
|
-
const content =
|
|
34750
|
+
const content = fs15.readFileSync(path26.join(latestScriptsDir, file), "utf-8");
|
|
34597
34751
|
lines.push(`### \`${file}\` \u270F\uFE0F EDIT`);
|
|
34598
34752
|
lines.push("```javascript");
|
|
34599
34753
|
lines.push(content);
|
|
@@ -34602,14 +34756,14 @@ function buildCliAutoImplPrompt(ctx, type, provider, providerDir, functions, ref
|
|
|
34602
34756
|
} catch {
|
|
34603
34757
|
}
|
|
34604
34758
|
}
|
|
34605
|
-
const refFiles =
|
|
34759
|
+
const refFiles = fs15.readdirSync(latestScriptsDir).filter((f) => f.endsWith(".js") && !targetFileNames.has(f));
|
|
34606
34760
|
if (refFiles.length > 0) {
|
|
34607
34761
|
lines.push("## \u{1F512} Other Scripts (REFERENCE ONLY \u2014 DO NOT EDIT)");
|
|
34608
34762
|
lines.push("These files are shown for context only. Do NOT modify them under any circumstances.");
|
|
34609
34763
|
lines.push("");
|
|
34610
34764
|
for (const file of refFiles) {
|
|
34611
34765
|
try {
|
|
34612
|
-
const content =
|
|
34766
|
+
const content = fs15.readFileSync(path26.join(latestScriptsDir, file), "utf-8");
|
|
34613
34767
|
lines.push(`### \`${file}\` \u{1F512}`);
|
|
34614
34768
|
lines.push("```javascript");
|
|
34615
34769
|
lines.push(content);
|
|
@@ -34646,7 +34800,7 @@ function buildCliAutoImplPrompt(ctx, type, provider, providerDir, functions, ref
|
|
|
34646
34800
|
const loadGuide = (name) => {
|
|
34647
34801
|
try {
|
|
34648
34802
|
const p = path26.join(docsDir, name);
|
|
34649
|
-
if (
|
|
34803
|
+
if (fs15.existsSync(p)) return fs15.readFileSync(p, "utf-8");
|
|
34650
34804
|
} catch {
|
|
34651
34805
|
}
|
|
34652
34806
|
return null;
|
|
@@ -35386,7 +35540,7 @@ var DevServer = class _DevServer {
|
|
|
35386
35540
|
path27.join(process.cwd(), "packages/web-devconsole/dist")
|
|
35387
35541
|
];
|
|
35388
35542
|
for (const dir of candidates) {
|
|
35389
|
-
if (
|
|
35543
|
+
if (fs16.existsSync(path27.join(dir, "index.html"))) return dir;
|
|
35390
35544
|
}
|
|
35391
35545
|
return null;
|
|
35392
35546
|
}
|
|
@@ -35398,7 +35552,7 @@ var DevServer = class _DevServer {
|
|
|
35398
35552
|
}
|
|
35399
35553
|
const htmlPath = path27.join(distDir, "index.html");
|
|
35400
35554
|
try {
|
|
35401
|
-
const html =
|
|
35555
|
+
const html = fs16.readFileSync(htmlPath, "utf-8");
|
|
35402
35556
|
res.writeHead(200, { "Content-Type": "text/html; charset=utf-8" });
|
|
35403
35557
|
res.end(html);
|
|
35404
35558
|
} catch (e) {
|
|
@@ -35428,7 +35582,7 @@ var DevServer = class _DevServer {
|
|
|
35428
35582
|
return;
|
|
35429
35583
|
}
|
|
35430
35584
|
try {
|
|
35431
|
-
const content =
|
|
35585
|
+
const content = fs16.readFileSync(filePath);
|
|
35432
35586
|
const ext = path27.extname(filePath);
|
|
35433
35587
|
const contentType = _DevServer.MIME_MAP[ext] || "application/octet-stream";
|
|
35434
35588
|
res.writeHead(200, { "Content-Type": contentType, "Cache-Control": "public, max-age=31536000, immutable" });
|
|
@@ -35537,14 +35691,14 @@ var DevServer = class _DevServer {
|
|
|
35537
35691
|
const files = [];
|
|
35538
35692
|
const scan = (d, prefix) => {
|
|
35539
35693
|
try {
|
|
35540
|
-
for (const entry of
|
|
35694
|
+
for (const entry of fs16.readdirSync(d, { withFileTypes: true })) {
|
|
35541
35695
|
if (entry.name.startsWith(".") || entry.name.endsWith(".bak")) continue;
|
|
35542
35696
|
const rel = prefix ? `${prefix}/${entry.name}` : entry.name;
|
|
35543
35697
|
if (entry.isDirectory()) {
|
|
35544
35698
|
files.push({ path: rel, size: 0, type: "dir" });
|
|
35545
35699
|
scan(path27.join(d, entry.name), rel);
|
|
35546
35700
|
} else {
|
|
35547
|
-
const stat2 =
|
|
35701
|
+
const stat2 = fs16.statSync(path27.join(d, entry.name));
|
|
35548
35702
|
files.push({ path: rel, size: stat2.size, type: "file" });
|
|
35549
35703
|
}
|
|
35550
35704
|
}
|
|
@@ -35572,11 +35726,11 @@ var DevServer = class _DevServer {
|
|
|
35572
35726
|
this.json(res, 403, { error: "Forbidden" });
|
|
35573
35727
|
return;
|
|
35574
35728
|
}
|
|
35575
|
-
if (!
|
|
35729
|
+
if (!fs16.existsSync(fullPath) || fs16.statSync(fullPath).isDirectory()) {
|
|
35576
35730
|
this.json(res, 404, { error: `File not found: ${filePath}` });
|
|
35577
35731
|
return;
|
|
35578
35732
|
}
|
|
35579
|
-
const content =
|
|
35733
|
+
const content = fs16.readFileSync(fullPath, "utf-8");
|
|
35580
35734
|
this.json(res, 200, { type, path: filePath, content, lines: content.split("\n").length });
|
|
35581
35735
|
}
|
|
35582
35736
|
/** POST /api/providers/:type/file — write a file { path, content } */
|
|
@@ -35598,9 +35752,9 @@ var DevServer = class _DevServer {
|
|
|
35598
35752
|
return;
|
|
35599
35753
|
}
|
|
35600
35754
|
try {
|
|
35601
|
-
if (
|
|
35602
|
-
|
|
35603
|
-
|
|
35755
|
+
if (fs16.existsSync(fullPath)) fs16.copyFileSync(fullPath, fullPath + ".bak");
|
|
35756
|
+
fs16.mkdirSync(path27.dirname(fullPath), { recursive: true });
|
|
35757
|
+
fs16.writeFileSync(fullPath, content, "utf-8");
|
|
35604
35758
|
this.log(`File saved: ${fullPath} (${content.length} chars)`);
|
|
35605
35759
|
this.providerLoader.reload();
|
|
35606
35760
|
this.json(res, 200, { saved: true, path: filePath, chars: content.length });
|
|
@@ -35617,8 +35771,8 @@ var DevServer = class _DevServer {
|
|
|
35617
35771
|
}
|
|
35618
35772
|
for (const name of ["scripts.js", "provider.json"]) {
|
|
35619
35773
|
const p = path27.join(dir, name);
|
|
35620
|
-
if (
|
|
35621
|
-
const source =
|
|
35774
|
+
if (fs16.existsSync(p)) {
|
|
35775
|
+
const source = fs16.readFileSync(p, "utf-8");
|
|
35622
35776
|
this.json(res, 200, { type, path: p, source, lines: source.split("\n").length });
|
|
35623
35777
|
return;
|
|
35624
35778
|
}
|
|
@@ -35637,11 +35791,11 @@ var DevServer = class _DevServer {
|
|
|
35637
35791
|
this.json(res, 404, { error: `Provider not found: ${type}` });
|
|
35638
35792
|
return;
|
|
35639
35793
|
}
|
|
35640
|
-
const target =
|
|
35794
|
+
const target = fs16.existsSync(path27.join(dir, "scripts.js")) ? "scripts.js" : "provider.json";
|
|
35641
35795
|
const targetPath = path27.join(dir, target);
|
|
35642
35796
|
try {
|
|
35643
|
-
if (
|
|
35644
|
-
|
|
35797
|
+
if (fs16.existsSync(targetPath)) fs16.copyFileSync(targetPath, targetPath + ".bak");
|
|
35798
|
+
fs16.writeFileSync(targetPath, source, "utf-8");
|
|
35645
35799
|
this.log(`Saved provider: ${targetPath} (${source.length} chars)`);
|
|
35646
35800
|
this.providerLoader.reload();
|
|
35647
35801
|
this.json(res, 200, { saved: true, path: targetPath, chars: source.length });
|
|
@@ -35786,20 +35940,20 @@ var DevServer = class _DevServer {
|
|
|
35786
35940
|
let targetDir;
|
|
35787
35941
|
targetDir = this.providerLoader.getUserProviderDir(category, type);
|
|
35788
35942
|
const jsonPath = path27.join(targetDir, "provider.json");
|
|
35789
|
-
if (
|
|
35943
|
+
if (fs16.existsSync(jsonPath)) {
|
|
35790
35944
|
this.json(res, 409, { error: `Provider already exists at ${targetDir}`, path: targetDir });
|
|
35791
35945
|
return;
|
|
35792
35946
|
}
|
|
35793
35947
|
try {
|
|
35794
35948
|
const result = generateFiles(type, name, category, { cdpPorts, cli, processName, installPath, binary, extensionId, version, osPaths, processNames });
|
|
35795
|
-
|
|
35796
|
-
|
|
35949
|
+
fs16.mkdirSync(targetDir, { recursive: true });
|
|
35950
|
+
fs16.writeFileSync(jsonPath, result["provider.json"], "utf-8");
|
|
35797
35951
|
const createdFiles = ["provider.json"];
|
|
35798
35952
|
if (result.files) {
|
|
35799
35953
|
for (const [relPath, content] of Object.entries(result.files)) {
|
|
35800
35954
|
const fullPath = path27.join(targetDir, relPath);
|
|
35801
|
-
|
|
35802
|
-
|
|
35955
|
+
fs16.mkdirSync(path27.dirname(fullPath), { recursive: true });
|
|
35956
|
+
fs16.writeFileSync(fullPath, content, "utf-8");
|
|
35803
35957
|
createdFiles.push(relPath);
|
|
35804
35958
|
}
|
|
35805
35959
|
}
|
|
@@ -35848,10 +36002,10 @@ var DevServer = class _DevServer {
|
|
|
35848
36002
|
}
|
|
35849
36003
|
// ─── Phase 2: Auto-Implement Backend ───
|
|
35850
36004
|
getLatestScriptVersionDir(scriptsDir) {
|
|
35851
|
-
if (!
|
|
35852
|
-
const versions =
|
|
36005
|
+
if (!fs16.existsSync(scriptsDir)) return null;
|
|
36006
|
+
const versions = fs16.readdirSync(scriptsDir).filter((d) => {
|
|
35853
36007
|
try {
|
|
35854
|
-
return
|
|
36008
|
+
return fs16.statSync(path27.join(scriptsDir, d)).isDirectory();
|
|
35855
36009
|
} catch {
|
|
35856
36010
|
return false;
|
|
35857
36011
|
}
|
|
@@ -35873,13 +36027,13 @@ var DevServer = class _DevServer {
|
|
|
35873
36027
|
if (!sourceDir) {
|
|
35874
36028
|
return { dir: null, reason: `Provider source directory not found for '${type}'` };
|
|
35875
36029
|
}
|
|
35876
|
-
if (!
|
|
35877
|
-
|
|
35878
|
-
|
|
36030
|
+
if (!fs16.existsSync(desiredDir)) {
|
|
36031
|
+
fs16.mkdirSync(path27.dirname(desiredDir), { recursive: true });
|
|
36032
|
+
fs16.cpSync(sourceDir, desiredDir, { recursive: true });
|
|
35879
36033
|
this.log(`Auto-implement writable copy created: ${desiredDir}`);
|
|
35880
36034
|
}
|
|
35881
36035
|
const providerJson = path27.join(desiredDir, "provider.json");
|
|
35882
|
-
if (!
|
|
36036
|
+
if (!fs16.existsSync(providerJson)) {
|
|
35883
36037
|
return { dir: null, reason: `provider.json not found in writable provider directory: ${desiredDir}` };
|
|
35884
36038
|
}
|
|
35885
36039
|
return { dir: desiredDir };
|
|
@@ -35922,10 +36076,10 @@ var DevServer = class _DevServer {
|
|
|
35922
36076
|
lines.push("## \u270F\uFE0F Target Files (EDIT THESE)");
|
|
35923
36077
|
lines.push("These are the ONLY files you are allowed to modify. Replace the TODO stubs with working implementations.");
|
|
35924
36078
|
lines.push("");
|
|
35925
|
-
for (const file of
|
|
36079
|
+
for (const file of fs16.readdirSync(latestScriptsDir)) {
|
|
35926
36080
|
if (file.endsWith(".js") && targetFileNames.has(file)) {
|
|
35927
36081
|
try {
|
|
35928
|
-
const content =
|
|
36082
|
+
const content = fs16.readFileSync(path27.join(latestScriptsDir, file), "utf-8");
|
|
35929
36083
|
lines.push(`### \`${file}\` \u270F\uFE0F EDIT`);
|
|
35930
36084
|
lines.push("```javascript");
|
|
35931
36085
|
lines.push(content);
|
|
@@ -35935,14 +36089,14 @@ var DevServer = class _DevServer {
|
|
|
35935
36089
|
}
|
|
35936
36090
|
}
|
|
35937
36091
|
}
|
|
35938
|
-
const refFiles =
|
|
36092
|
+
const refFiles = fs16.readdirSync(latestScriptsDir).filter((f) => f.endsWith(".js") && !targetFileNames.has(f));
|
|
35939
36093
|
if (refFiles.length > 0) {
|
|
35940
36094
|
lines.push("## \u{1F512} Other Scripts (REFERENCE ONLY \u2014 DO NOT EDIT)");
|
|
35941
36095
|
lines.push("These files are shown for context only. Do NOT modify them under any circumstances.");
|
|
35942
36096
|
lines.push("");
|
|
35943
36097
|
for (const file of refFiles) {
|
|
35944
36098
|
try {
|
|
35945
|
-
const content =
|
|
36099
|
+
const content = fs16.readFileSync(path27.join(latestScriptsDir, file), "utf-8");
|
|
35946
36100
|
lines.push(`### \`${file}\` \u{1F512}`);
|
|
35947
36101
|
lines.push("```javascript");
|
|
35948
36102
|
lines.push(content);
|
|
@@ -35987,7 +36141,7 @@ var DevServer = class _DevServer {
|
|
|
35987
36141
|
const loadGuide = (name) => {
|
|
35988
36142
|
try {
|
|
35989
36143
|
const p = path27.join(docsDir, name);
|
|
35990
|
-
if (
|
|
36144
|
+
if (fs16.existsSync(p)) return fs16.readFileSync(p, "utf-8");
|
|
35991
36145
|
} catch {
|
|
35992
36146
|
}
|
|
35993
36147
|
return null;
|
|
@@ -36168,11 +36322,11 @@ var DevServer = class _DevServer {
|
|
|
36168
36322
|
lines.push("## \u270F\uFE0F Target Files (EDIT THESE)");
|
|
36169
36323
|
lines.push("These are the ONLY files you are allowed to modify. Replace TODO or heuristic-only logic with working PTY-aware implementations.");
|
|
36170
36324
|
lines.push("");
|
|
36171
|
-
for (const file of
|
|
36325
|
+
for (const file of fs16.readdirSync(latestScriptsDir)) {
|
|
36172
36326
|
if (!file.endsWith(".js")) continue;
|
|
36173
36327
|
if (!targetFileNames.has(file)) continue;
|
|
36174
36328
|
try {
|
|
36175
|
-
const content =
|
|
36329
|
+
const content = fs16.readFileSync(path27.join(latestScriptsDir, file), "utf-8");
|
|
36176
36330
|
lines.push(`### \`${file}\` \u270F\uFE0F EDIT`);
|
|
36177
36331
|
lines.push("```javascript");
|
|
36178
36332
|
lines.push(content);
|
|
@@ -36181,14 +36335,14 @@ var DevServer = class _DevServer {
|
|
|
36181
36335
|
} catch {
|
|
36182
36336
|
}
|
|
36183
36337
|
}
|
|
36184
|
-
const refFiles =
|
|
36338
|
+
const refFiles = fs16.readdirSync(latestScriptsDir).filter((f) => f.endsWith(".js") && !targetFileNames.has(f));
|
|
36185
36339
|
if (refFiles.length > 0) {
|
|
36186
36340
|
lines.push("## \u{1F512} Other Scripts (REFERENCE ONLY \u2014 DO NOT EDIT)");
|
|
36187
36341
|
lines.push("These files are shown for context only. Do NOT modify them under any circumstances.");
|
|
36188
36342
|
lines.push("");
|
|
36189
36343
|
for (const file of refFiles) {
|
|
36190
36344
|
try {
|
|
36191
|
-
const content =
|
|
36345
|
+
const content = fs16.readFileSync(path27.join(latestScriptsDir, file), "utf-8");
|
|
36192
36346
|
lines.push(`### \`${file}\` \u{1F512}`);
|
|
36193
36347
|
lines.push("```javascript");
|
|
36194
36348
|
lines.push(content);
|
|
@@ -36225,7 +36379,7 @@ var DevServer = class _DevServer {
|
|
|
36225
36379
|
const loadGuide = (name) => {
|
|
36226
36380
|
try {
|
|
36227
36381
|
const p = path27.join(docsDir, name);
|
|
36228
|
-
if (
|
|
36382
|
+
if (fs16.existsSync(p)) return fs16.readFileSync(p, "utf-8");
|
|
36229
36383
|
} catch {
|
|
36230
36384
|
}
|
|
36231
36385
|
return null;
|
|
@@ -37002,7 +37156,8 @@ function shouldAutoRestoreHostedSessionsOnStartup(env = process.env) {
|
|
|
37002
37156
|
}
|
|
37003
37157
|
|
|
37004
37158
|
// src/installer.ts
|
|
37005
|
-
var
|
|
37159
|
+
var import_child_process10 = require("child_process");
|
|
37160
|
+
var import_util3 = require("util");
|
|
37006
37161
|
var EXTENSION_CATALOG = [
|
|
37007
37162
|
// AI Agent extensions
|
|
37008
37163
|
{
|
|
@@ -37089,15 +37244,15 @@ var EXTENSION_CATALOG = [
|
|
|
37089
37244
|
apiKeyName: "OpenAI/Anthropic API key"
|
|
37090
37245
|
}
|
|
37091
37246
|
];
|
|
37092
|
-
|
|
37247
|
+
var execAsync4 = (0, import_util3.promisify)(import_child_process10.exec);
|
|
37248
|
+
async function isExtensionInstalled(ide, marketplaceId) {
|
|
37093
37249
|
if (!ide.cliCommand) return false;
|
|
37094
37250
|
try {
|
|
37095
|
-
const
|
|
37251
|
+
const { stdout } = await execAsync4(`"${ide.cliCommand}" --list-extensions`, {
|
|
37096
37252
|
encoding: "utf-8",
|
|
37097
|
-
timeout: 15e3
|
|
37098
|
-
stdio: ["pipe", "pipe", "pipe"]
|
|
37253
|
+
timeout: 15e3
|
|
37099
37254
|
});
|
|
37100
|
-
const installed =
|
|
37255
|
+
const installed = stdout.trim().split("\n").map((e) => e.trim().toLowerCase());
|
|
37101
37256
|
return installed.includes(marketplaceId.toLowerCase());
|
|
37102
37257
|
} catch {
|
|
37103
37258
|
return false;
|
|
@@ -37113,7 +37268,7 @@ async function installExtension(ide, extension) {
|
|
|
37113
37268
|
error: `No CLI command found for ${ide.displayName}. Please install it manually.`
|
|
37114
37269
|
};
|
|
37115
37270
|
}
|
|
37116
|
-
const alreadyInstalled = isExtensionInstalled(ide, extension.marketplaceId);
|
|
37271
|
+
const alreadyInstalled = await isExtensionInstalled(ide, extension.marketplaceId);
|
|
37117
37272
|
if (alreadyInstalled) {
|
|
37118
37273
|
return {
|
|
37119
37274
|
extensionId: extension.id,
|
|
@@ -37129,11 +37284,11 @@ async function installExtension(ide, extension) {
|
|
|
37129
37284
|
const res = await fetch(extension.vsixUrl);
|
|
37130
37285
|
if (res.ok) {
|
|
37131
37286
|
const buffer = Buffer.from(await res.arrayBuffer());
|
|
37132
|
-
const
|
|
37133
|
-
|
|
37287
|
+
const fs17 = await import("fs");
|
|
37288
|
+
fs17.writeFileSync(vsixPath, buffer);
|
|
37134
37289
|
return new Promise((resolve16) => {
|
|
37135
37290
|
const cmd = `"${ide.cliCommand}" --install-extension "${vsixPath}" --force`;
|
|
37136
|
-
(0,
|
|
37291
|
+
(0, import_child_process10.exec)(cmd, { timeout: 6e4 }, (error, _stdout, stderr) => {
|
|
37137
37292
|
resolve16({
|
|
37138
37293
|
extensionId: extension.id,
|
|
37139
37294
|
marketplaceId: extension.marketplaceId,
|
|
@@ -37149,7 +37304,7 @@ async function installExtension(ide, extension) {
|
|
|
37149
37304
|
}
|
|
37150
37305
|
return new Promise((resolve16) => {
|
|
37151
37306
|
const cmd = `"${ide.cliCommand}" --install-extension ${extension.marketplaceId} --force`;
|
|
37152
|
-
(0,
|
|
37307
|
+
(0, import_child_process10.exec)(cmd, { timeout: 6e4 }, (error, stdout, stderr) => {
|
|
37153
37308
|
if (error) {
|
|
37154
37309
|
resolve16({
|
|
37155
37310
|
extensionId: extension.id,
|
|
@@ -37186,7 +37341,7 @@ function launchIDE(ide, workspacePath) {
|
|
|
37186
37341
|
if (!ide.cliCommand) return false;
|
|
37187
37342
|
try {
|
|
37188
37343
|
const args = workspacePath ? `"${workspacePath}"` : "";
|
|
37189
|
-
(0,
|
|
37344
|
+
(0, import_child_process10.exec)(`"${ide.cliCommand}" ${args}`, { timeout: 1e4 });
|
|
37190
37345
|
return true;
|
|
37191
37346
|
} catch {
|
|
37192
37347
|
return false;
|
|
@@ -37622,6 +37777,7 @@ async function shutdownDaemonComponents(components) {
|
|
|
37622
37777
|
getLogLevel,
|
|
37623
37778
|
getMesh,
|
|
37624
37779
|
getMeshByRepo,
|
|
37780
|
+
getMeshQueueRevision,
|
|
37625
37781
|
getMeshQueueStats,
|
|
37626
37782
|
getNpmExecOptions,
|
|
37627
37783
|
getPendingMeshCoordinatorEvents,
|