@sideboard-ai/core 0.1.238 → 0.1.240
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/{agents-6NAPLJU2.js → agents-CDQCQVWU.js} +1 -1
- package/dist/{agents-HJU23LIF.js → agents-PBRIHUYM.js} +1 -1
- package/dist/{chunk-WRUBICEF.js → chunk-3Q4PVZ3U.js} +14 -9
- package/dist/{chunk-E6UJGLPM.js → chunk-JJSHAVJB.js} +337 -144
- package/dist/{chunk-K6UTJOE6.js → chunk-QXYWLO6W.js} +16 -10
- package/dist/{chunk-32DG3DA2.js → chunk-WPNPIDJS.js} +361 -146
- package/dist/index.cjs +539 -300
- package/dist/index.d.cts +40 -5
- package/dist/index.d.ts +40 -5
- package/dist/index.js +25 -3
- package/dist/mcp/run-stdio.cjs +506 -301
- package/dist/mcp/run-stdio.js +3 -3
- package/dist/{orchestrator-HPMDB2SG.js → orchestrator-A2Q5O4W2.js} +2 -2
- package/dist/{orchestrator-AAYKR4AI.js → orchestrator-MIIKXPHH.js} +2 -2
- package/package.json +1 -1
package/dist/mcp/run-stdio.cjs
CHANGED
|
@@ -10212,12 +10212,14 @@ function skillCommandFromInput(input) {
|
|
|
10212
10212
|
}
|
|
10213
10213
|
return void 0;
|
|
10214
10214
|
}
|
|
10215
|
+
function looksLikeComposerSkillExpansion(text7) {
|
|
10216
|
+
const t = text7.trim();
|
|
10217
|
+
return /^## Skill: \//m.test(t) && /Follow this skill for the request above:/i.test(t);
|
|
10218
|
+
}
|
|
10215
10219
|
function looksLikeSkillBody(text7) {
|
|
10216
10220
|
const t = text7.trim();
|
|
10217
10221
|
if (!t) return false;
|
|
10218
|
-
if (
|
|
10219
|
-
return true;
|
|
10220
|
-
}
|
|
10222
|
+
if (looksLikeComposerSkillExpansion(t)) return true;
|
|
10221
10223
|
return skillNameFromFrontmatter(t) != null;
|
|
10222
10224
|
}
|
|
10223
10225
|
function skillNameFromFrontmatter(text7) {
|
|
@@ -10238,11 +10240,13 @@ function isCompactToolName(name) {
|
|
|
10238
10240
|
short
|
|
10239
10241
|
);
|
|
10240
10242
|
}
|
|
10241
|
-
function isContextCompactInProgress(text7) {
|
|
10242
|
-
return /^Compressing context/i.test(text7.trim());
|
|
10243
|
-
}
|
|
10244
10243
|
function isContextCompactDone(text7) {
|
|
10245
|
-
return
|
|
10244
|
+
return /\bContext compressed\b/i.test(text7.trim());
|
|
10245
|
+
}
|
|
10246
|
+
function isContextCompactInProgress(text7) {
|
|
10247
|
+
const t = text7.trim();
|
|
10248
|
+
if (isContextCompactDone(t)) return false;
|
|
10249
|
+
return /^Compressing context/i.test(t);
|
|
10246
10250
|
}
|
|
10247
10251
|
function looksLikeConversationSummary(text7) {
|
|
10248
10252
|
const t = text7.trim();
|
|
@@ -10666,7 +10670,7 @@ function applyAgentEvent(parts, event) {
|
|
|
10666
10670
|
);
|
|
10667
10671
|
}
|
|
10668
10672
|
const acc = next[next.length - 1];
|
|
10669
|
-
if (acc?.type === "text" &&
|
|
10673
|
+
if (acc?.type === "text" && looksLikeComposerSkillExpansion(acc.text)) {
|
|
10670
10674
|
next[next.length - 1] = skillToolFromTextPart(acc, `skill-${next.length}`);
|
|
10671
10675
|
} else if (acc?.type === "text" && looksLikeConversationSummary(acc.text)) {
|
|
10672
10676
|
next[next.length - 1] = compactToolPart(acc.text, `compact-${next.length}`, {
|
|
@@ -11236,10 +11240,10 @@ function eventsFromClaudeSystem(obj) {
|
|
|
11236
11240
|
if (subtype === "api_retry") {
|
|
11237
11241
|
const attempt = obj.attempt;
|
|
11238
11242
|
const max = obj.max_retries;
|
|
11239
|
-
const
|
|
11243
|
+
const delay2 = obj.retry_delay_ms;
|
|
11240
11244
|
return {
|
|
11241
11245
|
type: "thinking",
|
|
11242
|
-
data: `API retry ${attempt ?? "?"}/${max ?? "?"}${typeof
|
|
11246
|
+
data: `API retry ${attempt ?? "?"}/${max ?? "?"}${typeof delay2 === "number" ? ` (wait ${delay2}ms)` : ""}`
|
|
11243
11247
|
};
|
|
11244
11248
|
}
|
|
11245
11249
|
if (subtype === "status") {
|
|
@@ -11254,7 +11258,8 @@ function eventsFromClaudeSystem(obj) {
|
|
|
11254
11258
|
const trigger = meta.trigger ? ` (${meta.trigger})` : "";
|
|
11255
11259
|
const thinking = {
|
|
11256
11260
|
type: "thinking",
|
|
11257
|
-
data: `Context compressed${trigger}
|
|
11261
|
+
data: `Context compressed${trigger}`,
|
|
11262
|
+
replace: true
|
|
11258
11263
|
};
|
|
11259
11264
|
if (meta.postTokens != null && meta.postTokens > 0) {
|
|
11260
11265
|
return [
|
|
@@ -14525,15 +14530,76 @@ var init_request_review = __esm({
|
|
|
14525
14530
|
}
|
|
14526
14531
|
});
|
|
14527
14532
|
|
|
14533
|
+
// src/hook/worktree-run-ports.ts
|
|
14534
|
+
function worktreeRunPortsPath(worktreePath) {
|
|
14535
|
+
return (0, import_node_path38.join)(worktreePath, RUN_PORTS_REL);
|
|
14536
|
+
}
|
|
14537
|
+
function isPort(value) {
|
|
14538
|
+
return typeof value === "number" && Number.isInteger(value) && value > 0 && value <= 65535;
|
|
14539
|
+
}
|
|
14540
|
+
function parseFile(raw) {
|
|
14541
|
+
try {
|
|
14542
|
+
const parsed = JSON.parse(raw);
|
|
14543
|
+
if (!parsed || typeof parsed !== "object") return {};
|
|
14544
|
+
const scripts = parsed.scripts;
|
|
14545
|
+
if (!scripts || typeof scripts !== "object") return {};
|
|
14546
|
+
const next = {};
|
|
14547
|
+
for (const [name, ports] of Object.entries(scripts)) {
|
|
14548
|
+
if (!name || !Array.isArray(ports)) continue;
|
|
14549
|
+
const cleaned = ports.filter(isPort);
|
|
14550
|
+
if (cleaned.length) next[name] = cleaned;
|
|
14551
|
+
}
|
|
14552
|
+
return { scripts: next };
|
|
14553
|
+
} catch {
|
|
14554
|
+
return {};
|
|
14555
|
+
}
|
|
14556
|
+
}
|
|
14557
|
+
function loadWorktreeRunPorts(worktreePath, scriptName) {
|
|
14558
|
+
if (!worktreePath.trim() || !scriptName.trim()) return null;
|
|
14559
|
+
try {
|
|
14560
|
+
const raw = (0, import_node_fs38.readFileSync)(worktreeRunPortsPath(worktreePath), "utf8");
|
|
14561
|
+
const ports = parseFile(raw).scripts?.[scriptName];
|
|
14562
|
+
return ports?.length ? ports : null;
|
|
14563
|
+
} catch {
|
|
14564
|
+
return null;
|
|
14565
|
+
}
|
|
14566
|
+
}
|
|
14567
|
+
function saveWorktreeRunPorts(worktreePath, scriptName, ports) {
|
|
14568
|
+
if (!worktreePath.trim() || !scriptName.trim()) return;
|
|
14569
|
+
const cleaned = ports.filter(isPort);
|
|
14570
|
+
if (!cleaned.length) return;
|
|
14571
|
+
const path = worktreeRunPortsPath(worktreePath);
|
|
14572
|
+
let current = {};
|
|
14573
|
+
try {
|
|
14574
|
+
current = parseFile((0, import_node_fs38.readFileSync)(path, "utf8"));
|
|
14575
|
+
} catch {
|
|
14576
|
+
current = {};
|
|
14577
|
+
}
|
|
14578
|
+
const scripts = { ...current.scripts ?? {} };
|
|
14579
|
+
scripts[scriptName] = cleaned;
|
|
14580
|
+
(0, import_node_fs38.mkdirSync)((0, import_node_path38.dirname)(path), { recursive: true });
|
|
14581
|
+
(0, import_node_fs38.writeFileSync)(path, `${JSON.stringify({ scripts }, null, 2)}
|
|
14582
|
+
`, "utf8");
|
|
14583
|
+
}
|
|
14584
|
+
var import_node_fs38, import_node_path38, RUN_PORTS_REL;
|
|
14585
|
+
var init_worktree_run_ports = __esm({
|
|
14586
|
+
"src/hook/worktree-run-ports.ts"() {
|
|
14587
|
+
"use strict";
|
|
14588
|
+
import_node_fs38 = require("fs");
|
|
14589
|
+
import_node_path38 = require("path");
|
|
14590
|
+
RUN_PORTS_REL = ".context/.sideboard/run-ports.json";
|
|
14591
|
+
}
|
|
14592
|
+
});
|
|
14593
|
+
|
|
14528
14594
|
// src/hook/conductor.ts
|
|
14529
14595
|
function matchSimpleGlob(pattern, name) {
|
|
14530
14596
|
const escaped = pattern.replace(/[.+^${}()|[\]\\]/g, "\\$&").replace(/\*/g, ".*").replace(/\?/g, ".");
|
|
14531
14597
|
return new RegExp(`^${escaped}$`).test(name);
|
|
14532
14598
|
}
|
|
14533
14599
|
function readWorktreeInclude(repoPath) {
|
|
14534
|
-
const path = (0,
|
|
14535
|
-
if (!(0,
|
|
14536
|
-
return (0,
|
|
14600
|
+
const path = (0, import_node_path39.join)(repoPath, ".worktreeinclude");
|
|
14601
|
+
if (!(0, import_node_fs39.existsSync)(path)) return [];
|
|
14602
|
+
return (0, import_node_fs39.readFileSync)(path, "utf8").split("\n").map((l) => l.trim()).filter((l) => l && !l.startsWith("#"));
|
|
14537
14603
|
}
|
|
14538
14604
|
function resolveFilesToCopy(repoPath) {
|
|
14539
14605
|
const fromInclude = readWorktreeInclude(repoPath);
|
|
@@ -14543,10 +14609,10 @@ function resolveFilesToCopy(repoPath) {
|
|
|
14543
14609
|
if (settings?.fileIncludeGlobs?.length) {
|
|
14544
14610
|
const matched = [];
|
|
14545
14611
|
try {
|
|
14546
|
-
for (const entry of (0,
|
|
14612
|
+
for (const entry of (0, import_node_fs39.readdirSync)(repoPath, { withFileTypes: true })) {
|
|
14547
14613
|
if (!entry.isFile()) continue;
|
|
14548
14614
|
for (const glob of settings.fileIncludeGlobs) {
|
|
14549
|
-
if (matchSimpleGlob(glob, entry.name) || matchSimpleGlob((0,
|
|
14615
|
+
if (matchSimpleGlob(glob, entry.name) || matchSimpleGlob((0, import_node_path39.basename)(glob), entry.name)) {
|
|
14550
14616
|
matched.push(entry.name);
|
|
14551
14617
|
break;
|
|
14552
14618
|
}
|
|
@@ -14558,7 +14624,7 @@ function resolveFilesToCopy(repoPath) {
|
|
|
14558
14624
|
}
|
|
14559
14625
|
const defaults = [];
|
|
14560
14626
|
try {
|
|
14561
|
-
for (const entry of (0,
|
|
14627
|
+
for (const entry of (0, import_node_fs39.readdirSync)(repoPath, { withFileTypes: true })) {
|
|
14562
14628
|
if (entry.isFile() && entry.name.startsWith(".env")) {
|
|
14563
14629
|
defaults.push(entry.name);
|
|
14564
14630
|
}
|
|
@@ -14572,11 +14638,11 @@ function copyConfiguredFiles(repoPath, worktreePath) {
|
|
|
14572
14638
|
const patterns = resolveFilesToCopy(repoPath);
|
|
14573
14639
|
const copied = [];
|
|
14574
14640
|
for (const rel of patterns) {
|
|
14575
|
-
const src = (0,
|
|
14576
|
-
if (!(0,
|
|
14577
|
-
const dest = (0,
|
|
14578
|
-
(0,
|
|
14579
|
-
(0,
|
|
14641
|
+
const src = (0, import_node_path39.join)(repoPath, rel);
|
|
14642
|
+
if (!(0, import_node_fs39.existsSync)(src)) continue;
|
|
14643
|
+
const dest = (0, import_node_path39.join)(worktreePath, rel);
|
|
14644
|
+
(0, import_node_fs39.mkdirSync)((0, import_node_path39.dirname)(dest), { recursive: true });
|
|
14645
|
+
(0, import_node_fs39.copyFileSync)(src, dest);
|
|
14580
14646
|
copied.push(rel);
|
|
14581
14647
|
}
|
|
14582
14648
|
return copied;
|
|
@@ -14611,7 +14677,7 @@ function buildWorkspaceScriptEnv(opts, baseEnv) {
|
|
|
14611
14677
|
const env = stripNestedElectronEnv({
|
|
14612
14678
|
...baseEnv ?? process.env
|
|
14613
14679
|
});
|
|
14614
|
-
const name = opts.workspaceName ?? (0,
|
|
14680
|
+
const name = opts.workspaceName ?? (0, import_node_path39.basename)(opts.worktreePath);
|
|
14615
14681
|
const ports = opts.ports ?? [];
|
|
14616
14682
|
const primary = ports[0];
|
|
14617
14683
|
env.SIDEBOARD_WORKSPACE_NAME = name;
|
|
@@ -14651,6 +14717,57 @@ function killableListenerPids(raw, selfPid = process.pid) {
|
|
|
14651
14717
|
}
|
|
14652
14718
|
return pids;
|
|
14653
14719
|
}
|
|
14720
|
+
function listUnixListenerPids(port, selfPid) {
|
|
14721
|
+
try {
|
|
14722
|
+
const raw = (0, import_node_child_process4.execFileSync)("lsof", [`-tiTCP:${port}`, "-sTCP:LISTEN"], {
|
|
14723
|
+
encoding: "utf8",
|
|
14724
|
+
stdio: ["ignore", "pipe", "ignore"],
|
|
14725
|
+
timeout: 2e3
|
|
14726
|
+
});
|
|
14727
|
+
return killableListenerPids(raw, selfPid);
|
|
14728
|
+
} catch {
|
|
14729
|
+
return [];
|
|
14730
|
+
}
|
|
14731
|
+
}
|
|
14732
|
+
function listenerCwd(pid) {
|
|
14733
|
+
if (!Number.isFinite(pid) || pid <= 0) return null;
|
|
14734
|
+
try {
|
|
14735
|
+
const raw = (0, import_node_child_process4.execFileSync)("lsof", ["-a", "-p", String(pid), "-d", "cwd", "-Fn"], {
|
|
14736
|
+
encoding: "utf8",
|
|
14737
|
+
stdio: ["ignore", "pipe", "ignore"],
|
|
14738
|
+
timeout: 2e3
|
|
14739
|
+
});
|
|
14740
|
+
for (const line of raw.split("\n")) {
|
|
14741
|
+
if (line.startsWith("n") && line.length > 1) return line.slice(1);
|
|
14742
|
+
}
|
|
14743
|
+
} catch {
|
|
14744
|
+
}
|
|
14745
|
+
return null;
|
|
14746
|
+
}
|
|
14747
|
+
function realpathOrResolve(path) {
|
|
14748
|
+
try {
|
|
14749
|
+
return (0, import_node_fs39.realpathSync)(path);
|
|
14750
|
+
} catch {
|
|
14751
|
+
return (0, import_node_path39.resolve)(path);
|
|
14752
|
+
}
|
|
14753
|
+
}
|
|
14754
|
+
function isOtherWorktreeListenerCwd(cwd, worktreePath) {
|
|
14755
|
+
const wt = realpathOrResolve(worktreePath);
|
|
14756
|
+
const c = realpathOrResolve(cwd);
|
|
14757
|
+
if (c === wt || c.startsWith(wt + import_node_path39.sep)) return false;
|
|
14758
|
+
const parent = (0, import_node_path39.dirname)(wt);
|
|
14759
|
+
const thisName = (0, import_node_path39.basename)(wt);
|
|
14760
|
+
if (!thisName || c === parent) return false;
|
|
14761
|
+
if (!c.startsWith(parent + import_node_path39.sep)) return false;
|
|
14762
|
+
const first = c.slice(parent.length + 1).split(import_node_path39.sep)[0];
|
|
14763
|
+
return Boolean(first) && first !== thisName;
|
|
14764
|
+
}
|
|
14765
|
+
function signalPid(pid, signal) {
|
|
14766
|
+
try {
|
|
14767
|
+
process.kill(pid, signal);
|
|
14768
|
+
} catch {
|
|
14769
|
+
}
|
|
14770
|
+
}
|
|
14654
14771
|
function killListenersOnPorts(ports) {
|
|
14655
14772
|
const selfPid = process.pid;
|
|
14656
14773
|
for (const port of ports) {
|
|
@@ -14668,26 +14785,32 @@ function killListenersOnPorts(ports) {
|
|
|
14668
14785
|
);
|
|
14669
14786
|
continue;
|
|
14670
14787
|
}
|
|
14671
|
-
|
|
14672
|
-
|
|
14673
|
-
raw = (0, import_node_child_process4.execFileSync)("lsof", [`-tiTCP:${port}`, "-sTCP:LISTEN"], {
|
|
14674
|
-
encoding: "utf8",
|
|
14675
|
-
stdio: ["ignore", "pipe", "ignore"],
|
|
14676
|
-
timeout: 2e3
|
|
14677
|
-
});
|
|
14678
|
-
} catch {
|
|
14679
|
-
continue;
|
|
14680
|
-
}
|
|
14681
|
-
for (const pid of killableListenerPids(raw, selfPid)) {
|
|
14682
|
-
try {
|
|
14683
|
-
process.kill(pid, "SIGTERM");
|
|
14684
|
-
} catch {
|
|
14685
|
-
}
|
|
14788
|
+
for (const pid of listUnixListenerPids(port, selfPid)) {
|
|
14789
|
+
signalPid(pid, "SIGTERM");
|
|
14686
14790
|
}
|
|
14687
14791
|
} catch {
|
|
14688
14792
|
}
|
|
14689
14793
|
}
|
|
14690
14794
|
}
|
|
14795
|
+
function killStaleWorktreeListeners(ports, worktreePath, signal = "SIGTERM") {
|
|
14796
|
+
if (!worktreePath.trim()) {
|
|
14797
|
+
killListenersOnPorts(ports);
|
|
14798
|
+
return;
|
|
14799
|
+
}
|
|
14800
|
+
if (process.platform === "win32") {
|
|
14801
|
+
killListenersOnPorts(ports);
|
|
14802
|
+
return;
|
|
14803
|
+
}
|
|
14804
|
+
const selfPid = process.pid;
|
|
14805
|
+
for (const port of ports) {
|
|
14806
|
+
if (!Number.isFinite(port) || port <= 0) continue;
|
|
14807
|
+
for (const pid of listUnixListenerPids(port, selfPid)) {
|
|
14808
|
+
const cwd = listenerCwd(pid);
|
|
14809
|
+
if (cwd && isOtherWorktreeListenerCwd(cwd, worktreePath)) continue;
|
|
14810
|
+
signalPid(pid, signal);
|
|
14811
|
+
}
|
|
14812
|
+
}
|
|
14813
|
+
}
|
|
14691
14814
|
function killScriptTree(child, ports = []) {
|
|
14692
14815
|
const pid = child.pid;
|
|
14693
14816
|
if (pid) {
|
|
@@ -14849,7 +14972,7 @@ function getRunMode(worktreePath, repoPath) {
|
|
|
14849
14972
|
return loadWorkspaceSettings(worktreePath, repoPath)?.runMode ?? "concurrent";
|
|
14850
14973
|
}
|
|
14851
14974
|
async function reservePort() {
|
|
14852
|
-
return new Promise((
|
|
14975
|
+
return new Promise((resolve2, reject) => {
|
|
14853
14976
|
const server = (0, import_node_net.createServer)();
|
|
14854
14977
|
let released = false;
|
|
14855
14978
|
const release = () => new Promise((res) => {
|
|
@@ -14866,13 +14989,14 @@ async function reservePort() {
|
|
|
14866
14989
|
void release().then(() => reject(new Error("Failed to allocate port")));
|
|
14867
14990
|
return;
|
|
14868
14991
|
}
|
|
14869
|
-
|
|
14992
|
+
resolve2({ port: addr.port, release });
|
|
14870
14993
|
});
|
|
14871
14994
|
server.on("error", reject);
|
|
14872
14995
|
});
|
|
14873
14996
|
}
|
|
14874
14997
|
async function tryReservePort(port) {
|
|
14875
|
-
|
|
14998
|
+
if (!Number.isInteger(port) || port <= 0 || port > 65535) return null;
|
|
14999
|
+
return new Promise((resolve2) => {
|
|
14876
15000
|
const server = (0, import_node_net.createServer)();
|
|
14877
15001
|
let released = false;
|
|
14878
15002
|
const release = () => new Promise((res) => {
|
|
@@ -14883,23 +15007,51 @@ async function tryReservePort(port) {
|
|
|
14883
15007
|
released = true;
|
|
14884
15008
|
server.close(() => res());
|
|
14885
15009
|
});
|
|
14886
|
-
server.once("error", () =>
|
|
15010
|
+
server.once("error", () => {
|
|
15011
|
+
try {
|
|
15012
|
+
server.close();
|
|
15013
|
+
} catch {
|
|
15014
|
+
}
|
|
15015
|
+
resolve2(null);
|
|
15016
|
+
});
|
|
14887
15017
|
server.listen(port, "127.0.0.1", () => {
|
|
14888
|
-
|
|
15018
|
+
resolve2({ port, release });
|
|
14889
15019
|
});
|
|
14890
15020
|
});
|
|
14891
15021
|
}
|
|
14892
|
-
|
|
14893
|
-
|
|
14894
|
-
const
|
|
15022
|
+
function normalizePreferredPorts(ports, size) {
|
|
15023
|
+
if (!ports?.length) return [];
|
|
15024
|
+
const seen = /* @__PURE__ */ new Set();
|
|
15025
|
+
const out = [];
|
|
15026
|
+
for (const p of ports) {
|
|
15027
|
+
if (!Number.isInteger(p) || p <= 0 || p > 65535 || seen.has(p)) continue;
|
|
15028
|
+
seen.add(p);
|
|
15029
|
+
out.push(p);
|
|
15030
|
+
if (out.length >= size) break;
|
|
15031
|
+
}
|
|
15032
|
+
return out;
|
|
15033
|
+
}
|
|
15034
|
+
function delay(ms) {
|
|
15035
|
+
return new Promise((resolve2) => setTimeout(resolve2, ms));
|
|
15036
|
+
}
|
|
15037
|
+
async function fillPortRange(held, size) {
|
|
15038
|
+
if (held.length >= size) return held;
|
|
15039
|
+
const base = held[0]?.port;
|
|
15040
|
+
const taken = new Set(held.map((h) => h.port));
|
|
14895
15041
|
try {
|
|
14896
|
-
|
|
14897
|
-
|
|
14898
|
-
const
|
|
15042
|
+
let offset = 0;
|
|
15043
|
+
while (held.length < size) {
|
|
15044
|
+
const candidate = base != null ? base + offset : null;
|
|
15045
|
+
offset += 1;
|
|
15046
|
+
if (candidate != null && taken.has(candidate)) continue;
|
|
15047
|
+
const next = candidate != null ? await tryReservePort(candidate) : null;
|
|
14899
15048
|
if (next) {
|
|
14900
15049
|
held.push(next);
|
|
15050
|
+
taken.add(next.port);
|
|
14901
15051
|
} else {
|
|
14902
|
-
|
|
15052
|
+
const ephemeral = await reservePort();
|
|
15053
|
+
held.push(ephemeral);
|
|
15054
|
+
taken.add(ephemeral.port);
|
|
14903
15055
|
}
|
|
14904
15056
|
}
|
|
14905
15057
|
return held;
|
|
@@ -14908,11 +15060,59 @@ async function reservePortRange(size = PORT_RANGE_SIZE) {
|
|
|
14908
15060
|
throw err;
|
|
14909
15061
|
}
|
|
14910
15062
|
}
|
|
15063
|
+
async function tryReserveAvailablePorts(ports) {
|
|
15064
|
+
const held = [];
|
|
15065
|
+
for (const port of ports) {
|
|
15066
|
+
const next = await tryReservePort(port);
|
|
15067
|
+
if (next) held.push(next);
|
|
15068
|
+
}
|
|
15069
|
+
return held;
|
|
15070
|
+
}
|
|
15071
|
+
async function reclaimPreferredPorts(ports, worktreePath) {
|
|
15072
|
+
const primary = ports[0];
|
|
15073
|
+
if (primary == null) return null;
|
|
15074
|
+
const takePrimary = async () => {
|
|
15075
|
+
const held2 = await tryReserveAvailablePorts(ports);
|
|
15076
|
+
if (held2.some((h) => h.port === primary)) return held2;
|
|
15077
|
+
await Promise.all(held2.map((h) => h.release()));
|
|
15078
|
+
return null;
|
|
15079
|
+
};
|
|
15080
|
+
let held = await takePrimary();
|
|
15081
|
+
if (held) return held;
|
|
15082
|
+
if (worktreePath) {
|
|
15083
|
+
killStaleWorktreeListeners(ports, worktreePath, "SIGTERM");
|
|
15084
|
+
} else {
|
|
15085
|
+
killListenersOnPorts(ports);
|
|
15086
|
+
}
|
|
15087
|
+
for (let i = 0; i < RECLAIM_TRIES; i++) {
|
|
15088
|
+
await delay(RECLAIM_RETRY_DELAY_MS);
|
|
15089
|
+
held = await takePrimary();
|
|
15090
|
+
if (held) return held;
|
|
15091
|
+
if (i === 2 && worktreePath) {
|
|
15092
|
+
killStaleWorktreeListeners(ports, worktreePath, "SIGKILL");
|
|
15093
|
+
}
|
|
15094
|
+
}
|
|
15095
|
+
return null;
|
|
15096
|
+
}
|
|
15097
|
+
async function reservePortRange(size = PORT_RANGE_SIZE, opts) {
|
|
15098
|
+
const preferred = normalizePreferredPorts(opts?.preferred, size);
|
|
15099
|
+
if (preferred.length) {
|
|
15100
|
+
const reused = await reclaimPreferredPorts(preferred, opts?.worktreePath);
|
|
15101
|
+
if (reused) return fillPortRange(reused, size);
|
|
15102
|
+
}
|
|
15103
|
+
const held = [await reservePort()];
|
|
15104
|
+
return fillPortRange(held, size);
|
|
15105
|
+
}
|
|
14911
15106
|
async function startDevServer(repoPath, worktreePath, onLine, opts) {
|
|
14912
15107
|
const script = getRunScript(worktreePath, repoPath, opts?.scriptName);
|
|
14913
15108
|
if (!script) return null;
|
|
14914
|
-
const
|
|
15109
|
+
const preferred = loadWorktreeRunPorts(worktreePath, script.name) ?? opts?.preferredPorts;
|
|
15110
|
+
const held = await reservePortRange(PORT_RANGE_SIZE, {
|
|
15111
|
+
preferred: preferred ?? void 0,
|
|
15112
|
+
worktreePath
|
|
15113
|
+
});
|
|
14915
15114
|
const ports = held.map((h) => h.port);
|
|
15115
|
+
saveWorktreeRunPorts(worktreePath, script.name, ports);
|
|
14916
15116
|
try {
|
|
14917
15117
|
const handle = await spawnWorkspaceScript(script.command, {
|
|
14918
15118
|
worktreePath,
|
|
@@ -14935,14 +15135,14 @@ async function startDevServer(repoPath, worktreePath, onLine, opts) {
|
|
|
14935
15135
|
throw err;
|
|
14936
15136
|
}
|
|
14937
15137
|
}
|
|
14938
|
-
var
|
|
15138
|
+
var import_node_fs39, import_node_child_process4, import_node_net, import_node_path39, import_execa4, import_node_readline3, PORT_RANGE_SIZE, RECLAIM_RETRY_DELAY_MS, RECLAIM_TRIES, cachedLoginEnv;
|
|
14939
15139
|
var init_conductor = __esm({
|
|
14940
15140
|
"src/hook/conductor.ts"() {
|
|
14941
15141
|
"use strict";
|
|
14942
|
-
|
|
15142
|
+
import_node_fs39 = require("fs");
|
|
14943
15143
|
import_node_child_process4 = require("child_process");
|
|
14944
15144
|
import_node_net = require("net");
|
|
14945
|
-
|
|
15145
|
+
import_node_path39 = require("path");
|
|
14946
15146
|
import_execa4 = require("execa");
|
|
14947
15147
|
import_node_readline3 = require("readline");
|
|
14948
15148
|
init_settings();
|
|
@@ -14953,8 +15153,12 @@ var init_conductor = __esm({
|
|
|
14953
15153
|
init_git_auth_mode();
|
|
14954
15154
|
init_request_review();
|
|
14955
15155
|
init_worktree_exclude();
|
|
15156
|
+
init_worktree_run_ports();
|
|
15157
|
+
init_worktree_run_ports();
|
|
14956
15158
|
init_nested_electron_env();
|
|
14957
15159
|
PORT_RANGE_SIZE = 10;
|
|
15160
|
+
RECLAIM_RETRY_DELAY_MS = 40;
|
|
15161
|
+
RECLAIM_TRIES = 8;
|
|
14958
15162
|
cachedLoginEnv = null;
|
|
14959
15163
|
}
|
|
14960
15164
|
});
|
|
@@ -14992,7 +15196,7 @@ function materialize(mem) {
|
|
|
14992
15196
|
};
|
|
14993
15197
|
}
|
|
14994
15198
|
function setupLogPath(threadId) {
|
|
14995
|
-
return (0,
|
|
15199
|
+
return (0, import_node_path40.join)(threadsDir(), `${threadId}.setup.log.json`);
|
|
14996
15200
|
}
|
|
14997
15201
|
function setupLogKeyForWorktree(worktreePath) {
|
|
14998
15202
|
const norm = normalizeWorktreePath(worktreePath);
|
|
@@ -15010,7 +15214,7 @@ function persistNow(threadId) {
|
|
|
15010
15214
|
const mem = memory.get(threadId);
|
|
15011
15215
|
if (!mem) return;
|
|
15012
15216
|
try {
|
|
15013
|
-
(0,
|
|
15217
|
+
(0, import_node_fs40.writeFileSync)(
|
|
15014
15218
|
setupLogPath(threadId),
|
|
15015
15219
|
`${JSON.stringify(materialize(mem))}
|
|
15016
15220
|
`,
|
|
@@ -15031,9 +15235,9 @@ function schedulePersist(threadId) {
|
|
|
15031
15235
|
}
|
|
15032
15236
|
function loadFromDisk(threadId) {
|
|
15033
15237
|
const path = setupLogPath(threadId);
|
|
15034
|
-
if (!(0,
|
|
15238
|
+
if (!(0, import_node_fs40.existsSync)(path)) return null;
|
|
15035
15239
|
try {
|
|
15036
|
-
const raw = JSON.parse((0,
|
|
15240
|
+
const raw = JSON.parse((0, import_node_fs40.readFileSync)(path, "utf8"));
|
|
15037
15241
|
return {
|
|
15038
15242
|
output: typeof raw.output === "string" ? raw.output : "",
|
|
15039
15243
|
running: Boolean(raw.running),
|
|
@@ -15089,13 +15293,13 @@ function finishSetupLog(threadId, exitCode, source) {
|
|
|
15089
15293
|
persistNow(threadId);
|
|
15090
15294
|
return materialize(mem);
|
|
15091
15295
|
}
|
|
15092
|
-
var import_node_crypto8,
|
|
15296
|
+
var import_node_crypto8, import_node_fs40, import_node_path40, EMPTY, MAX_SETUP_LOG_CHARS, memory, persistTimers, PERSIST_DEBOUNCE_MS;
|
|
15093
15297
|
var init_setup_log = __esm({
|
|
15094
15298
|
"src/store/setup-log.ts"() {
|
|
15095
15299
|
"use strict";
|
|
15096
15300
|
import_node_crypto8 = require("crypto");
|
|
15097
|
-
|
|
15098
|
-
|
|
15301
|
+
import_node_fs40 = require("fs");
|
|
15302
|
+
import_node_path40 = require("path");
|
|
15099
15303
|
init_worktree_labels();
|
|
15100
15304
|
init_paths();
|
|
15101
15305
|
EMPTY = {
|
|
@@ -15140,7 +15344,7 @@ function safeScriptToken(scriptName) {
|
|
|
15140
15344
|
return token || "dev";
|
|
15141
15345
|
}
|
|
15142
15346
|
function runLogPath(key) {
|
|
15143
|
-
return (0,
|
|
15347
|
+
return (0, import_node_path41.join)(threadsDir(), `${key}.run.log.json`);
|
|
15144
15348
|
}
|
|
15145
15349
|
function runLogKeyForWorktree(worktreePath, scriptName) {
|
|
15146
15350
|
const norm = normalizeWorktreePath(worktreePath);
|
|
@@ -15168,7 +15372,7 @@ function persistNow2(key) {
|
|
|
15168
15372
|
const mem = memory2.get(key);
|
|
15169
15373
|
if (!mem) return;
|
|
15170
15374
|
try {
|
|
15171
|
-
(0,
|
|
15375
|
+
(0, import_node_fs41.writeFileSync)(runLogPath(key), `${JSON.stringify(materialize2(mem))}
|
|
15172
15376
|
`, "utf8");
|
|
15173
15377
|
} catch {
|
|
15174
15378
|
}
|
|
@@ -15185,9 +15389,9 @@ function schedulePersist2(key) {
|
|
|
15185
15389
|
}
|
|
15186
15390
|
function loadFromDisk2(key) {
|
|
15187
15391
|
const path = runLogPath(key);
|
|
15188
|
-
if (!(0,
|
|
15392
|
+
if (!(0, import_node_fs41.existsSync)(path)) return null;
|
|
15189
15393
|
try {
|
|
15190
|
-
const raw = JSON.parse((0,
|
|
15394
|
+
const raw = JSON.parse((0, import_node_fs41.readFileSync)(path, "utf8"));
|
|
15191
15395
|
return {
|
|
15192
15396
|
output: typeof raw.output === "string" ? raw.output : "",
|
|
15193
15397
|
running: Boolean(raw.running),
|
|
@@ -15245,13 +15449,13 @@ function finishRunLog(key, exitCode) {
|
|
|
15245
15449
|
function flushRunLog(key) {
|
|
15246
15450
|
persistNow2(key);
|
|
15247
15451
|
}
|
|
15248
|
-
var import_node_crypto9,
|
|
15452
|
+
var import_node_crypto9, import_node_fs41, import_node_path41, EMPTY2, MAX_RUN_LOG_CHARS, DEFAULT_RUN_LOG_TAIL_CHARS, memory2, persistTimers2, PERSIST_DEBOUNCE_MS2;
|
|
15249
15453
|
var init_run_log = __esm({
|
|
15250
15454
|
"src/store/run-log.ts"() {
|
|
15251
15455
|
"use strict";
|
|
15252
15456
|
import_node_crypto9 = require("crypto");
|
|
15253
|
-
|
|
15254
|
-
|
|
15457
|
+
import_node_fs41 = require("fs");
|
|
15458
|
+
import_node_path41 = require("path");
|
|
15255
15459
|
init_worktree_labels();
|
|
15256
15460
|
init_setup_log();
|
|
15257
15461
|
init_paths();
|
|
@@ -15280,9 +15484,9 @@ async function findOrphanWorktrees(repoPaths) {
|
|
|
15280
15484
|
repoPaths?.length ? repoPaths : threads.map((t) => t.repoPath).filter(Boolean)
|
|
15281
15485
|
);
|
|
15282
15486
|
const homeRoot = sideboardWorkspacesDir();
|
|
15283
|
-
if ((0,
|
|
15487
|
+
if ((0, import_node_fs42.existsSync)(homeRoot)) {
|
|
15284
15488
|
try {
|
|
15285
|
-
for (const entry of (0,
|
|
15489
|
+
for (const entry of (0, import_node_fs42.readdirSync)(homeRoot, { withFileTypes: true })) {
|
|
15286
15490
|
if (!entry.isDirectory()) continue;
|
|
15287
15491
|
void entry;
|
|
15288
15492
|
}
|
|
@@ -15292,7 +15496,7 @@ async function findOrphanWorktrees(repoPaths) {
|
|
|
15292
15496
|
const orphans = [];
|
|
15293
15497
|
const seen = /* @__PURE__ */ new Set();
|
|
15294
15498
|
for (const repoPath of repos) {
|
|
15295
|
-
if (!repoPath || !(0,
|
|
15499
|
+
if (!repoPath || !(0, import_node_fs42.existsSync)(repoPath)) continue;
|
|
15296
15500
|
try {
|
|
15297
15501
|
const wts = await listWorktrees(repoPath);
|
|
15298
15502
|
for (const wt of wts) {
|
|
@@ -15303,7 +15507,7 @@ async function findOrphanWorktrees(repoPaths) {
|
|
|
15303
15507
|
seen.add(path);
|
|
15304
15508
|
let mtimeMs = 0;
|
|
15305
15509
|
try {
|
|
15306
|
-
mtimeMs = (0,
|
|
15510
|
+
mtimeMs = (0, import_node_fs42.statSync)(path).mtimeMs;
|
|
15307
15511
|
} catch {
|
|
15308
15512
|
mtimeMs = 0;
|
|
15309
15513
|
}
|
|
@@ -15313,16 +15517,16 @@ async function findOrphanWorktrees(repoPaths) {
|
|
|
15313
15517
|
}
|
|
15314
15518
|
try {
|
|
15315
15519
|
const root = worktreesRoot(repoPath);
|
|
15316
|
-
if ((0,
|
|
15317
|
-
for (const entry of (0,
|
|
15520
|
+
if ((0, import_node_fs42.existsSync)(root)) {
|
|
15521
|
+
for (const entry of (0, import_node_fs42.readdirSync)(root, { withFileTypes: true })) {
|
|
15318
15522
|
if (!entry.isDirectory()) continue;
|
|
15319
|
-
const path = (0,
|
|
15523
|
+
const path = (0, import_node_path42.join)(root, entry.name).replace(/\/$/, "");
|
|
15320
15524
|
if (known.has(path) || seen.has(path)) continue;
|
|
15321
|
-
if (!(0,
|
|
15525
|
+
if (!(0, import_node_fs42.existsSync)((0, import_node_path42.join)(path, ".git"))) continue;
|
|
15322
15526
|
seen.add(path);
|
|
15323
15527
|
let mtimeMs = 0;
|
|
15324
15528
|
try {
|
|
15325
|
-
mtimeMs = (0,
|
|
15529
|
+
mtimeMs = (0, import_node_fs42.statSync)(path).mtimeMs;
|
|
15326
15530
|
} catch {
|
|
15327
15531
|
mtimeMs = Date.now();
|
|
15328
15532
|
}
|
|
@@ -15374,12 +15578,12 @@ function shouldRunWorktreeCleanup(settings = loadAppSettings()) {
|
|
|
15374
15578
|
const elapsed = Date.now() - Date.parse(last);
|
|
15375
15579
|
return elapsed >= intervalHours * 36e5;
|
|
15376
15580
|
}
|
|
15377
|
-
var
|
|
15581
|
+
var import_node_fs42, import_node_path42;
|
|
15378
15582
|
var init_orphan_cleanup = __esm({
|
|
15379
15583
|
"src/git/orphan-cleanup.ts"() {
|
|
15380
15584
|
"use strict";
|
|
15381
|
-
|
|
15382
|
-
|
|
15585
|
+
import_node_fs42 = require("fs");
|
|
15586
|
+
import_node_path42 = require("path");
|
|
15383
15587
|
init_worktree();
|
|
15384
15588
|
init_thread_store();
|
|
15385
15589
|
init_paths();
|
|
@@ -15554,12 +15758,12 @@ async function cloneRepoIntoSideboard(opts) {
|
|
|
15554
15758
|
if (!url) throw new Error("Clone URL is required");
|
|
15555
15759
|
let name = opts.name?.trim();
|
|
15556
15760
|
if (!name) {
|
|
15557
|
-
const leaf = (0,
|
|
15761
|
+
const leaf = (0, import_node_path43.basename)(url.replace(/\/$/, "").replace(/\.git$/, ""));
|
|
15558
15762
|
name = leaf || "repo";
|
|
15559
15763
|
}
|
|
15560
15764
|
name = name.replace(/[^a-zA-Z0-9._-]+/g, "-").replace(/^-+|-+$/g, "") || "repo";
|
|
15561
|
-
const dest = (0,
|
|
15562
|
-
if ((0,
|
|
15765
|
+
const dest = (0, import_node_path43.join)(sideboardReposDir(), name);
|
|
15766
|
+
if ((0, import_node_fs43.existsSync)(dest)) {
|
|
15563
15767
|
const repoPath2 = await resolveRepoRoot(dest);
|
|
15564
15768
|
const workspace2 = await ensureWorkspace(repoPath2);
|
|
15565
15769
|
return { repoPath: repoPath2, workspace: workspace2 };
|
|
@@ -15574,12 +15778,12 @@ async function cloneRepoIntoSideboard(opts) {
|
|
|
15574
15778
|
const workspace = await ensureWorkspace(repoPath);
|
|
15575
15779
|
return { repoPath, workspace };
|
|
15576
15780
|
}
|
|
15577
|
-
var
|
|
15781
|
+
var import_node_fs43, import_node_path43, import_execa6;
|
|
15578
15782
|
var init_clone_repo = __esm({
|
|
15579
15783
|
"src/git/clone-repo.ts"() {
|
|
15580
15784
|
"use strict";
|
|
15581
|
-
|
|
15582
|
-
|
|
15785
|
+
import_node_fs43 = require("fs");
|
|
15786
|
+
import_node_path43 = require("path");
|
|
15583
15787
|
import_execa6 = require("execa");
|
|
15584
15788
|
init_paths();
|
|
15585
15789
|
init_workspaces();
|
|
@@ -15599,11 +15803,11 @@ var init_thread = __esm({
|
|
|
15599
15803
|
|
|
15600
15804
|
// src/store/desktop-host.ts
|
|
15601
15805
|
function desktopHostPidPath() {
|
|
15602
|
-
return (0,
|
|
15806
|
+
return (0, import_node_path44.join)(appDataDir(), "desktop-host.pid");
|
|
15603
15807
|
}
|
|
15604
15808
|
function readDesktopHostPid() {
|
|
15605
15809
|
try {
|
|
15606
|
-
const pid = Number.parseInt((0,
|
|
15810
|
+
const pid = Number.parseInt((0, import_node_fs44.readFileSync)(desktopHostPidPath(), "utf8").trim(), 10);
|
|
15607
15811
|
if (!Number.isFinite(pid) || pid <= 0) return null;
|
|
15608
15812
|
return pid;
|
|
15609
15813
|
} catch {
|
|
@@ -15629,12 +15833,12 @@ function thisProcessShouldDrainAgentQueues() {
|
|
|
15629
15833
|
if (isThisProcessDesktopHost()) return true;
|
|
15630
15834
|
return !isDesktopHostAlive();
|
|
15631
15835
|
}
|
|
15632
|
-
var
|
|
15836
|
+
var import_node_fs44, import_node_path44;
|
|
15633
15837
|
var init_desktop_host = __esm({
|
|
15634
15838
|
"src/store/desktop-host.ts"() {
|
|
15635
15839
|
"use strict";
|
|
15636
|
-
|
|
15637
|
-
|
|
15840
|
+
import_node_fs44 = require("fs");
|
|
15841
|
+
import_node_path44 = require("path");
|
|
15638
15842
|
init_paths();
|
|
15639
15843
|
}
|
|
15640
15844
|
});
|
|
@@ -15760,24 +15964,24 @@ function jobTreeAlive(pid) {
|
|
|
15760
15964
|
return jobAlive(pid) || processGroupAlive(pid);
|
|
15761
15965
|
}
|
|
15762
15966
|
function readIntFile(file) {
|
|
15763
|
-
if (!(0,
|
|
15764
|
-
const n = Number.parseInt((0,
|
|
15967
|
+
if (!(0, import_node_fs45.existsSync)(file)) return null;
|
|
15968
|
+
const n = Number.parseInt((0, import_node_fs45.readFileSync)(file, "utf8").trim(), 10);
|
|
15765
15969
|
return Number.isInteger(n) ? n : null;
|
|
15766
15970
|
}
|
|
15767
15971
|
function jobDir(root, id, legacy = false) {
|
|
15768
|
-
return (0,
|
|
15972
|
+
return (0, import_node_path45.join)(root, legacy ? LEGACY_DETACHED_JOBS_DIR : DETACHED_JOBS_DIR, id);
|
|
15769
15973
|
}
|
|
15770
15974
|
function resolveJobDir(root, id) {
|
|
15771
15975
|
const modern = jobDir(root, id, false);
|
|
15772
|
-
if ((0,
|
|
15976
|
+
if ((0, import_node_fs45.existsSync)(modern)) return modern;
|
|
15773
15977
|
const legacy = jobDir(root, id, true);
|
|
15774
|
-
if ((0,
|
|
15978
|
+
if ((0, import_node_fs45.existsSync)(legacy)) return legacy;
|
|
15775
15979
|
return modern;
|
|
15776
15980
|
}
|
|
15777
15981
|
function listJobIdsIn(root, rel) {
|
|
15778
|
-
const dir = (0,
|
|
15779
|
-
if (!(0,
|
|
15780
|
-
return (0,
|
|
15982
|
+
const dir = (0, import_node_path45.join)(root, rel);
|
|
15983
|
+
if (!(0, import_node_fs45.existsSync)(dir)) return [];
|
|
15984
|
+
return (0, import_node_fs45.readdirSync)(dir, { withFileTypes: true }).filter((e) => e.isDirectory() && JOB_ID_RE.test(e.name)).map((e) => e.name);
|
|
15781
15985
|
}
|
|
15782
15986
|
function listRunningDetachedJobs(worktreePath) {
|
|
15783
15987
|
const root = worktreePath.trim();
|
|
@@ -15789,7 +15993,7 @@ function listRunningDetachedJobs(worktreePath) {
|
|
|
15789
15993
|
const running = [];
|
|
15790
15994
|
for (const id of ids) {
|
|
15791
15995
|
const dir = resolveJobDir(root, id);
|
|
15792
|
-
const pid = readIntFile((0,
|
|
15996
|
+
const pid = readIntFile((0, import_node_path45.join)(dir, "pid"));
|
|
15793
15997
|
if (jobTreeAlive(pid)) running.push(id);
|
|
15794
15998
|
}
|
|
15795
15999
|
return running.sort();
|
|
@@ -15872,8 +16076,8 @@ function planJobContinue(opts) {
|
|
|
15872
16076
|
return { action: "none" };
|
|
15873
16077
|
}
|
|
15874
16078
|
function tailProgress(logFile, maxLines = 12) {
|
|
15875
|
-
if (!(0,
|
|
15876
|
-
const lines = (0,
|
|
16079
|
+
if (!(0, import_node_fs45.existsSync)(logFile)) return "(no log yet)";
|
|
16080
|
+
const lines = (0, import_node_fs45.readFileSync)(logFile, "utf8").split("\n");
|
|
15877
16081
|
return lines.slice(-maxLines).join("\n");
|
|
15878
16082
|
}
|
|
15879
16083
|
function lastProgressLine(progress) {
|
|
@@ -15881,8 +16085,8 @@ function lastProgressLine(progress) {
|
|
|
15881
16085
|
return last ? last.slice(0, 72) : void 0;
|
|
15882
16086
|
}
|
|
15883
16087
|
function readLogLines(file) {
|
|
15884
|
-
if (!(0,
|
|
15885
|
-
const lines = (0,
|
|
16088
|
+
if (!(0, import_node_fs45.existsSync)(file)) return [];
|
|
16089
|
+
const lines = (0, import_node_fs45.readFileSync)(file, "utf8").split("\n");
|
|
15886
16090
|
if (lines.length && lines[lines.length - 1] === "") lines.pop();
|
|
15887
16091
|
return lines;
|
|
15888
16092
|
}
|
|
@@ -15893,15 +16097,15 @@ function takeDelta(logFile, cursorFile) {
|
|
|
15893
16097
|
return { delta: capJobLogDelta(lines.slice(start).join("\n")), nextCursor: lines.length };
|
|
15894
16098
|
}
|
|
15895
16099
|
function snapshotJob(dir) {
|
|
15896
|
-
const pid = readIntFile((0,
|
|
16100
|
+
const pid = readIntFile((0, import_node_path45.join)(dir, "pid"));
|
|
15897
16101
|
const running = jobTreeAlive(pid);
|
|
15898
16102
|
return {
|
|
15899
16103
|
pid,
|
|
15900
16104
|
running,
|
|
15901
|
-
exitCode: readIntFile((0,
|
|
15902
|
-
log: (0,
|
|
15903
|
-
cursor: (0,
|
|
15904
|
-
progress: tailProgress((0,
|
|
16105
|
+
exitCode: readIntFile((0, import_node_path45.join)(dir, "exit")),
|
|
16106
|
+
log: (0, import_node_path45.join)(dir, "log"),
|
|
16107
|
+
cursor: (0, import_node_path45.join)(dir, "present.cursor"),
|
|
16108
|
+
progress: tailProgress((0, import_node_path45.join)(dir, "log"))
|
|
15905
16109
|
};
|
|
15906
16110
|
}
|
|
15907
16111
|
function toResult(id, snap, extra) {
|
|
@@ -15910,8 +16114,8 @@ function toResult(id, snap, extra) {
|
|
|
15910
16114
|
const stillRunning = snap.running && !ok;
|
|
15911
16115
|
const { delta, nextCursor } = takeDelta(snap.log, snap.cursor);
|
|
15912
16116
|
try {
|
|
15913
|
-
(0,
|
|
15914
|
-
(0,
|
|
16117
|
+
(0, import_node_fs45.mkdirSync)((0, import_node_path45.dirname)(snap.cursor), { recursive: true });
|
|
16118
|
+
(0, import_node_fs45.writeFileSync)(snap.cursor, `${nextCursor}
|
|
15915
16119
|
`);
|
|
15916
16120
|
} catch {
|
|
15917
16121
|
}
|
|
@@ -15932,7 +16136,7 @@ function toResult(id, snap, extra) {
|
|
|
15932
16136
|
};
|
|
15933
16137
|
}
|
|
15934
16138
|
async function sleepMs(ms) {
|
|
15935
|
-
await new Promise((
|
|
16139
|
+
await new Promise((resolve2) => setTimeout(resolve2, ms));
|
|
15936
16140
|
}
|
|
15937
16141
|
async function waitForDetachedJob(cwd, id, opts) {
|
|
15938
16142
|
const jobId = sanitizeDetachedJobId(id);
|
|
@@ -15940,7 +16144,7 @@ async function waitForDetachedJob(cwd, id, opts) {
|
|
|
15940
16144
|
const dir = resolveJobDir(root, jobId);
|
|
15941
16145
|
const timeoutMs = mcpWaitForJobTimeoutMs(opts?.timeoutMs);
|
|
15942
16146
|
const sleep = opts?.sleep ?? sleepMs;
|
|
15943
|
-
if (!(0,
|
|
16147
|
+
if (!(0, import_node_fs45.existsSync)(dir)) {
|
|
15944
16148
|
return {
|
|
15945
16149
|
stillRunning: false,
|
|
15946
16150
|
ok: false,
|
|
@@ -15986,10 +16190,10 @@ function killProcessTree(pid, signal) {
|
|
|
15986
16190
|
}
|
|
15987
16191
|
function appendJobLog(logFile, line) {
|
|
15988
16192
|
try {
|
|
15989
|
-
(0,
|
|
16193
|
+
(0, import_node_fs45.mkdirSync)((0, import_node_path45.dirname)(logFile), { recursive: true });
|
|
15990
16194
|
const body = line.endsWith("\n") ? line : `${line}
|
|
15991
16195
|
`;
|
|
15992
|
-
(0,
|
|
16196
|
+
(0, import_node_fs45.appendFileSync)(logFile, body);
|
|
15993
16197
|
} catch {
|
|
15994
16198
|
}
|
|
15995
16199
|
}
|
|
@@ -15999,7 +16203,7 @@ async function stopDetachedJob(cwd, id, opts) {
|
|
|
15999
16203
|
const dir = resolveJobDir(root, jobId);
|
|
16000
16204
|
const sleep = opts?.sleep ?? sleepMs;
|
|
16001
16205
|
const why = opts?.reason?.trim() ?? "";
|
|
16002
|
-
if (!(0,
|
|
16206
|
+
if (!(0, import_node_fs45.existsSync)(dir)) {
|
|
16003
16207
|
return {
|
|
16004
16208
|
stillRunning: false,
|
|
16005
16209
|
ok: false,
|
|
@@ -16035,10 +16239,10 @@ async function stopDetachedJob(cwd, id, opts) {
|
|
|
16035
16239
|
killProcessTree(targetPid, "SIGKILL");
|
|
16036
16240
|
await sleep(100);
|
|
16037
16241
|
}
|
|
16038
|
-
const exitFile = (0,
|
|
16039
|
-
if (!(0,
|
|
16242
|
+
const exitFile = (0, import_node_path45.join)(dir, "exit");
|
|
16243
|
+
if (!(0, import_node_fs45.existsSync)(exitFile)) {
|
|
16040
16244
|
try {
|
|
16041
|
-
(0,
|
|
16245
|
+
(0, import_node_fs45.writeFileSync)(exitFile, "1\n");
|
|
16042
16246
|
} catch {
|
|
16043
16247
|
}
|
|
16044
16248
|
}
|
|
@@ -16058,12 +16262,12 @@ async function stopDetachedJob(cwd, id, opts) {
|
|
|
16058
16262
|
hint: stopped ? MCP_STOP_JOB_HINT : MCP_WAIT_JOB_STILL_RUNNING_HINT
|
|
16059
16263
|
};
|
|
16060
16264
|
}
|
|
16061
|
-
var
|
|
16265
|
+
var import_node_fs45, import_node_path45, MAX_JOB_CONTINUES, MAX_JOB_DELTA_LINES, MAX_JOB_DELTA_CHARS, DEFERRED_DONE_MAX_CHARS, GH_WATCH_REFRESH, MCP_WAIT_JOB_STILL_RUNNING_HINT, MCP_STOP_JOB_HINT, JOB_ID_RE;
|
|
16062
16266
|
var init_wait_for_job = __esm({
|
|
16063
16267
|
"src/mcp/wait-for-job.ts"() {
|
|
16064
16268
|
"use strict";
|
|
16065
|
-
|
|
16066
|
-
|
|
16269
|
+
import_node_fs45 = require("fs");
|
|
16270
|
+
import_node_path45 = require("path");
|
|
16067
16271
|
init_workspace_scratch();
|
|
16068
16272
|
init_wait_for_turn();
|
|
16069
16273
|
MAX_JOB_CONTINUES = 8;
|
|
@@ -16798,14 +17002,14 @@ async function startAbleTimeOAuth(opts) {
|
|
|
16798
17002
|
const pkce = createAbleTimePkce();
|
|
16799
17003
|
const authorizeUrl = ableTimeOAuthAuthorizeUrl(clientId, state, pkce.challenge, host);
|
|
16800
17004
|
const timeoutMs = opts?.timeoutMs ?? 5 * 6e4;
|
|
16801
|
-
const code = await new Promise((
|
|
17005
|
+
const code = await new Promise((resolve2, reject) => {
|
|
16802
17006
|
let settled = false;
|
|
16803
17007
|
const finish = (err, value) => {
|
|
16804
17008
|
if (settled) return;
|
|
16805
17009
|
settled = true;
|
|
16806
17010
|
cleanup();
|
|
16807
17011
|
if (err) reject(err);
|
|
16808
|
-
else
|
|
17012
|
+
else resolve2(value);
|
|
16809
17013
|
};
|
|
16810
17014
|
const server = (0, import_node_http.createServer)((req, res) => {
|
|
16811
17015
|
try {
|
|
@@ -18098,7 +18302,7 @@ function reuseLiveThread(input, repoPath, match) {
|
|
|
18098
18302
|
}
|
|
18099
18303
|
async function createThread(input, _onSetupLine) {
|
|
18100
18304
|
const repoPath = await resolveRepoRoot(input.repoPath);
|
|
18101
|
-
if (!(0,
|
|
18305
|
+
if (!(0, import_node_fs46.existsSync)(repoPath)) {
|
|
18102
18306
|
throw new Error(`Repo not found: ${repoPath}`);
|
|
18103
18307
|
}
|
|
18104
18308
|
const reused = reuseLiveThread(input, repoPath, {
|
|
@@ -18274,11 +18478,11 @@ async function createThread(input, _onSetupLine) {
|
|
|
18274
18478
|
await ensureWorkspace(repoPath);
|
|
18275
18479
|
return readThread(thread.id) ?? thread;
|
|
18276
18480
|
}
|
|
18277
|
-
var
|
|
18481
|
+
var import_node_fs46;
|
|
18278
18482
|
var init_create = __esm({
|
|
18279
18483
|
"src/threads/create.ts"() {
|
|
18280
18484
|
"use strict";
|
|
18281
|
-
|
|
18485
|
+
import_node_fs46 = require("fs");
|
|
18282
18486
|
init_detect();
|
|
18283
18487
|
init_worktree();
|
|
18284
18488
|
init_home_board();
|
|
@@ -18430,20 +18634,20 @@ function writeTurnLive(threadId, progress) {
|
|
|
18430
18634
|
const path = threadLivePath(threadId);
|
|
18431
18635
|
const tmp = `${path}.${process.pid}.tmp`;
|
|
18432
18636
|
try {
|
|
18433
|
-
(0,
|
|
18434
|
-
(0,
|
|
18637
|
+
(0, import_node_fs47.writeFileSync)(tmp, JSON.stringify(progress), "utf8");
|
|
18638
|
+
(0, import_node_fs47.renameSync)(tmp, path);
|
|
18435
18639
|
} catch {
|
|
18436
18640
|
try {
|
|
18437
|
-
(0,
|
|
18641
|
+
(0, import_node_fs47.unlinkSync)(tmp);
|
|
18438
18642
|
} catch {
|
|
18439
18643
|
}
|
|
18440
18644
|
}
|
|
18441
18645
|
}
|
|
18442
18646
|
function readTurnLive(threadId) {
|
|
18443
18647
|
const path = threadLivePath(threadId);
|
|
18444
|
-
if (!(0,
|
|
18648
|
+
if (!(0, import_node_fs47.existsSync)(path)) return null;
|
|
18445
18649
|
try {
|
|
18446
|
-
const raw = JSON.parse((0,
|
|
18650
|
+
const raw = JSON.parse((0, import_node_fs47.readFileSync)(path, "utf8"));
|
|
18447
18651
|
if (!raw || typeof raw.summary !== "string") return null;
|
|
18448
18652
|
return raw;
|
|
18449
18653
|
} catch {
|
|
@@ -18455,17 +18659,17 @@ function clearTurnLive(threadId) {
|
|
|
18455
18659
|
if (buf?.timer) clearTimeout(buf.timer);
|
|
18456
18660
|
buffers.delete(threadId);
|
|
18457
18661
|
const path = threadLivePath(threadId);
|
|
18458
|
-
if (!(0,
|
|
18662
|
+
if (!(0, import_node_fs47.existsSync)(path)) return;
|
|
18459
18663
|
try {
|
|
18460
|
-
(0,
|
|
18664
|
+
(0, import_node_fs47.unlinkSync)(path);
|
|
18461
18665
|
} catch {
|
|
18462
18666
|
}
|
|
18463
18667
|
}
|
|
18464
|
-
var
|
|
18668
|
+
var import_node_fs47, buffers, FLUSH_MS, MAX_PARTS;
|
|
18465
18669
|
var init_turn_live = __esm({
|
|
18466
18670
|
"src/store/turn-live.ts"() {
|
|
18467
18671
|
"use strict";
|
|
18468
|
-
|
|
18672
|
+
import_node_fs47 = require("fs");
|
|
18469
18673
|
init_message_parts();
|
|
18470
18674
|
init_paths();
|
|
18471
18675
|
buffers = /* @__PURE__ */ new Map();
|
|
@@ -18706,7 +18910,7 @@ var init_quota_failover = __esm({
|
|
|
18706
18910
|
// src/threads/adopt.ts
|
|
18707
18911
|
function thisModuleFile2() {
|
|
18708
18912
|
const cjsFile = typeof __filename !== "undefined" ? __filename : "";
|
|
18709
|
-
return cjsFile || process.argv[1] || (0,
|
|
18913
|
+
return cjsFile || process.argv[1] || (0, import_node_path46.join)(process.cwd(), "package.json");
|
|
18710
18914
|
}
|
|
18711
18915
|
function openReadonlySqlite(file) {
|
|
18712
18916
|
const req = (0, import_node_module5.createRequire)(thisModuleFile2());
|
|
@@ -18724,21 +18928,21 @@ function mapAgentType(raw) {
|
|
|
18724
18928
|
return null;
|
|
18725
18929
|
}
|
|
18726
18930
|
function resolveConductorCursorAgentId(workspacePath) {
|
|
18727
|
-
if (!workspacePath || !(0,
|
|
18931
|
+
if (!workspacePath || !(0, import_node_fs48.existsSync)(CURSOR_SDK_STORE)) return null;
|
|
18728
18932
|
const normalized = workspacePath.replace(/\/$/, "");
|
|
18729
18933
|
let best = null;
|
|
18730
18934
|
let hashes;
|
|
18731
18935
|
try {
|
|
18732
|
-
hashes = (0,
|
|
18936
|
+
hashes = (0, import_node_fs48.readdirSync)(CURSOR_SDK_STORE);
|
|
18733
18937
|
} catch {
|
|
18734
18938
|
return null;
|
|
18735
18939
|
}
|
|
18736
18940
|
for (const hash of hashes) {
|
|
18737
|
-
const agentsFile = (0,
|
|
18738
|
-
if (!(0,
|
|
18941
|
+
const agentsFile = (0, import_node_path46.join)(CURSOR_SDK_STORE, hash, "agents.ndjson");
|
|
18942
|
+
if (!(0, import_node_fs48.existsSync)(agentsFile)) continue;
|
|
18739
18943
|
let text7;
|
|
18740
18944
|
try {
|
|
18741
|
-
text7 = (0,
|
|
18945
|
+
text7 = (0, import_node_fs48.readFileSync)(agentsFile, "utf8");
|
|
18742
18946
|
} catch {
|
|
18743
18947
|
continue;
|
|
18744
18948
|
}
|
|
@@ -18762,7 +18966,7 @@ function resolveConductorCursorAgentId(workspacePath) {
|
|
|
18762
18966
|
return best?.agentId ?? null;
|
|
18763
18967
|
}
|
|
18764
18968
|
async function adoptThread(input) {
|
|
18765
|
-
if (!(0,
|
|
18969
|
+
if (!(0, import_node_fs48.existsSync)(input.worktreePath)) {
|
|
18766
18970
|
throw new Error(`Worktree not found: ${input.worktreePath}`);
|
|
18767
18971
|
}
|
|
18768
18972
|
const repoPath = await resolveRepoRoot(input.worktreePath);
|
|
@@ -18788,18 +18992,18 @@ async function adoptThread(input) {
|
|
|
18788
18992
|
return thread;
|
|
18789
18993
|
}
|
|
18790
18994
|
function listConductorWorkspaces() {
|
|
18791
|
-
if (!(0,
|
|
18995
|
+
if (!(0, import_node_fs48.existsSync)(CONDUCTOR_DB)) {
|
|
18792
18996
|
throw new Error(`Conductor DB not found at ${CONDUCTOR_DB}`);
|
|
18793
18997
|
}
|
|
18794
|
-
const tmp = (0,
|
|
18795
|
-
const snapshot = (0,
|
|
18998
|
+
const tmp = (0, import_node_fs48.mkdtempSync)((0, import_node_path46.join)((0, import_node_os14.tmpdir)(), "sideboard-conductor-"));
|
|
18999
|
+
const snapshot = (0, import_node_path46.join)(tmp, "conductor.db");
|
|
18796
19000
|
try {
|
|
18797
|
-
(0,
|
|
19001
|
+
(0, import_node_fs48.copyFileSync)(CONDUCTOR_DB, snapshot);
|
|
18798
19002
|
for (const suffix of ["-wal", "-shm"]) {
|
|
18799
19003
|
const src = `${CONDUCTOR_DB}${suffix}`;
|
|
18800
|
-
if ((0,
|
|
19004
|
+
if ((0, import_node_fs48.existsSync)(src)) {
|
|
18801
19005
|
try {
|
|
18802
|
-
(0,
|
|
19006
|
+
(0, import_node_fs48.copyFileSync)(src, `${snapshot}${suffix}`);
|
|
18803
19007
|
} catch {
|
|
18804
19008
|
}
|
|
18805
19009
|
}
|
|
@@ -18875,22 +19079,22 @@ function listConductorWorkspaces() {
|
|
|
18875
19079
|
db.close();
|
|
18876
19080
|
}
|
|
18877
19081
|
} finally {
|
|
18878
|
-
(0,
|
|
19082
|
+
(0, import_node_fs48.rmSync)(tmp, { recursive: true, force: true });
|
|
18879
19083
|
}
|
|
18880
19084
|
}
|
|
18881
19085
|
function importConductorWorkspace(workspaceId) {
|
|
18882
|
-
if (!(0,
|
|
19086
|
+
if (!(0, import_node_fs48.existsSync)(CONDUCTOR_DB)) {
|
|
18883
19087
|
throw new Error(`Conductor DB not found at ${CONDUCTOR_DB}`);
|
|
18884
19088
|
}
|
|
18885
|
-
const tmp = (0,
|
|
18886
|
-
const snapshot = (0,
|
|
19089
|
+
const tmp = (0, import_node_fs48.mkdtempSync)((0, import_node_path46.join)((0, import_node_os14.tmpdir)(), "sideboard-conductor-"));
|
|
19090
|
+
const snapshot = (0, import_node_path46.join)(tmp, "conductor.db");
|
|
18887
19091
|
try {
|
|
18888
|
-
(0,
|
|
19092
|
+
(0, import_node_fs48.copyFileSync)(CONDUCTOR_DB, snapshot);
|
|
18889
19093
|
for (const suffix of ["-wal", "-shm"]) {
|
|
18890
19094
|
const src = `${CONDUCTOR_DB}${suffix}`;
|
|
18891
|
-
if ((0,
|
|
19095
|
+
if ((0, import_node_fs48.existsSync)(src)) {
|
|
18892
19096
|
try {
|
|
18893
|
-
(0,
|
|
19097
|
+
(0, import_node_fs48.copyFileSync)(src, `${snapshot}${suffix}`);
|
|
18894
19098
|
} catch {
|
|
18895
19099
|
}
|
|
18896
19100
|
}
|
|
@@ -18908,7 +19112,7 @@ function importConductorWorkspace(workspaceId) {
|
|
|
18908
19112
|
).get(workspaceId);
|
|
18909
19113
|
if (!row) throw new Error(`Conductor workspace not found: ${workspaceId}`);
|
|
18910
19114
|
const worktreePath = String(row.workspacePath);
|
|
18911
|
-
if (!(0,
|
|
19115
|
+
if (!(0, import_node_fs48.existsSync)(worktreePath)) {
|
|
18912
19116
|
throw new Error(`Conductor worktree missing on disk: ${worktreePath}`);
|
|
18913
19117
|
}
|
|
18914
19118
|
let sessionId = null;
|
|
@@ -18971,31 +19175,31 @@ function importConductorWorkspace(workspaceId) {
|
|
|
18971
19175
|
db.close();
|
|
18972
19176
|
}
|
|
18973
19177
|
} finally {
|
|
18974
|
-
(0,
|
|
19178
|
+
(0, import_node_fs48.rmSync)(tmp, { recursive: true, force: true });
|
|
18975
19179
|
}
|
|
18976
19180
|
}
|
|
18977
19181
|
async function importConductorWorkspaceAsync(workspaceId) {
|
|
18978
19182
|
return importConductorWorkspace(workspaceId);
|
|
18979
19183
|
}
|
|
18980
|
-
var import_node_child_process5,
|
|
19184
|
+
var import_node_child_process5, import_node_fs48, import_node_os14, import_node_path46, import_node_module5, CONDUCTOR_APP_SUPPORT, CONDUCTOR_DB, CURSOR_SDK_STORE;
|
|
18981
19185
|
var init_adopt = __esm({
|
|
18982
19186
|
"src/threads/adopt.ts"() {
|
|
18983
19187
|
"use strict";
|
|
18984
19188
|
import_node_child_process5 = require("child_process");
|
|
18985
|
-
|
|
19189
|
+
import_node_fs48 = require("fs");
|
|
18986
19190
|
import_node_os14 = require("os");
|
|
18987
|
-
|
|
19191
|
+
import_node_path46 = require("path");
|
|
18988
19192
|
import_node_module5 = require("module");
|
|
18989
19193
|
init_worktree();
|
|
18990
19194
|
init_thread_store();
|
|
18991
|
-
CONDUCTOR_APP_SUPPORT = (0,
|
|
19195
|
+
CONDUCTOR_APP_SUPPORT = (0, import_node_path46.join)(
|
|
18992
19196
|
process.env.HOME ?? "",
|
|
18993
19197
|
"Library",
|
|
18994
19198
|
"Application Support",
|
|
18995
19199
|
"com.conductor.app"
|
|
18996
19200
|
);
|
|
18997
|
-
CONDUCTOR_DB = (0,
|
|
18998
|
-
CURSOR_SDK_STORE = (0,
|
|
19201
|
+
CONDUCTOR_DB = (0, import_node_path46.join)(CONDUCTOR_APP_SUPPORT, "conductor.db");
|
|
19202
|
+
CURSOR_SDK_STORE = (0, import_node_path46.join)(CONDUCTOR_APP_SUPPORT, "cursor-sdk-store");
|
|
18999
19203
|
}
|
|
19000
19204
|
});
|
|
19001
19205
|
|
|
@@ -19062,7 +19266,7 @@ async function openStackLayer(input, _onSetupLine) {
|
|
|
19062
19266
|
let createdWorktree = false;
|
|
19063
19267
|
const trees = await listWorktrees(repoPath);
|
|
19064
19268
|
const checkedOut = trees.find((w) => w.branch === branchName);
|
|
19065
|
-
if (checkedOut?.path && (0,
|
|
19269
|
+
if (checkedOut?.path && (0, import_node_fs49.existsSync)(checkedOut.path)) {
|
|
19066
19270
|
if (input.reuseExistingWorktree !== false) {
|
|
19067
19271
|
worktreePath = checkedOut.path;
|
|
19068
19272
|
} else {
|
|
@@ -19204,7 +19408,7 @@ async function initStackFromThread(input, onSetupLine) {
|
|
|
19204
19408
|
async function createPrStack(input, onSetupLine) {
|
|
19205
19409
|
await requireAgent(input.agent);
|
|
19206
19410
|
const repoPath = await resolveRepoRoot(input.repoPath);
|
|
19207
|
-
if (!(0,
|
|
19411
|
+
if (!(0, import_node_fs49.existsSync)(repoPath)) throw new Error(`Repo not found: ${repoPath}`);
|
|
19208
19412
|
if (!input.branches.length) throw new Error("At least one branch name required");
|
|
19209
19413
|
const status = await detectGhStack(repoPath);
|
|
19210
19414
|
if (!status.available) throw new Error(status.reason);
|
|
@@ -19271,7 +19475,7 @@ async function createPrStack(input, onSetupLine) {
|
|
|
19271
19475
|
}
|
|
19272
19476
|
}
|
|
19273
19477
|
const claimed = new Set(threads.map((t) => t.worktreePath));
|
|
19274
|
-
if (!claimed.has(bootstrap.worktreePath) && (0,
|
|
19478
|
+
if (!claimed.has(bootstrap.worktreePath) && (0, import_node_fs49.existsSync)(bootstrap.worktreePath)) {
|
|
19275
19479
|
try {
|
|
19276
19480
|
await removeWorktree(repoPath, bootstrap.worktreePath, {
|
|
19277
19481
|
deleteBranch: bootstrap.branchName
|
|
@@ -19281,11 +19485,11 @@ async function createPrStack(input, onSetupLine) {
|
|
|
19281
19485
|
}
|
|
19282
19486
|
return { stack, threads, createdThreadIds };
|
|
19283
19487
|
}
|
|
19284
|
-
var
|
|
19488
|
+
var import_node_fs49;
|
|
19285
19489
|
var init_stack_layers = __esm({
|
|
19286
19490
|
"src/threads/stack-layers.ts"() {
|
|
19287
19491
|
"use strict";
|
|
19288
|
-
|
|
19492
|
+
import_node_fs49 = require("fs");
|
|
19289
19493
|
init_detect();
|
|
19290
19494
|
init_run();
|
|
19291
19495
|
init_stack();
|
|
@@ -19298,7 +19502,7 @@ var init_stack_layers = __esm({
|
|
|
19298
19502
|
|
|
19299
19503
|
// src/diff/diff.ts
|
|
19300
19504
|
async function inspectGitWorktree(worktreePath) {
|
|
19301
|
-
if (!worktreePath || !(0,
|
|
19505
|
+
if (!worktreePath || !(0, import_node_fs50.existsSync)(worktreePath)) return "missing_worktree";
|
|
19302
19506
|
const check = await git(["rev-parse", "--is-inside-work-tree"], worktreePath, {
|
|
19303
19507
|
reject: false
|
|
19304
19508
|
});
|
|
@@ -19306,7 +19510,7 @@ async function inspectGitWorktree(worktreePath) {
|
|
|
19306
19510
|
return "ok";
|
|
19307
19511
|
}
|
|
19308
19512
|
async function initializeGitRepository(worktreePath) {
|
|
19309
|
-
if (!worktreePath || !(0,
|
|
19513
|
+
if (!worktreePath || !(0, import_node_fs50.existsSync)(worktreePath)) {
|
|
19310
19514
|
throw new Error("Worktree not found");
|
|
19311
19515
|
}
|
|
19312
19516
|
const status = await inspectGitWorktree(worktreePath);
|
|
@@ -19440,11 +19644,11 @@ new file mode 100644
|
|
|
19440
19644
|
};
|
|
19441
19645
|
}
|
|
19442
19646
|
async function untrackedPatch(worktreePath, path, maxHunk) {
|
|
19443
|
-
const abs = (0,
|
|
19647
|
+
const abs = (0, import_node_path47.join)(worktreePath, path);
|
|
19444
19648
|
try {
|
|
19445
|
-
const st = (0,
|
|
19649
|
+
const st = (0, import_node_fs50.statSync)(abs);
|
|
19446
19650
|
if (st.isFile() && st.size > maxHunk) {
|
|
19447
|
-
const buf = (0,
|
|
19651
|
+
const buf = (0, import_node_fs50.readFileSync)(abs).subarray(0, maxHunk);
|
|
19448
19652
|
return syntheticAddPatch(path, buf.toString("utf8"), maxHunk);
|
|
19449
19653
|
}
|
|
19450
19654
|
} catch {
|
|
@@ -19911,9 +20115,9 @@ async function getDiff(worktreePath, repoPath, opts) {
|
|
|
19911
20115
|
}
|
|
19912
20116
|
function statWorktreePath(worktreePath, relativePath) {
|
|
19913
20117
|
assertSafeRelativePath(relativePath);
|
|
19914
|
-
const abs = (0,
|
|
19915
|
-
if (!(0,
|
|
19916
|
-
const st = (0,
|
|
20118
|
+
const abs = (0, import_node_path47.join)(worktreePath, relativePath);
|
|
20119
|
+
if (!(0, import_node_fs50.existsSync)(abs)) return "missing";
|
|
20120
|
+
const st = (0, import_node_fs50.statSync)(abs);
|
|
19917
20121
|
if (st.isDirectory()) return "dir";
|
|
19918
20122
|
if (st.isFile()) return "file";
|
|
19919
20123
|
return "missing";
|
|
@@ -19942,8 +20146,8 @@ function isImageRelativePath(relativePath) {
|
|
|
19942
20146
|
function readWorktreeFileForUpload(worktreePath, relativePath, opts) {
|
|
19943
20147
|
assertSafeRelativePath(relativePath);
|
|
19944
20148
|
const maxBytes = opts?.maxBytes ?? DEFAULT_UPLOAD_MAX_BYTES;
|
|
19945
|
-
const abs = (0,
|
|
19946
|
-
const st = (0,
|
|
20149
|
+
const abs = (0, import_node_path47.join)(worktreePath, relativePath);
|
|
20150
|
+
const st = (0, import_node_fs50.statSync)(abs);
|
|
19947
20151
|
if (!st.isFile()) {
|
|
19948
20152
|
throw new Error(`Not a file: ${relativePath}`);
|
|
19949
20153
|
}
|
|
@@ -19952,7 +20156,7 @@ function readWorktreeFileForUpload(worktreePath, relativePath, opts) {
|
|
|
19952
20156
|
`File too large to upload (${st.size} bytes; max ${maxBytes})`
|
|
19953
20157
|
);
|
|
19954
20158
|
}
|
|
19955
|
-
const buf = (0,
|
|
20159
|
+
const buf = (0, import_node_fs50.readFileSync)(abs);
|
|
19956
20160
|
return {
|
|
19957
20161
|
path: relativePath,
|
|
19958
20162
|
contentBase64: buf.toString("base64"),
|
|
@@ -19962,12 +20166,12 @@ function readWorktreeFileForUpload(worktreePath, relativePath, opts) {
|
|
|
19962
20166
|
function readWorktreeFile(worktreePath, relativePath, opts) {
|
|
19963
20167
|
assertSafeRelativePath(relativePath);
|
|
19964
20168
|
const maxBytes = opts?.maxBytes ?? 2e5;
|
|
19965
|
-
const abs = (0,
|
|
19966
|
-
const st = (0,
|
|
20169
|
+
const abs = (0, import_node_path47.join)(worktreePath, relativePath);
|
|
20170
|
+
const st = (0, import_node_fs50.statSync)(abs);
|
|
19967
20171
|
if (!st.isFile()) {
|
|
19968
20172
|
throw new Error(`Not a file: ${relativePath}`);
|
|
19969
20173
|
}
|
|
19970
|
-
const buf = (0,
|
|
20174
|
+
const buf = (0, import_node_fs50.readFileSync)(abs);
|
|
19971
20175
|
if (isImageRelativePath(relativePath)) {
|
|
19972
20176
|
const maxImageBytes = Math.max(maxBytes, 15e6);
|
|
19973
20177
|
const truncated2 = buf.length > maxImageBytes;
|
|
@@ -20010,9 +20214,9 @@ function assertSafeRelativePath(relativePath) {
|
|
|
20010
20214
|
}
|
|
20011
20215
|
function writeWorktreeFile(worktreePath, relativePath, content) {
|
|
20012
20216
|
assertSafeRelativePath(relativePath);
|
|
20013
|
-
const abs = (0,
|
|
20014
|
-
(0,
|
|
20015
|
-
(0,
|
|
20217
|
+
const abs = (0, import_node_path47.join)(worktreePath, relativePath);
|
|
20218
|
+
(0, import_node_fs50.mkdirSync)((0, import_node_path47.dirname)(abs), { recursive: true });
|
|
20219
|
+
(0, import_node_fs50.writeFileSync)(abs, content, "utf8");
|
|
20016
20220
|
return { path: relativePath };
|
|
20017
20221
|
}
|
|
20018
20222
|
async function getWorktreeDirtyStat(worktreePath) {
|
|
@@ -20052,12 +20256,12 @@ async function getDiffSummary(worktreePath, repoPath, opts) {
|
|
|
20052
20256
|
truncated: full.files.length > maxFiles
|
|
20053
20257
|
};
|
|
20054
20258
|
}
|
|
20055
|
-
var
|
|
20259
|
+
var import_node_fs50, import_node_path47, mergeBaseCache, MERGE_BASE_TTL_MS, SHA_RE, IMAGE_EXTENSIONS2, DEFAULT_UPLOAD_MAX_BYTES;
|
|
20056
20260
|
var init_diff = __esm({
|
|
20057
20261
|
"src/diff/diff.ts"() {
|
|
20058
20262
|
"use strict";
|
|
20059
|
-
|
|
20060
|
-
|
|
20263
|
+
import_node_fs50 = require("fs");
|
|
20264
|
+
import_node_path47 = require("path");
|
|
20061
20265
|
init_run();
|
|
20062
20266
|
init_worktree();
|
|
20063
20267
|
mergeBaseCache = /* @__PURE__ */ new Map();
|
|
@@ -20414,7 +20618,7 @@ function parseFrontmatter(content) {
|
|
|
20414
20618
|
}
|
|
20415
20619
|
function readSkill(skillMd, source) {
|
|
20416
20620
|
try {
|
|
20417
|
-
const content = (0,
|
|
20621
|
+
const content = (0, import_node_fs51.readFileSync)(skillMd, "utf8");
|
|
20418
20622
|
const { name: fmName, description } = parseFrontmatter(content);
|
|
20419
20623
|
const dirName = skillMd.split("/").slice(-2, -1)[0] || "skill";
|
|
20420
20624
|
const name = fmName || dirName;
|
|
@@ -20433,19 +20637,19 @@ function readSkill(skillMd, source) {
|
|
|
20433
20637
|
}
|
|
20434
20638
|
}
|
|
20435
20639
|
function scanSkillsDir(dir, source, out) {
|
|
20436
|
-
if (!(0,
|
|
20640
|
+
if (!(0, import_node_fs51.existsSync)(dir)) return;
|
|
20437
20641
|
let entries;
|
|
20438
20642
|
try {
|
|
20439
|
-
entries = (0,
|
|
20643
|
+
entries = (0, import_node_fs51.readdirSync)(dir);
|
|
20440
20644
|
} catch {
|
|
20441
20645
|
return;
|
|
20442
20646
|
}
|
|
20443
20647
|
for (const entry of entries) {
|
|
20444
20648
|
if (entry.startsWith(".")) continue;
|
|
20445
|
-
const skillMd = (0,
|
|
20446
|
-
if (!(0,
|
|
20649
|
+
const skillMd = (0, import_node_path48.join)(dir, entry, "SKILL.md");
|
|
20650
|
+
if (!(0, import_node_fs51.existsSync)(skillMd)) continue;
|
|
20447
20651
|
try {
|
|
20448
|
-
if (!(0,
|
|
20652
|
+
if (!(0, import_node_fs51.statSync)(skillMd).isFile()) continue;
|
|
20449
20653
|
} catch {
|
|
20450
20654
|
continue;
|
|
20451
20655
|
}
|
|
@@ -20454,24 +20658,24 @@ function scanSkillsDir(dir, source, out) {
|
|
|
20454
20658
|
}
|
|
20455
20659
|
}
|
|
20456
20660
|
function scanClaudePluginSkills(pluginsRoot, out) {
|
|
20457
|
-
if (!(0,
|
|
20661
|
+
if (!(0, import_node_fs51.existsSync)(pluginsRoot)) return;
|
|
20458
20662
|
const walk = (dir, depth, lookingForSkillsDir) => {
|
|
20459
20663
|
if (depth > 7) return;
|
|
20460
20664
|
let entries;
|
|
20461
20665
|
try {
|
|
20462
|
-
entries = (0,
|
|
20666
|
+
entries = (0, import_node_fs51.readdirSync)(dir);
|
|
20463
20667
|
} catch {
|
|
20464
20668
|
return;
|
|
20465
20669
|
}
|
|
20466
20670
|
if (lookingForSkillsDir && entries.includes("SKILL.md")) {
|
|
20467
|
-
const skill = readSkill((0,
|
|
20671
|
+
const skill = readSkill((0, import_node_path48.join)(dir, "SKILL.md"), "cli");
|
|
20468
20672
|
if (skill) out.push(skill);
|
|
20469
20673
|
}
|
|
20470
20674
|
for (const entry of entries) {
|
|
20471
20675
|
if (entry === "node_modules" || entry === ".git") continue;
|
|
20472
|
-
const full = (0,
|
|
20676
|
+
const full = (0, import_node_path48.join)(dir, entry);
|
|
20473
20677
|
try {
|
|
20474
|
-
if (!(0,
|
|
20678
|
+
if (!(0, import_node_fs51.statSync)(full).isDirectory()) continue;
|
|
20475
20679
|
} catch {
|
|
20476
20680
|
continue;
|
|
20477
20681
|
}
|
|
@@ -20489,17 +20693,17 @@ function discoverSkills(worktreePath) {
|
|
|
20489
20693
|
const home = (0, import_node_os15.homedir)();
|
|
20490
20694
|
const collected = [];
|
|
20491
20695
|
for (const rel of [".claude/skills", ".cursor/skills", ".sideboard/skills", ".brightsy/skills", "skills"]) {
|
|
20492
|
-
scanSkillsDir((0,
|
|
20696
|
+
scanSkillsDir((0, import_node_path48.join)(worktreePath, rel), "workspace", collected);
|
|
20493
20697
|
}
|
|
20494
20698
|
for (const abs of [
|
|
20495
|
-
(0,
|
|
20496
|
-
(0,
|
|
20497
|
-
(0,
|
|
20498
|
-
(0,
|
|
20699
|
+
(0, import_node_path48.join)(home, ".claude/skills"),
|
|
20700
|
+
(0, import_node_path48.join)(home, ".cursor/skills"),
|
|
20701
|
+
(0, import_node_path48.join)(home, ".sideboard/skills"),
|
|
20702
|
+
(0, import_node_path48.join)(home, ".brightsy/skills")
|
|
20499
20703
|
]) {
|
|
20500
20704
|
scanSkillsDir(abs, "user", collected);
|
|
20501
20705
|
}
|
|
20502
|
-
scanClaudePluginSkills((0,
|
|
20706
|
+
scanClaudePluginSkills((0, import_node_path48.join)(home, ".claude/plugins"), collected);
|
|
20503
20707
|
collected.push(...bundledSkills());
|
|
20504
20708
|
const rank = {
|
|
20505
20709
|
workspace: 0,
|
|
@@ -20525,7 +20729,7 @@ function readSkillBody(skillPath, maxChars = 12e3) {
|
|
|
20525
20729
|
\u2026(truncated)` : body;
|
|
20526
20730
|
}
|
|
20527
20731
|
}
|
|
20528
|
-
const raw = (0,
|
|
20732
|
+
const raw = (0, import_node_fs51.readFileSync)(skillPath, "utf8");
|
|
20529
20733
|
if (raw.startsWith("---")) {
|
|
20530
20734
|
const end = raw.indexOf("\n---", 3);
|
|
20531
20735
|
if (end >= 0) {
|
|
@@ -20539,13 +20743,13 @@ function readSkillBody(skillPath, maxChars = 12e3) {
|
|
|
20539
20743
|
|
|
20540
20744
|
\u2026(truncated)` : raw;
|
|
20541
20745
|
}
|
|
20542
|
-
var
|
|
20746
|
+
var import_node_fs51, import_node_os15, import_node_path48, BUNDLED_SKILL_PREFIX;
|
|
20543
20747
|
var init_discover = __esm({
|
|
20544
20748
|
"src/skills/discover.ts"() {
|
|
20545
20749
|
"use strict";
|
|
20546
|
-
|
|
20750
|
+
import_node_fs51 = require("fs");
|
|
20547
20751
|
import_node_os15 = require("os");
|
|
20548
|
-
|
|
20752
|
+
import_node_path48 = require("path");
|
|
20549
20753
|
init_long_running();
|
|
20550
20754
|
BUNDLED_SKILL_PREFIX = "bundled:";
|
|
20551
20755
|
}
|
|
@@ -20700,7 +20904,7 @@ function compiledModuleDir() {
|
|
|
20700
20904
|
try {
|
|
20701
20905
|
const url = import_meta4.url;
|
|
20702
20906
|
if (typeof url === "string" && url.length > 0) {
|
|
20703
|
-
return (0,
|
|
20907
|
+
return (0, import_node_path49.dirname)((0, import_node_url4.fileURLToPath)(url));
|
|
20704
20908
|
}
|
|
20705
20909
|
} catch {
|
|
20706
20910
|
}
|
|
@@ -20708,8 +20912,8 @@ function compiledModuleDir() {
|
|
|
20708
20912
|
}
|
|
20709
20913
|
function detachedJobScriptIn(dir) {
|
|
20710
20914
|
for (const name of DETACHED_JOB_FILENAMES) {
|
|
20711
|
-
const script = (0,
|
|
20712
|
-
if ((0,
|
|
20915
|
+
const script = (0, import_node_path49.join)(dir, "scripts", name);
|
|
20916
|
+
if ((0, import_node_fs52.existsSync)(script)) return script;
|
|
20713
20917
|
}
|
|
20714
20918
|
return null;
|
|
20715
20919
|
}
|
|
@@ -20726,7 +20930,7 @@ function resolveDetachedJobScript() {
|
|
|
20726
20930
|
for (let i = 0; i < 8; i++) {
|
|
20727
20931
|
const candidate = detachedJobScriptIn(dir);
|
|
20728
20932
|
if (candidate) return candidate;
|
|
20729
|
-
const parent = (0,
|
|
20933
|
+
const parent = (0, import_node_path49.dirname)(dir);
|
|
20730
20934
|
if (parent === dir) break;
|
|
20731
20935
|
dir = parent;
|
|
20732
20936
|
}
|
|
@@ -20737,12 +20941,12 @@ function formatDetachedJobInvoke(scriptPath) {
|
|
|
20737
20941
|
if (resolved) return `node ${JSON.stringify(resolved)}`;
|
|
20738
20942
|
return "node scripts/detached-job.cjs";
|
|
20739
20943
|
}
|
|
20740
|
-
var
|
|
20944
|
+
var import_node_fs52, import_node_path49, import_node_url4, import_meta4, DETACHED_JOB_FILENAMES;
|
|
20741
20945
|
var init_detached_job_path = __esm({
|
|
20742
20946
|
"src/skills/detached-job-path.ts"() {
|
|
20743
20947
|
"use strict";
|
|
20744
|
-
|
|
20745
|
-
|
|
20948
|
+
import_node_fs52 = require("fs");
|
|
20949
|
+
import_node_path49 = require("path");
|
|
20746
20950
|
import_node_url4 = require("url");
|
|
20747
20951
|
init_packaged_runtime();
|
|
20748
20952
|
import_meta4 = {};
|
|
@@ -20843,9 +21047,9 @@ function formatWorktreeDirective(thread, opts) {
|
|
|
20843
21047
|
);
|
|
20844
21048
|
} else {
|
|
20845
21049
|
const slug = opts?.githubSlug ?? "<origin-owner/name>";
|
|
20846
|
-
const
|
|
21050
|
+
const resolve2 = opts?.githubSlug ? "" : " Resolve `<origin-owner/name>` with `git remote get-url origin` in this worktree.";
|
|
20847
21051
|
lines.push(
|
|
20848
|
-
`- Prefer a draft PR first: \`gh pr create --draft -R ${slug}\` (update via \`gh pr edit -R ${slug}\`). Always pass \`-R\` \u2014 bare \`gh pr create\` may target upstream on dual-remote checkouts.${
|
|
21052
|
+
`- Prefer a draft PR first: \`gh pr create --draft -R ${slug}\` (update via \`gh pr edit -R ${slug}\`). Always pass \`-R\` \u2014 bare \`gh pr create\` may target upstream on dual-remote checkouts.${resolve2} Mark ready for review only when asked. If GitHub rejects the body as too long, retry with a short \`--body-file\` \u2014 do not paste a changelog or diff into \`--body\`.`
|
|
20849
21053
|
);
|
|
20850
21054
|
}
|
|
20851
21055
|
lines.push(
|
|
@@ -20932,9 +21136,9 @@ function formatPrGateDirective() {
|
|
|
20932
21136
|
}
|
|
20933
21137
|
function formatProcessGuideDirective(opts) {
|
|
20934
21138
|
const worktree = opts?.worktreePath?.trim();
|
|
20935
|
-
const hasGraphSkill = !!worktree && (0,
|
|
20936
|
-
const hasReviewSkill = !!worktree && (0,
|
|
20937
|
-
const hasInstallSkill = !!worktree && (0,
|
|
21139
|
+
const hasGraphSkill = !!worktree && (0, import_node_fs53.existsSync)((0, import_node_path50.join)(worktree, ".claude/skills/graph-engineering/SKILL.md"));
|
|
21140
|
+
const hasReviewSkill = !!worktree && (0, import_node_fs53.existsSync)((0, import_node_path50.join)(worktree, ".claude/skills/review/SKILL.md"));
|
|
21141
|
+
const hasInstallSkill = !!worktree && (0, import_node_fs53.existsSync)((0, import_node_path50.join)(worktree, ".claude/skills/worktree-install/SKILL.md"));
|
|
20938
21142
|
return [
|
|
20939
21143
|
"Process guides (recurring work only):",
|
|
20940
21144
|
hasGraphSkill ? "- Migrations, ports, batch fixes, and other fan-out: follow `.claude/skills/graph-engineering/SKILL.md` (`/graph-engineering`). Judge first; state on disk; grow the rulebook; do not patch around it." : null,
|
|
@@ -20973,12 +21177,12 @@ function formatArtifactDirective() {
|
|
|
20973
21177
|
function formatUiReminder() {
|
|
20974
21178
|
return "Sideboard UI: markdown table is enough to read data; present_schema if they ask to edit/filter (even after markdown); present_files for the file manager. html fence or present_artifact, not both for the same document. type=log appends (same artifact_id, new lines only). ask_user only for a real multiple-choice (not hellos, \u201Cwhat next?\u201D, or after a review) \u2014 reply in chat. ask_user wakes the parent orchestrator; notify_orchestrator if blocked without a picker. Do not say artifacts/CMS UI are unavailable. Dev / preview: run_dev_script (same as the Dev button) returns {url, port, preview} (SIDEBOARD_PORT \u2014 never guess :3000). preview=url \u2192 open url; preview=window \u2192 Electron window is the app, url is renderer/HMR only. list_run_scripts active[].url if already running; get_run_log for the Run-tab terminal; stop_dev_script to stop.";
|
|
20975
21179
|
}
|
|
20976
|
-
var
|
|
21180
|
+
var import_node_fs53, import_node_path50, PR_GOAL_RE, GITHUB_TICKET_REF, KEYED_TICKET_REF;
|
|
20977
21181
|
var init_instructions = __esm({
|
|
20978
21182
|
"src/agents/instructions.ts"() {
|
|
20979
21183
|
"use strict";
|
|
20980
|
-
|
|
20981
|
-
|
|
21184
|
+
import_node_fs53 = require("fs");
|
|
21185
|
+
import_node_path50 = require("path");
|
|
20982
21186
|
init_git_auth_mode();
|
|
20983
21187
|
init_branch_prefix();
|
|
20984
21188
|
init_worktree_labels();
|
|
@@ -21202,40 +21406,40 @@ __export(plan_file_exports, {
|
|
|
21202
21406
|
writePlanFile: () => writePlanFile
|
|
21203
21407
|
});
|
|
21204
21408
|
function ensureAttachmentsGitignore(worktreePath) {
|
|
21205
|
-
const gitignoreAbs = (0,
|
|
21206
|
-
if ((0,
|
|
21207
|
-
(0,
|
|
21208
|
-
(0,
|
|
21409
|
+
const gitignoreAbs = (0, import_node_path51.join)(worktreePath, ATTACHMENTS_DIR, ".gitignore");
|
|
21410
|
+
if ((0, import_node_fs54.existsSync)(gitignoreAbs)) return;
|
|
21411
|
+
(0, import_node_fs54.mkdirSync)((0, import_node_path51.dirname)(gitignoreAbs), { recursive: true });
|
|
21412
|
+
(0, import_node_fs54.writeFileSync)(gitignoreAbs, attachmentsGitignoreBody(), "utf8");
|
|
21209
21413
|
}
|
|
21210
21414
|
function planFileAbs(worktreePath) {
|
|
21211
|
-
return (0,
|
|
21415
|
+
return (0, import_node_path51.join)(worktreePath, PLAN_FILE_REL);
|
|
21212
21416
|
}
|
|
21213
21417
|
function readTextIfPresent2(abs) {
|
|
21214
|
-
if (!(0,
|
|
21418
|
+
if (!(0, import_node_fs54.existsSync)(abs)) return null;
|
|
21215
21419
|
try {
|
|
21216
|
-
const content = (0,
|
|
21420
|
+
const content = (0, import_node_fs54.readFileSync)(abs, "utf8");
|
|
21217
21421
|
return content.trim() ? content : null;
|
|
21218
21422
|
} catch {
|
|
21219
21423
|
return null;
|
|
21220
21424
|
}
|
|
21221
21425
|
}
|
|
21222
21426
|
function readPlanFile(worktreePath) {
|
|
21223
|
-
return readTextIfPresent2(planFileAbs(worktreePath)) ?? readTextIfPresent2((0,
|
|
21427
|
+
return readTextIfPresent2(planFileAbs(worktreePath)) ?? readTextIfPresent2((0, import_node_path51.join)(worktreePath, `${LEGACY_ATTACHMENTS_DIR}/plan.md`)) ?? readTextIfPresent2((0, import_node_path51.join)(worktreePath, LEGACY_PLAN_FILE_REL));
|
|
21224
21428
|
}
|
|
21225
21429
|
function writePlanFile(worktreePath, content) {
|
|
21226
21430
|
ensureAttachmentsGitignore(worktreePath);
|
|
21227
21431
|
const abs = planFileAbs(worktreePath);
|
|
21228
|
-
(0,
|
|
21432
|
+
(0, import_node_fs54.mkdirSync)((0, import_node_path51.dirname)(abs), { recursive: true });
|
|
21229
21433
|
const body = content.trimEnd() + (content.endsWith("\n") ? "" : "\n");
|
|
21230
|
-
(0,
|
|
21434
|
+
(0, import_node_fs54.writeFileSync)(abs, body, "utf8");
|
|
21231
21435
|
return PLAN_FILE_REL;
|
|
21232
21436
|
}
|
|
21233
|
-
var
|
|
21437
|
+
var import_node_fs54, import_node_path51;
|
|
21234
21438
|
var init_plan_file = __esm({
|
|
21235
21439
|
"src/plan/plan-file.ts"() {
|
|
21236
21440
|
"use strict";
|
|
21237
|
-
|
|
21238
|
-
|
|
21441
|
+
import_node_fs54 = require("fs");
|
|
21442
|
+
import_node_path51 = require("path");
|
|
21239
21443
|
init_workspace_scratch();
|
|
21240
21444
|
init_plan_present();
|
|
21241
21445
|
init_plan_present();
|
|
@@ -21295,7 +21499,7 @@ function setCaffeinateHoldHooks(next) {
|
|
|
21295
21499
|
hooks = next;
|
|
21296
21500
|
}
|
|
21297
21501
|
function caffeinateHoldPath() {
|
|
21298
|
-
return (0,
|
|
21502
|
+
return (0, import_node_path52.join)(appDataDir(), "caffeinate-hold.json");
|
|
21299
21503
|
}
|
|
21300
21504
|
function processAlive(pid) {
|
|
21301
21505
|
if (hooks.processAlive) return hooks.processAlive(pid);
|
|
@@ -21329,9 +21533,9 @@ function uniqueIds(ids) {
|
|
|
21329
21533
|
}
|
|
21330
21534
|
function readHold() {
|
|
21331
21535
|
const path = caffeinateHoldPath();
|
|
21332
|
-
if (!(0,
|
|
21536
|
+
if (!(0, import_node_fs55.existsSync)(path)) return null;
|
|
21333
21537
|
try {
|
|
21334
|
-
const parsed = JSON.parse((0,
|
|
21538
|
+
const parsed = JSON.parse((0, import_node_fs55.readFileSync)(path, "utf8"));
|
|
21335
21539
|
if (typeof parsed?.pid === "number" && parsed.pid > 0) {
|
|
21336
21540
|
return {
|
|
21337
21541
|
pid: parsed.pid,
|
|
@@ -21353,7 +21557,7 @@ function writeHold(pid, threadIds) {
|
|
|
21353
21557
|
}
|
|
21354
21558
|
function clearHold() {
|
|
21355
21559
|
try {
|
|
21356
|
-
(0,
|
|
21560
|
+
(0, import_node_fs55.unlinkSync)(caffeinateHoldPath());
|
|
21357
21561
|
} catch {
|
|
21358
21562
|
}
|
|
21359
21563
|
}
|
|
@@ -21438,13 +21642,13 @@ function releaseCaffeinateHoldForThread(threadId) {
|
|
|
21438
21642
|
}
|
|
21439
21643
|
return setCaffeinateHold(false, { threadId: id });
|
|
21440
21644
|
}
|
|
21441
|
-
var import_node_child_process6,
|
|
21645
|
+
var import_node_child_process6, import_node_fs55, import_node_path52, hooks;
|
|
21442
21646
|
var init_caffeinate_hold = __esm({
|
|
21443
21647
|
"src/store/caffeinate-hold.ts"() {
|
|
21444
21648
|
"use strict";
|
|
21445
21649
|
import_node_child_process6 = require("child_process");
|
|
21446
|
-
|
|
21447
|
-
|
|
21650
|
+
import_node_fs55 = require("fs");
|
|
21651
|
+
import_node_path52 = require("path");
|
|
21448
21652
|
init_paths();
|
|
21449
21653
|
init_private_file();
|
|
21450
21654
|
hooks = {};
|
|
@@ -21453,7 +21657,7 @@ var init_caffeinate_hold = __esm({
|
|
|
21453
21657
|
|
|
21454
21658
|
// src/store/schedules.ts
|
|
21455
21659
|
function schedulesPath() {
|
|
21456
|
-
return (0,
|
|
21660
|
+
return (0, import_node_path53.join)(appDataDir(), "schedules.json");
|
|
21457
21661
|
}
|
|
21458
21662
|
function parseDurationMs(every) {
|
|
21459
21663
|
const m = every.trim().match(DURATION_RE);
|
|
@@ -21553,9 +21757,9 @@ function normalizeTask(raw) {
|
|
|
21553
21757
|
}
|
|
21554
21758
|
function readAll2() {
|
|
21555
21759
|
const path = schedulesPath();
|
|
21556
|
-
if (!(0,
|
|
21760
|
+
if (!(0, import_node_fs56.existsSync)(path)) return [];
|
|
21557
21761
|
try {
|
|
21558
|
-
const parsed = JSON.parse((0,
|
|
21762
|
+
const parsed = JSON.parse((0, import_node_fs56.readFileSync)(path, "utf8"));
|
|
21559
21763
|
if (!Array.isArray(parsed)) return [];
|
|
21560
21764
|
return parsed.map((row) => {
|
|
21561
21765
|
try {
|
|
@@ -21667,13 +21871,13 @@ function recordScheduleRun(id, result) {
|
|
|
21667
21871
|
writeAll2(rows);
|
|
21668
21872
|
return next;
|
|
21669
21873
|
}
|
|
21670
|
-
var import_node_crypto12,
|
|
21874
|
+
var import_node_crypto12, import_node_fs56, import_node_path53, import_croner, DURATION_RE, UNIT_MS;
|
|
21671
21875
|
var init_schedules = __esm({
|
|
21672
21876
|
"src/store/schedules.ts"() {
|
|
21673
21877
|
"use strict";
|
|
21674
21878
|
import_node_crypto12 = require("crypto");
|
|
21675
|
-
|
|
21676
|
-
|
|
21879
|
+
import_node_fs56 = require("fs");
|
|
21880
|
+
import_node_path53 = require("path");
|
|
21677
21881
|
import_croner = require("croner");
|
|
21678
21882
|
init_orchestrator_capable();
|
|
21679
21883
|
init_paths();
|
|
@@ -21759,14 +21963,14 @@ function armOne(schedule) {
|
|
|
21759
21963
|
if (!schedule.enabled) return;
|
|
21760
21964
|
const at = new Date(schedule.nextRunAt);
|
|
21761
21965
|
if (Number.isNaN(at.getTime())) return;
|
|
21762
|
-
const
|
|
21763
|
-
if (
|
|
21966
|
+
const delay2 = Math.max(0, at.getTime() - Date.now());
|
|
21967
|
+
if (delay2 <= 250) {
|
|
21764
21968
|
void fireSchedule(schedule.id).then(() => {
|
|
21765
21969
|
if (isThisProcessDesktopHost()) armSchedules();
|
|
21766
21970
|
});
|
|
21767
21971
|
return;
|
|
21768
21972
|
}
|
|
21769
|
-
const capped = Math.min(
|
|
21973
|
+
const capped = Math.min(delay2, SET_TIMEOUT_MAX);
|
|
21770
21974
|
const timer = setTimeout(() => {
|
|
21771
21975
|
timers.delete(schedule.id);
|
|
21772
21976
|
const live = getSchedule(schedule.id);
|
|
@@ -21829,9 +22033,9 @@ function recoverFinishedCursorRun(opts) {
|
|
|
21829
22033
|
return best;
|
|
21830
22034
|
}
|
|
21831
22035
|
function scanFinishedCursorRuns(runsPath, agentId, startedAfterMs) {
|
|
21832
|
-
if (!(0,
|
|
22036
|
+
if (!(0, import_node_fs57.existsSync)(runsPath)) return null;
|
|
21833
22037
|
try {
|
|
21834
|
-
const lines = (0,
|
|
22038
|
+
const lines = (0, import_node_fs57.readFileSync)(runsPath, "utf8").split("\n");
|
|
21835
22039
|
let best = null;
|
|
21836
22040
|
for (const line of lines) {
|
|
21837
22041
|
const trimmed = line.trim();
|
|
@@ -21857,11 +22061,11 @@ function scanFinishedCursorRuns(runsPath, agentId, startedAfterMs) {
|
|
|
21857
22061
|
return null;
|
|
21858
22062
|
}
|
|
21859
22063
|
}
|
|
21860
|
-
var
|
|
22064
|
+
var import_node_fs57;
|
|
21861
22065
|
var init_cursor_recover = __esm({
|
|
21862
22066
|
"src/agents/cursor-recover.ts"() {
|
|
21863
22067
|
"use strict";
|
|
21864
|
-
|
|
22068
|
+
import_node_fs57 = require("fs");
|
|
21865
22069
|
init_cursor_store();
|
|
21866
22070
|
}
|
|
21867
22071
|
});
|
|
@@ -22015,7 +22219,7 @@ async function startOrchestration(opts) {
|
|
|
22015
22219
|
}
|
|
22016
22220
|
return updated;
|
|
22017
22221
|
}
|
|
22018
|
-
var import_node_events, import_node_crypto13,
|
|
22222
|
+
var import_node_events, import_node_crypto13, import_node_fs58, LIVE_TURN_SPAWN_GRACE_MS, RUN_SCRIPT_DESKTOP_ADOPT_MS, STALE_AGENT_PID_WAIT_MS, LIGHT_RECONCILE_THROTTLE_MS, Orchestrator, singleton;
|
|
22019
22223
|
var init_orchestrator = __esm({
|
|
22020
22224
|
"src/orchestrator/orchestrator.ts"() {
|
|
22021
22225
|
"use strict";
|
|
@@ -22023,7 +22227,7 @@ var init_orchestrator = __esm({
|
|
|
22023
22227
|
init_injected_notices();
|
|
22024
22228
|
init_task_state();
|
|
22025
22229
|
import_node_crypto13 = require("crypto");
|
|
22026
|
-
|
|
22230
|
+
import_node_fs58 = require("fs");
|
|
22027
22231
|
init_error_detail();
|
|
22028
22232
|
init_run();
|
|
22029
22233
|
init_stale_lock();
|
|
@@ -22202,7 +22406,7 @@ var init_orchestrator = __esm({
|
|
|
22202
22406
|
this.lightReconcileAt.set(repoPath, Date.now());
|
|
22203
22407
|
for (const thread of listThreads()) {
|
|
22204
22408
|
if (isGlobalThread(thread) || thread.repoPath !== repoPath) continue;
|
|
22205
|
-
if (!(0,
|
|
22409
|
+
if (!(0, import_node_fs58.existsSync)(thread.worktreePath)) {
|
|
22206
22410
|
setStatus(thread.id, "broken", "Worktree missing on disk");
|
|
22207
22411
|
this.emit({ type: "status_changed", threadId: thread.id, status: "broken" });
|
|
22208
22412
|
}
|
|
@@ -22231,7 +22435,7 @@ var init_orchestrator = __esm({
|
|
|
22231
22435
|
}
|
|
22232
22436
|
continue;
|
|
22233
22437
|
}
|
|
22234
|
-
if (!(0,
|
|
22438
|
+
if (!(0, import_node_fs58.existsSync)(thread.worktreePath)) {
|
|
22235
22439
|
setStatus(thread.id, "broken", "Worktree missing on disk");
|
|
22236
22440
|
this.emit({ type: "status_changed", threadId: thread.id, status: "broken" });
|
|
22237
22441
|
continue;
|
|
@@ -22399,8 +22603,8 @@ var init_orchestrator = __esm({
|
|
|
22399
22603
|
scheduleQuotaResume(threadId, resumeAt) {
|
|
22400
22604
|
this.clearQuotaResumeTimer(threadId);
|
|
22401
22605
|
updateThread(threadId, { quotaResumeAt: resumeAt.toISOString() });
|
|
22402
|
-
const
|
|
22403
|
-
const capped = Math.min(
|
|
22606
|
+
const delay2 = Math.max(5e3, resumeAt.getTime() - Date.now());
|
|
22607
|
+
const capped = Math.min(delay2, 2147483647);
|
|
22404
22608
|
const timer = setTimeout(() => {
|
|
22405
22609
|
this.quotaResumeTimers.delete(threadId);
|
|
22406
22610
|
void this.resumeAfterQuotaWait(threadId);
|
|
@@ -23455,6 +23659,7 @@ var init_orchestrator = __esm({
|
|
|
23455
23659
|
return { port: shared.devPort, scriptName: resolvedName, ports: [shared.devPort] };
|
|
23456
23660
|
}
|
|
23457
23661
|
}
|
|
23662
|
+
const preferredPorts = active?.ports?.length ? active.ports : active?.port != null ? [active.port] : void 0;
|
|
23458
23663
|
if (active && !existing) {
|
|
23459
23664
|
killListenersOnPorts(collectActiveRunPorts([active]));
|
|
23460
23665
|
this.syncWorktreeRuns(
|
|
@@ -23493,7 +23698,7 @@ var init_orchestrator = __esm({
|
|
|
23493
23698
|
thread.repoPath,
|
|
23494
23699
|
thread.worktreePath,
|
|
23495
23700
|
runOutput.push,
|
|
23496
|
-
{ scriptName: resolvedName }
|
|
23701
|
+
{ scriptName: resolvedName, preferredPorts }
|
|
23497
23702
|
);
|
|
23498
23703
|
} catch (err) {
|
|
23499
23704
|
runOutput.flush();
|
|
@@ -23942,7 +24147,7 @@ var init_orchestrator = __esm({
|
|
|
23942
24147
|
return thread;
|
|
23943
24148
|
}
|
|
23944
24149
|
const start = Date.now();
|
|
23945
|
-
return new Promise((
|
|
24150
|
+
return new Promise((resolve2, reject) => {
|
|
23946
24151
|
let settled = false;
|
|
23947
24152
|
let timer;
|
|
23948
24153
|
const finish = (fn) => {
|
|
@@ -23960,7 +24165,7 @@ var init_orchestrator = __esm({
|
|
|
23960
24165
|
finish(() => reject(new Error(`Thread not found: ${thread.id}`)));
|
|
23961
24166
|
return;
|
|
23962
24167
|
}
|
|
23963
|
-
finish(() =>
|
|
24168
|
+
finish(() => resolve2(latest));
|
|
23964
24169
|
return;
|
|
23965
24170
|
}
|
|
23966
24171
|
if (event.type === "status_changed") {
|
|
@@ -23970,7 +24175,7 @@ var init_orchestrator = __esm({
|
|
|
23970
24175
|
return;
|
|
23971
24176
|
}
|
|
23972
24177
|
if (!["running", "queued"].includes(latest.status)) {
|
|
23973
|
-
finish(() =>
|
|
24178
|
+
finish(() => resolve2(latest));
|
|
23974
24179
|
}
|
|
23975
24180
|
}
|
|
23976
24181
|
});
|
|
@@ -23982,12 +24187,12 @@ var init_orchestrator = __esm({
|
|
|
23982
24187
|
}
|
|
23983
24188
|
const current = this.healStaleReportedActivity(raw);
|
|
23984
24189
|
if (!this.threadLooksLive(current)) {
|
|
23985
|
-
finish(() =>
|
|
24190
|
+
finish(() => resolve2(current));
|
|
23986
24191
|
return;
|
|
23987
24192
|
}
|
|
23988
24193
|
if (Date.now() - start > timeoutMs) {
|
|
23989
24194
|
if (opts?.resolveIfStillRunning) {
|
|
23990
|
-
finish(() =>
|
|
24195
|
+
finish(() => resolve2(current));
|
|
23991
24196
|
} else {
|
|
23992
24197
|
finish(() => reject(new Error("wait_for_turn timed out")));
|
|
23993
24198
|
}
|
|
@@ -24579,7 +24784,7 @@ var init_orchestrator = __esm({
|
|
|
24579
24784
|
this.emit({ type: "status_changed", threadId: restored2.id, status: restored2.status });
|
|
24580
24785
|
return restored2;
|
|
24581
24786
|
}
|
|
24582
|
-
if (!(0,
|
|
24787
|
+
if (!(0, import_node_fs58.existsSync)(thread.worktreePath)) {
|
|
24583
24788
|
if (isCowboyThread(thread) || isPrimaryCheckoutThread(thread)) {
|
|
24584
24789
|
throw new Error(
|
|
24585
24790
|
`Cowboy checkout missing: ${thread.worktreePath}. Re-add the project folder, then restore.`
|
|
@@ -24663,7 +24868,7 @@ var import_mcp = require("@modelcontextprotocol/sdk/server/mcp.js");
|
|
|
24663
24868
|
var import_stdio = require("@modelcontextprotocol/sdk/server/stdio.js");
|
|
24664
24869
|
var import_zod9 = require("zod");
|
|
24665
24870
|
var import_node_crypto16 = require("crypto");
|
|
24666
|
-
var
|
|
24871
|
+
var import_node_path59 = require("path");
|
|
24667
24872
|
init_orchestrator();
|
|
24668
24873
|
init_task_state();
|
|
24669
24874
|
init_worktree();
|
|
@@ -26778,8 +26983,8 @@ ${link}` : link;
|
|
|
26778
26983
|
}
|
|
26779
26984
|
|
|
26780
26985
|
// src/slack/outbound-watch.ts
|
|
26781
|
-
var
|
|
26782
|
-
var
|
|
26986
|
+
var import_node_fs60 = require("fs");
|
|
26987
|
+
var import_node_path56 = require("path");
|
|
26783
26988
|
init_paths();
|
|
26784
26989
|
init_private_file();
|
|
26785
26990
|
init_secure_file();
|
|
@@ -26787,19 +26992,19 @@ init_thread_store();
|
|
|
26787
26992
|
init_injected_notices();
|
|
26788
26993
|
|
|
26789
26994
|
// src/slack/reply-target.ts
|
|
26790
|
-
var
|
|
26791
|
-
var
|
|
26995
|
+
var import_node_fs59 = require("fs");
|
|
26996
|
+
var import_node_path54 = require("path");
|
|
26792
26997
|
init_paths();
|
|
26793
26998
|
init_private_file();
|
|
26794
26999
|
init_secure_file();
|
|
26795
27000
|
function storePath2() {
|
|
26796
|
-
return (0,
|
|
27001
|
+
return (0, import_node_path54.join)(appDataDir(), "slack-reply-to.json");
|
|
26797
27002
|
}
|
|
26798
27003
|
function readStore2() {
|
|
26799
27004
|
const path = storePath2();
|
|
26800
|
-
if (!(0,
|
|
27005
|
+
if (!(0, import_node_fs59.existsSync)(path)) return {};
|
|
26801
27006
|
try {
|
|
26802
|
-
const parsed = isSecureFileEncrypted(path) ? readSecureJson(path) : JSON.parse((0,
|
|
27007
|
+
const parsed = isSecureFileEncrypted(path) ? readSecureJson(path) : JSON.parse((0, import_node_fs59.readFileSync)(path, "utf8"));
|
|
26803
27008
|
return parsed?.targets && typeof parsed.targets === "object" ? parsed.targets : {};
|
|
26804
27009
|
} catch {
|
|
26805
27010
|
return {};
|
|
@@ -26810,11 +27015,11 @@ function getSlackReplyTarget(threadId) {
|
|
|
26810
27015
|
}
|
|
26811
27016
|
|
|
26812
27017
|
// src/slack/workspaces.ts
|
|
26813
|
-
var
|
|
27018
|
+
var import_node_path55 = require("path");
|
|
26814
27019
|
init_paths();
|
|
26815
27020
|
init_secure_file();
|
|
26816
27021
|
function storePath3() {
|
|
26817
|
-
return (0,
|
|
27022
|
+
return (0, import_node_path55.join)(appDataDir(), "slack-workspaces.json");
|
|
26818
27023
|
}
|
|
26819
27024
|
function readStore3() {
|
|
26820
27025
|
try {
|
|
@@ -26884,7 +27089,7 @@ var POLL_INTERVAL_MS = 12e3;
|
|
|
26884
27089
|
var lastPollMs = 0;
|
|
26885
27090
|
var nameCache = /* @__PURE__ */ new Map();
|
|
26886
27091
|
function storePath4() {
|
|
26887
|
-
return (0,
|
|
27092
|
+
return (0, import_node_path56.join)(appDataDir(), "slack-outbound-watch.json");
|
|
26888
27093
|
}
|
|
26889
27094
|
function watchId(teamId, channelId, ts) {
|
|
26890
27095
|
return `${teamId}:${channelId}:${ts}`;
|
|
@@ -26897,9 +27102,9 @@ function tsNewer(a, b) {
|
|
|
26897
27102
|
}
|
|
26898
27103
|
function readStore4() {
|
|
26899
27104
|
const path = storePath4();
|
|
26900
|
-
if (!(0,
|
|
27105
|
+
if (!(0, import_node_fs60.existsSync)(path)) return [];
|
|
26901
27106
|
try {
|
|
26902
|
-
const parsed = isSecureFileEncrypted(path) ? readSecureJson(path) : JSON.parse((0,
|
|
27107
|
+
const parsed = isSecureFileEncrypted(path) ? readSecureJson(path) : JSON.parse((0, import_node_fs60.readFileSync)(path, "utf8"));
|
|
26903
27108
|
return Array.isArray(parsed?.watches) ? parsed.watches : [];
|
|
26904
27109
|
} catch {
|
|
26905
27110
|
return [];
|
|
@@ -28641,27 +28846,27 @@ init_gh_errors();
|
|
|
28641
28846
|
init_git_auth_mode();
|
|
28642
28847
|
|
|
28643
28848
|
// src/board/load-home-board.ts
|
|
28644
|
-
var
|
|
28645
|
-
var
|
|
28849
|
+
var import_node_fs62 = require("fs");
|
|
28850
|
+
var import_node_path58 = require("path");
|
|
28646
28851
|
init_worktree();
|
|
28647
28852
|
init_paths();
|
|
28648
28853
|
|
|
28649
28854
|
// src/board/board-pins.ts
|
|
28650
28855
|
var import_node_crypto15 = require("crypto");
|
|
28651
|
-
var
|
|
28652
|
-
var
|
|
28856
|
+
var import_node_fs61 = require("fs");
|
|
28857
|
+
var import_node_path57 = require("path");
|
|
28653
28858
|
init_paths();
|
|
28654
28859
|
init_home_board();
|
|
28655
28860
|
var FILE = "home-board-pins.json";
|
|
28656
28861
|
var VERSION = 1;
|
|
28657
28862
|
function pinsFile() {
|
|
28658
|
-
return (0,
|
|
28863
|
+
return (0, import_node_path57.join)(appDataDir(), FILE);
|
|
28659
28864
|
}
|
|
28660
28865
|
function readDisk() {
|
|
28661
28866
|
const path = pinsFile();
|
|
28662
|
-
if (!(0,
|
|
28867
|
+
if (!(0, import_node_fs61.existsSync)(path)) return [];
|
|
28663
28868
|
try {
|
|
28664
|
-
const raw = JSON.parse((0,
|
|
28869
|
+
const raw = JSON.parse((0, import_node_fs61.readFileSync)(path, "utf8"));
|
|
28665
28870
|
if (raw?.version !== VERSION || !Array.isArray(raw.items)) return [];
|
|
28666
28871
|
return raw.items.filter((item) => item?.id && item.kind && item.ref);
|
|
28667
28872
|
} catch {
|
|
@@ -28669,8 +28874,8 @@ function readDisk() {
|
|
|
28669
28874
|
}
|
|
28670
28875
|
}
|
|
28671
28876
|
function writeDisk(items) {
|
|
28672
|
-
(0,
|
|
28673
|
-
(0,
|
|
28877
|
+
(0, import_node_fs61.mkdirSync)(appDataDir(), { recursive: true });
|
|
28878
|
+
(0, import_node_fs61.writeFileSync)(pinsFile(), JSON.stringify({ version: VERSION, items }, null, 2), "utf8");
|
|
28674
28879
|
}
|
|
28675
28880
|
function listBoardPins() {
|
|
28676
28881
|
return readDisk();
|
|
@@ -28691,7 +28896,7 @@ function homeBoardWorkspaceKey(workspaces) {
|
|
|
28691
28896
|
return workspaces.map((w) => w.path).filter(Boolean).sort().join("\n");
|
|
28692
28897
|
}
|
|
28693
28898
|
function cacheFile() {
|
|
28694
|
-
return (0,
|
|
28899
|
+
return (0, import_node_path58.join)(appDataDir(), "home-board-cache.json");
|
|
28695
28900
|
}
|
|
28696
28901
|
function emptyInputs() {
|
|
28697
28902
|
return {
|
|
@@ -28717,9 +28922,9 @@ function shouldCacheHomeBoardInputs(inputs) {
|
|
|
28717
28922
|
}
|
|
28718
28923
|
function readDiskCache() {
|
|
28719
28924
|
const path = cacheFile();
|
|
28720
|
-
if (!(0,
|
|
28925
|
+
if (!(0, import_node_fs62.existsSync)(path)) return null;
|
|
28721
28926
|
try {
|
|
28722
|
-
const raw = JSON.parse((0,
|
|
28927
|
+
const raw = JSON.parse((0, import_node_fs62.readFileSync)(path, "utf8"));
|
|
28723
28928
|
if (raw?.version !== CACHE_VERSION || typeof raw.fetchedAt !== "number") {
|
|
28724
28929
|
return null;
|
|
28725
28930
|
}
|
|
@@ -28733,8 +28938,8 @@ function readDiskCache() {
|
|
|
28733
28938
|
}
|
|
28734
28939
|
function writeDiskCache(entry) {
|
|
28735
28940
|
try {
|
|
28736
|
-
(0,
|
|
28737
|
-
(0,
|
|
28941
|
+
(0, import_node_fs62.mkdirSync)(appDataDir(), { recursive: true });
|
|
28942
|
+
(0, import_node_fs62.writeFileSync)(cacheFile(), JSON.stringify(entry), "utf8");
|
|
28738
28943
|
} catch {
|
|
28739
28944
|
}
|
|
28740
28945
|
}
|
|
@@ -28958,14 +29163,14 @@ function orchCreateThreadAgentNote(input) {
|
|
|
28958
29163
|
var MAX_ORCH_THREADS = 5;
|
|
28959
29164
|
var CREATE_THREAD_TIMEOUT_MS = 9e4;
|
|
28960
29165
|
function withTimeout2(promise, ms, label) {
|
|
28961
|
-
return new Promise((
|
|
29166
|
+
return new Promise((resolve2, reject) => {
|
|
28962
29167
|
const timer = setTimeout(() => {
|
|
28963
29168
|
reject(new Error(`${label} timed out after ${Math.round(ms / 1e3)}s`));
|
|
28964
29169
|
}, ms);
|
|
28965
29170
|
promise.then(
|
|
28966
29171
|
(value) => {
|
|
28967
29172
|
clearTimeout(timer);
|
|
28968
|
-
|
|
29173
|
+
resolve2(value);
|
|
28969
29174
|
},
|
|
28970
29175
|
(err) => {
|
|
28971
29176
|
clearTimeout(timer);
|
|
@@ -29137,7 +29342,7 @@ async function startMcpServer() {
|
|
|
29137
29342
|
async () => {
|
|
29138
29343
|
const threads = orch.getThreads(true);
|
|
29139
29344
|
const lines = threads.map((t) => {
|
|
29140
|
-
const repo = t.repoPath === GLOBAL_WORKSPACE_ID ? "Orchestration" : (0,
|
|
29345
|
+
const repo = t.repoPath === GLOBAL_WORKSPACE_ID ? "Orchestration" : (0, import_node_path59.basename)(t.repoPath) || t.repoPath;
|
|
29141
29346
|
const live = orch.threadLooksLive(t) ? readTurnLive(t.id) : null;
|
|
29142
29347
|
const parent = t.parentThreadId ? ` parent:${t.parentThreadId.slice(0, 8)}` : "";
|
|
29143
29348
|
const preview = lastMessagePreview(t.messages, 80);
|