@zixt/host 0.0.76 → 0.0.77
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +219 -321
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -16,22 +16,22 @@ import { fstatSync } from "node:fs";
|
|
|
16
16
|
import {
|
|
17
17
|
access as access2,
|
|
18
18
|
lstat as lstat5,
|
|
19
|
-
mkdir as
|
|
19
|
+
mkdir as mkdir4,
|
|
20
20
|
open as open4,
|
|
21
21
|
readFile as readFile6,
|
|
22
22
|
readlink,
|
|
23
23
|
readdir as readdir3,
|
|
24
24
|
rename as rename3,
|
|
25
|
-
rm as
|
|
25
|
+
rm as rm4,
|
|
26
26
|
symlink
|
|
27
27
|
} from "node:fs/promises";
|
|
28
|
-
import { basename as
|
|
28
|
+
import { basename as basename3, dirname as dirname4, isAbsolute as isAbsolute8, join as join7, relative as relative4, resolve as resolve5, sep as sep4 } from "node:path";
|
|
29
29
|
import { homedir as homedir2 } from "node:os";
|
|
30
30
|
|
|
31
31
|
// package.json
|
|
32
32
|
var package_default = {
|
|
33
33
|
name: "@zixt/host",
|
|
34
|
-
version: "0.0.
|
|
34
|
+
version: "0.0.77",
|
|
35
35
|
type: "module",
|
|
36
36
|
exports: {
|
|
37
37
|
".": "./src/client.ts",
|
|
@@ -24037,107 +24037,22 @@ function createReleaseStateStore(root) {
|
|
|
24037
24037
|
};
|
|
24038
24038
|
}
|
|
24039
24039
|
|
|
24040
|
-
// src/launcher-claim.ts
|
|
24041
|
-
import { createHash as createHash2 } from "node:crypto";
|
|
24042
|
-
import { mkdir as mkdir3, rm as rm3 } from "node:fs/promises";
|
|
24043
|
-
import { createConnection, createServer } from "node:net";
|
|
24044
|
-
import { basename as basename3, dirname as dirname3, join as join6 } from "node:path";
|
|
24045
|
-
var PEER_PROBE_TIMEOUT_MS = 2e3;
|
|
24046
|
-
function machineLauncherClaimAddress(ownershipRoot, platform = process.platform) {
|
|
24047
|
-
if (platform !== "win32") {
|
|
24048
|
-
return join6(dirname3(ownershipRoot), `.${basename3(ownershipRoot)}-claim.sock`);
|
|
24049
|
-
}
|
|
24050
|
-
const digest = createHash2("sha256").update(ownershipRoot.toLowerCase()).digest("hex").slice(0, 32);
|
|
24051
|
-
return `\\\\.\\pipe\\zixt-host-launcher-${digest}`;
|
|
24052
|
-
}
|
|
24053
|
-
function describe4(error52) {
|
|
24054
|
-
const code = error52?.code;
|
|
24055
|
-
if (typeof code === "string" && code.length > 0) return code;
|
|
24056
|
-
return error52 instanceof Error ? error52.message : "unknown error";
|
|
24057
|
-
}
|
|
24058
|
-
function peerAnswers(address) {
|
|
24059
|
-
return new Promise((resolve17) => {
|
|
24060
|
-
const socket = createConnection(address);
|
|
24061
|
-
let settled = false;
|
|
24062
|
-
const finish = (answered) => {
|
|
24063
|
-
if (settled) return;
|
|
24064
|
-
settled = true;
|
|
24065
|
-
socket.destroy();
|
|
24066
|
-
resolve17(answered);
|
|
24067
|
-
};
|
|
24068
|
-
socket.setTimeout(PEER_PROBE_TIMEOUT_MS, () => finish(true));
|
|
24069
|
-
socket.once("connect", () => finish(true));
|
|
24070
|
-
socket.once("error", () => finish(false));
|
|
24071
|
-
});
|
|
24072
|
-
}
|
|
24073
|
-
function listen(address) {
|
|
24074
|
-
return new Promise((resolve17) => {
|
|
24075
|
-
const server = createServer((socket) => socket.destroy());
|
|
24076
|
-
const fail = (error52) => {
|
|
24077
|
-
server.close();
|
|
24078
|
-
resolve17({ error: error52 });
|
|
24079
|
-
};
|
|
24080
|
-
server.once("error", fail);
|
|
24081
|
-
server.listen(address, () => {
|
|
24082
|
-
server.off("error", fail);
|
|
24083
|
-
server.on("error", () => {
|
|
24084
|
-
});
|
|
24085
|
-
server.unref();
|
|
24086
|
-
resolve17({ server });
|
|
24087
|
-
});
|
|
24088
|
-
});
|
|
24089
|
-
}
|
|
24090
|
-
async function claimMachineLauncher(ownershipRoot, platform = process.platform) {
|
|
24091
|
-
const address = machineLauncherClaimAddress(ownershipRoot, platform);
|
|
24092
|
-
if (platform !== "win32") {
|
|
24093
|
-
try {
|
|
24094
|
-
await mkdir3(dirname3(address), { recursive: true, mode: 448 });
|
|
24095
|
-
} catch (error52) {
|
|
24096
|
-
return { kind: "unavailable", reason: describe4(error52) };
|
|
24097
|
-
}
|
|
24098
|
-
}
|
|
24099
|
-
for (let attempt = 0; attempt < 2; attempt++) {
|
|
24100
|
-
const outcome = await listen(address);
|
|
24101
|
-
if ("server" in outcome) {
|
|
24102
|
-
const { server } = outcome;
|
|
24103
|
-
return {
|
|
24104
|
-
kind: "held",
|
|
24105
|
-
release: async () => {
|
|
24106
|
-
await new Promise((resolve17) => server.close(() => resolve17()));
|
|
24107
|
-
if (platform !== "win32") await rm3(address, { force: true }).catch(() => {
|
|
24108
|
-
});
|
|
24109
|
-
}
|
|
24110
|
-
};
|
|
24111
|
-
}
|
|
24112
|
-
if (outcome.error.code !== "EADDRINUSE") {
|
|
24113
|
-
return { kind: "unavailable", reason: describe4(outcome.error) };
|
|
24114
|
-
}
|
|
24115
|
-
if (platform === "win32" || await peerAnswers(address)) return { kind: "busy" };
|
|
24116
|
-
try {
|
|
24117
|
-
await rm3(address, { force: true });
|
|
24118
|
-
} catch (error52) {
|
|
24119
|
-
return { kind: "unavailable", reason: describe4(error52) };
|
|
24120
|
-
}
|
|
24121
|
-
}
|
|
24122
|
-
return { kind: "busy" };
|
|
24123
|
-
}
|
|
24124
|
-
|
|
24125
24040
|
// src/runners/run-artifacts.ts
|
|
24126
24041
|
import { spawn as spawn4 } from "node:child_process";
|
|
24127
24042
|
import {
|
|
24128
24043
|
chmod as chmod2,
|
|
24129
24044
|
lstat as lstat4,
|
|
24130
|
-
mkdir as
|
|
24045
|
+
mkdir as mkdir3,
|
|
24131
24046
|
open as open3,
|
|
24132
24047
|
readdir as readdir2,
|
|
24133
24048
|
readFile as readFile5,
|
|
24134
24049
|
realpath as realpath3,
|
|
24135
24050
|
rename as rename2,
|
|
24136
|
-
rm as
|
|
24051
|
+
rm as rm3,
|
|
24137
24052
|
writeFile
|
|
24138
24053
|
} from "node:fs/promises";
|
|
24139
24054
|
import { homedir } from "node:os";
|
|
24140
|
-
import { dirname as
|
|
24055
|
+
import { dirname as dirname3, isAbsolute as isAbsolute7, join as join6, relative as relative3, resolve as resolve4, sep as sep3, win32 as win322 } from "node:path";
|
|
24141
24056
|
|
|
24142
24057
|
// src/windows-job.ts
|
|
24143
24058
|
import { spawn as spawn3 } from "node:child_process";
|
|
@@ -24876,7 +24791,7 @@ foreach ($path in $paths) {
|
|
|
24876
24791
|
}
|
|
24877
24792
|
`;
|
|
24878
24793
|
function defaultRunArtifactRoot() {
|
|
24879
|
-
return
|
|
24794
|
+
return join6(homedir(), ".zixt", "run-artifacts");
|
|
24880
24795
|
}
|
|
24881
24796
|
function requireSafeSegment(value, field) {
|
|
24882
24797
|
if (!SAFE_SEGMENT.test(value)) {
|
|
@@ -24932,7 +24847,7 @@ async function prepareRoot(root) {
|
|
|
24932
24847
|
await lstat4(absolute);
|
|
24933
24848
|
} catch (error52) {
|
|
24934
24849
|
if (!isMissing(error52)) throw error52;
|
|
24935
|
-
await
|
|
24850
|
+
await mkdir3(absolute, { recursive: true, mode: DIRECTORY_MODE });
|
|
24936
24851
|
}
|
|
24937
24852
|
const real = await requireRealDirectory(absolute, "run artifact root");
|
|
24938
24853
|
if (realProfile) assertWindowsProfileBoundary(realProfile, real);
|
|
@@ -24940,14 +24855,14 @@ async function prepareRoot(root) {
|
|
|
24940
24855
|
return real;
|
|
24941
24856
|
}
|
|
24942
24857
|
async function prepareAgentRoot(root, agentId) {
|
|
24943
|
-
const path =
|
|
24858
|
+
const path = join6(root, agentId);
|
|
24944
24859
|
assertBelow(root, path);
|
|
24945
24860
|
try {
|
|
24946
24861
|
await lstat4(path);
|
|
24947
24862
|
} catch (error52) {
|
|
24948
24863
|
if (!isMissing(error52)) throw error52;
|
|
24949
24864
|
try {
|
|
24950
|
-
await
|
|
24865
|
+
await mkdir3(path, { mode: DIRECTORY_MODE });
|
|
24951
24866
|
} catch (mkdirError) {
|
|
24952
24867
|
if (mkdirError.code !== "EEXIST") throw mkdirError;
|
|
24953
24868
|
}
|
|
@@ -24963,7 +24878,7 @@ async function lockDownWindowsDirectories(paths) {
|
|
|
24963
24878
|
if (!windowsRoot || !win322.isAbsolute(windowsRoot)) {
|
|
24964
24879
|
throw new Error("private Windows run-artifact ACL authority is unavailable");
|
|
24965
24880
|
}
|
|
24966
|
-
const powershell =
|
|
24881
|
+
const powershell = join6(windowsRoot, "System32", "WindowsPowerShell", "v1.0", "powershell.exe");
|
|
24967
24882
|
const encoded = Buffer.from(WINDOWS_PRIVATE_DACL_SCRIPT, "utf16le").toString("base64");
|
|
24968
24883
|
await new Promise((resolvePromise, reject3) => {
|
|
24969
24884
|
const helper = spawn4(
|
|
@@ -25005,9 +24920,9 @@ async function lockDownWindowsDirectories(paths) {
|
|
|
25005
24920
|
});
|
|
25006
24921
|
}
|
|
25007
24922
|
async function createPrivateDirectory(parent, name) {
|
|
25008
|
-
const path =
|
|
24923
|
+
const path = join6(parent, name);
|
|
25009
24924
|
assertBelow(parent, path);
|
|
25010
|
-
await
|
|
24925
|
+
await mkdir3(path, { mode: DIRECTORY_MODE });
|
|
25011
24926
|
await chmod2(path, DIRECTORY_MODE);
|
|
25012
24927
|
const real = await realpath3(path);
|
|
25013
24928
|
assertBelow(parent, real);
|
|
@@ -25034,24 +24949,24 @@ async function createRunArtifacts(input) {
|
|
|
25034
24949
|
requireSafeSegment(input.agentId, "agentId");
|
|
25035
24950
|
requireSafeSegment(input.runToken, "runToken");
|
|
25036
24951
|
const root = await prepareRoot(input.root);
|
|
25037
|
-
const removeTree = input.removeTree ?? ((path) =>
|
|
24952
|
+
const removeTree = input.removeTree ?? ((path) => rm3(path, { recursive: true, force: true }));
|
|
25038
24953
|
const cleanupRetryDelayMs = input.cleanupRetryDelayMs ?? CLEANUP_RETRY_DELAY_MS;
|
|
25039
24954
|
const agentRoot = await prepareAgentRoot(root, input.agentId);
|
|
25040
24955
|
await lockDownWindowsDirectories([root, agentRoot]);
|
|
25041
|
-
const runRoot =
|
|
24956
|
+
const runRoot = join6(agentRoot, input.runToken);
|
|
25042
24957
|
assertBelow(agentRoot, runRoot);
|
|
25043
24958
|
try {
|
|
25044
|
-
await
|
|
24959
|
+
await mkdir3(runRoot, { mode: DIRECTORY_MODE });
|
|
25045
24960
|
await chmod2(runRoot, DIRECTORY_MODE);
|
|
25046
24961
|
const realRunRoot = await realpath3(runRoot);
|
|
25047
24962
|
assertBelow(agentRoot, realRunRoot);
|
|
25048
24963
|
const emptyGithubConfigDirectory = await createPrivateDirectory(realRunRoot, "gh-config");
|
|
25049
24964
|
const emptyGitHooksDirectory = await createPrivateDirectory(realRunRoot, "git-hooks");
|
|
25050
24965
|
const gitBridgesDirectory = await createPrivateDirectory(realRunRoot, "git-bridges");
|
|
25051
|
-
const denySshScript =
|
|
25052
|
-
const runnerWrapperScript =
|
|
25053
|
-
const systemPromptPath =
|
|
25054
|
-
const mcpConfigPath =
|
|
24966
|
+
const denySshScript = join6(realRunRoot, "deny-ssh.cjs");
|
|
24967
|
+
const runnerWrapperScript = join6(realRunRoot, "runner-wrapper.cjs");
|
|
24968
|
+
const systemPromptPath = join6(realRunRoot, "system-prompt.txt");
|
|
24969
|
+
const mcpConfigPath = join6(realRunRoot, "mcp.json");
|
|
25055
24970
|
await writePrivateFile(denySshScript, "process.exitCode = 127;");
|
|
25056
24971
|
await writePrivateFile(runnerWrapperScript, RUNNER_GUARDIAN);
|
|
25057
24972
|
return {
|
|
@@ -25115,20 +25030,20 @@ async function sweepOrphanedRunArtifacts(root) {
|
|
|
25115
25030
|
let removed = 0;
|
|
25116
25031
|
for (const agent of agents) {
|
|
25117
25032
|
if (!SAFE_SEGMENT.test(agent.name) || !agent.isDirectory() || agent.isSymbolicLink()) continue;
|
|
25118
|
-
const agentPath =
|
|
25033
|
+
const agentPath = join6(realRoot, agent.name);
|
|
25119
25034
|
const runs = await readdir2(agentPath, { withFileTypes: true });
|
|
25120
25035
|
for (const run3 of runs) {
|
|
25121
25036
|
if (!SAFE_SEGMENT.test(run3.name) || !run3.isDirectory() || run3.isSymbolicLink()) continue;
|
|
25122
|
-
const runPath =
|
|
25037
|
+
const runPath = join6(agentPath, run3.name);
|
|
25123
25038
|
assertBelow(agentPath, runPath);
|
|
25124
|
-
await
|
|
25039
|
+
await rm3(runPath, { recursive: true, force: true });
|
|
25125
25040
|
removed++;
|
|
25126
25041
|
}
|
|
25127
25042
|
}
|
|
25128
25043
|
return removed;
|
|
25129
25044
|
}
|
|
25130
25045
|
function defaultRunRegistryRoot() {
|
|
25131
|
-
return
|
|
25046
|
+
return join6(homedir(), ".zixt", "run-registry");
|
|
25132
25047
|
}
|
|
25133
25048
|
async function terminateRecordedRunProcesses(registryRoot = defaultRunRegistryRoot(), terminate = terminateRecordedProcessTree) {
|
|
25134
25049
|
const entries = await readRecordedRunAssignmentEntriesStrict(registryRoot);
|
|
@@ -25154,23 +25069,23 @@ async function syncRunRegistryDirectory(path) {
|
|
|
25154
25069
|
}
|
|
25155
25070
|
}
|
|
25156
25071
|
async function ensureDurableRunRegistryRoot(registryRoot, syncDirectory7) {
|
|
25157
|
-
const firstCreated = await
|
|
25072
|
+
const firstCreated = await mkdir3(registryRoot, { recursive: true, mode: DIRECTORY_MODE });
|
|
25158
25073
|
if (firstCreated && process.platform !== "win32") {
|
|
25159
25074
|
const first = resolve4(firstCreated);
|
|
25160
25075
|
const target = resolve4(registryRoot);
|
|
25161
|
-
await syncDirectory7(
|
|
25076
|
+
await syncDirectory7(dirname3(first));
|
|
25162
25077
|
let current = first;
|
|
25163
25078
|
for (const part of relative3(first, target).split(sep3).filter(Boolean)) {
|
|
25164
25079
|
await syncDirectory7(current);
|
|
25165
|
-
current =
|
|
25080
|
+
current = join6(current, part);
|
|
25166
25081
|
}
|
|
25167
25082
|
}
|
|
25168
25083
|
await chmod2(registryRoot, DIRECTORY_MODE);
|
|
25169
25084
|
}
|
|
25170
25085
|
async function recordRunAssignment(runToken, record2, registryRoot = defaultRunRegistryRoot(), options = {}) {
|
|
25171
25086
|
if (!SAFE_SEGMENT.test(runToken)) return false;
|
|
25172
|
-
const destination =
|
|
25173
|
-
const temporary =
|
|
25087
|
+
const destination = join6(registryRoot, `${runToken}.json`);
|
|
25088
|
+
const temporary = join6(registryRoot, `.${runToken}.${process.pid}.${Date.now()}.tmp`);
|
|
25174
25089
|
let handle;
|
|
25175
25090
|
try {
|
|
25176
25091
|
const syncDirectory7 = options.syncDirectory ?? syncRunRegistryDirectory;
|
|
@@ -25190,7 +25105,7 @@ async function recordRunAssignment(runToken, record2, registryRoot = defaultRunR
|
|
|
25190
25105
|
} finally {
|
|
25191
25106
|
await handle?.close().catch(() => {
|
|
25192
25107
|
});
|
|
25193
|
-
await
|
|
25108
|
+
await rm3(temporary, { force: true }).catch(() => {
|
|
25194
25109
|
});
|
|
25195
25110
|
}
|
|
25196
25111
|
}
|
|
@@ -25202,7 +25117,7 @@ async function forgetRunAssignment(runToken, registryRoot = defaultRunRegistryRo
|
|
|
25202
25117
|
if (retainingAssignments) return;
|
|
25203
25118
|
if (!SAFE_SEGMENT.test(runToken)) return;
|
|
25204
25119
|
try {
|
|
25205
|
-
await
|
|
25120
|
+
await rm3(join6(registryRoot, `${runToken}.json`), { force: true });
|
|
25206
25121
|
} catch {
|
|
25207
25122
|
}
|
|
25208
25123
|
}
|
|
@@ -25247,7 +25162,7 @@ async function readRecordedRunAssignmentEntries(registryRoot = defaultRunRegistr
|
|
|
25247
25162
|
if (!SAFE_SEGMENT.test(runToken)) continue;
|
|
25248
25163
|
let text;
|
|
25249
25164
|
try {
|
|
25250
|
-
text = await readFile5(
|
|
25165
|
+
text = await readFile5(join6(registryRoot, entry.name), "utf8");
|
|
25251
25166
|
} catch {
|
|
25252
25167
|
continue;
|
|
25253
25168
|
}
|
|
@@ -25283,7 +25198,7 @@ async function readRecordedRunAssignmentEntriesStrict(registryRoot = defaultRunR
|
|
|
25283
25198
|
}
|
|
25284
25199
|
let text;
|
|
25285
25200
|
try {
|
|
25286
|
-
text = await readFile5(
|
|
25201
|
+
text = await readFile5(join6(registryRoot, entry.name), "utf8");
|
|
25287
25202
|
} catch {
|
|
25288
25203
|
throw new Error("committed run registry witness could not be read");
|
|
25289
25204
|
}
|
|
@@ -25300,13 +25215,13 @@ async function forgetAcknowledgedRunAssignments(assignments, registryRoot = defa
|
|
|
25300
25215
|
);
|
|
25301
25216
|
const entries = await readRecordedRunAssignmentEntries(registryRoot);
|
|
25302
25217
|
await Promise.all(
|
|
25303
|
-
entries.filter(({ record: record2 }) => acknowledged.has(`${record2.taskId}:${record2.epoch}`)).map(({ runToken }) =>
|
|
25218
|
+
entries.filter(({ record: record2 }) => acknowledged.has(`${record2.taskId}:${record2.epoch}`)).map(({ runToken }) => rm3(join6(registryRoot, `${runToken}.json`), { force: true }))
|
|
25304
25219
|
);
|
|
25305
25220
|
}
|
|
25306
25221
|
async function forgetSupersededRunAssignments(taskId, epoch, registryRoot = defaultRunRegistryRoot()) {
|
|
25307
25222
|
const entries = await readRecordedRunAssignmentEntries(registryRoot);
|
|
25308
25223
|
await Promise.all(
|
|
25309
|
-
entries.filter(({ record: record2 }) => record2.taskId === taskId && record2.epoch < epoch).map(({ runToken }) =>
|
|
25224
|
+
entries.filter(({ record: record2 }) => record2.taskId === taskId && record2.epoch < epoch).map(({ runToken }) => rm3(join6(registryRoot, `${runToken}.json`), { force: true }))
|
|
25310
25225
|
);
|
|
25311
25226
|
}
|
|
25312
25227
|
|
|
@@ -25348,7 +25263,7 @@ function signalWorkerGroup(child, signal) {
|
|
|
25348
25263
|
}
|
|
25349
25264
|
}
|
|
25350
25265
|
function versionsRoot() {
|
|
25351
|
-
return process.env.ZIXT_HOST_VERSIONS_DIR ??
|
|
25266
|
+
return process.env.ZIXT_HOST_VERSIONS_DIR ?? join7(homedir2(), ".zixt", "host-versions");
|
|
25352
25267
|
}
|
|
25353
25268
|
function npmCommand(platform = process.platform) {
|
|
25354
25269
|
return platform === "win32" ? "npm.cmd" : "npm";
|
|
@@ -25357,13 +25272,13 @@ function windowsInstallerCommandLine(command, args) {
|
|
|
25357
25272
|
return [command, ...args].map(quoteForCmd).join(" ");
|
|
25358
25273
|
}
|
|
25359
25274
|
function installedReleaseEntry(version2, root = versionsRoot()) {
|
|
25360
|
-
return
|
|
25275
|
+
return join7(root, version2, "node_modules", PACKAGE_NAME, "dist", "index.js");
|
|
25361
25276
|
}
|
|
25362
25277
|
function releaseEntryAtPrefix(prefix) {
|
|
25363
|
-
return
|
|
25278
|
+
return join7(prefix, "node_modules", PACKAGE_NAME, "dist", "index.js");
|
|
25364
25279
|
}
|
|
25365
25280
|
function releaseManifestAtPrefix(prefix) {
|
|
25366
|
-
return
|
|
25281
|
+
return join7(prefix, "node_modules", PACKAGE_NAME, "package.json");
|
|
25367
25282
|
}
|
|
25368
25283
|
async function validReleaseAtPrefix(prefix, version2) {
|
|
25369
25284
|
try {
|
|
@@ -25398,10 +25313,10 @@ function installedReleaseVersion(entry, root = versionsRoot()) {
|
|
|
25398
25313
|
return resolve5(entry) === resolve5(installedReleaseEntry(version2, root)) ? version2 : null;
|
|
25399
25314
|
}
|
|
25400
25315
|
function currentReleaseEntry(root = versionsRoot(), platform = process.platform) {
|
|
25401
|
-
return
|
|
25316
|
+
return join7(root, platform === "win32" ? "current-launcher.cjs" : CURRENT_RELEASE_ENTRY);
|
|
25402
25317
|
}
|
|
25403
25318
|
function windowsReleasePointer(root = versionsRoot()) {
|
|
25404
|
-
return
|
|
25319
|
+
return join7(root, WINDOWS_RELEASE_POINTER);
|
|
25405
25320
|
}
|
|
25406
25321
|
var WINDOWS_STABLE_LAUNCHER = `${WINDOWS_LAUNCHER_MARKER}
|
|
25407
25322
|
'use strict';
|
|
@@ -25436,9 +25351,9 @@ child.once('error', () => process.exit(1));
|
|
|
25436
25351
|
child.once('exit', (code) => process.exit(code == null ? 1 : code));
|
|
25437
25352
|
`;
|
|
25438
25353
|
async function replaceDurableFile(path, contents, sync = syncDirectory3) {
|
|
25439
|
-
const parent =
|
|
25440
|
-
await
|
|
25441
|
-
const temporary =
|
|
25354
|
+
const parent = dirname4(path);
|
|
25355
|
+
await mkdir4(parent, { recursive: true, mode: 448 });
|
|
25356
|
+
const temporary = join7(parent, `.${CURRENT_RELEASE_ENTRY}.${process.pid}.${crypto.randomUUID()}`);
|
|
25442
25357
|
const handle = await open4(temporary, "wx", 384);
|
|
25443
25358
|
try {
|
|
25444
25359
|
await handle.writeFile(contents, "utf8");
|
|
@@ -25448,7 +25363,7 @@ async function replaceDurableFile(path, contents, sync = syncDirectory3) {
|
|
|
25448
25363
|
await sync(parent);
|
|
25449
25364
|
} catch (error52) {
|
|
25450
25365
|
await handle.close().catch(() => void 0);
|
|
25451
|
-
await
|
|
25366
|
+
await rm4(temporary, { force: true }).catch(() => void 0);
|
|
25452
25367
|
throw error52;
|
|
25453
25368
|
}
|
|
25454
25369
|
}
|
|
@@ -25458,7 +25373,7 @@ async function activateInstalledRelease(entry, root = versionsRoot(), platform =
|
|
|
25458
25373
|
}
|
|
25459
25374
|
await access2(entry);
|
|
25460
25375
|
if (platform === "win32") {
|
|
25461
|
-
await
|
|
25376
|
+
await mkdir4(root, { recursive: true, mode: 448 });
|
|
25462
25377
|
const launcher = currentReleaseEntry(root, platform);
|
|
25463
25378
|
const existingLauncher = await lstat5(launcher).catch((error52) => {
|
|
25464
25379
|
if (error52.code === "ENOENT") return null;
|
|
@@ -25507,7 +25422,7 @@ async function activateInstalledRelease(entry, root = versionsRoot(), platform =
|
|
|
25507
25422
|
return launcher;
|
|
25508
25423
|
}
|
|
25509
25424
|
if (platform !== "linux" && platform !== "darwin") return entry;
|
|
25510
|
-
await
|
|
25425
|
+
await mkdir4(root, { recursive: true, mode: 448 });
|
|
25511
25426
|
const current = currentReleaseEntry(root, platform);
|
|
25512
25427
|
const existing = await lstat5(current).catch((error52) => {
|
|
25513
25428
|
if (error52.code === "ENOENT") return null;
|
|
@@ -25516,13 +25431,13 @@ async function activateInstalledRelease(entry, root = versionsRoot(), platform =
|
|
|
25516
25431
|
if (existing && !existing.isSymbolicLink()) {
|
|
25517
25432
|
throw new Error("the Zixt Host current-release entry is not a symbolic link");
|
|
25518
25433
|
}
|
|
25519
|
-
const temporary =
|
|
25434
|
+
const temporary = join7(root, `.${CURRENT_RELEASE_ENTRY}.${process.pid}.${crypto.randomUUID()}`);
|
|
25520
25435
|
try {
|
|
25521
25436
|
await symlink(entry, temporary, "file");
|
|
25522
25437
|
await rename3(temporary, current);
|
|
25523
25438
|
await sync(root);
|
|
25524
25439
|
} catch (error52) {
|
|
25525
|
-
await
|
|
25440
|
+
await rm4(temporary, { force: true }).catch(() => void 0);
|
|
25526
25441
|
throw error52;
|
|
25527
25442
|
}
|
|
25528
25443
|
return current;
|
|
@@ -25543,7 +25458,7 @@ async function activatedReleaseVersion(root = versionsRoot(), platform = process
|
|
|
25543
25458
|
try {
|
|
25544
25459
|
const current = currentReleaseEntry(root, platform);
|
|
25545
25460
|
const target = await readlink(current);
|
|
25546
|
-
return installedReleaseVersion(resolve5(
|
|
25461
|
+
return installedReleaseVersion(resolve5(dirname4(current), target), root);
|
|
25547
25462
|
} catch {
|
|
25548
25463
|
return null;
|
|
25549
25464
|
}
|
|
@@ -25647,13 +25562,13 @@ async function installRelease(version2, options = {}) {
|
|
|
25647
25562
|
const platform = options.platform ?? process.platform;
|
|
25648
25563
|
const installerCommand = options.installerCommand ?? npmCommand(platform);
|
|
25649
25564
|
const root = options.root ?? versionsRoot();
|
|
25650
|
-
const prefix =
|
|
25565
|
+
const prefix = join7(root, version2);
|
|
25651
25566
|
const entry = installedReleaseEntry(version2, root);
|
|
25652
25567
|
if (await validReleaseAtPrefix(prefix, version2)) return entry;
|
|
25653
25568
|
if (options.signal?.aborted) return null;
|
|
25654
|
-
await
|
|
25655
|
-
const staging =
|
|
25656
|
-
const quarantine =
|
|
25569
|
+
await mkdir4(root, { recursive: true, mode: 448 });
|
|
25570
|
+
const staging = join7(root, `.install-${version2}-${process.pid}-${crypto.randomUUID()}`);
|
|
25571
|
+
const quarantine = join7(root, `.invalid-${version2}-${process.pid}-${crypto.randomUUID()}`);
|
|
25657
25572
|
const usesWindowsInstallerGuardian = platform === "win32" && options.spawnInstaller === void 0;
|
|
25658
25573
|
const installerGateNonce = usesWindowsInstallerGuardian ? crypto.randomUUID() : null;
|
|
25659
25574
|
const installerArguments = (installPrefix, installVersion) => [
|
|
@@ -25685,7 +25600,7 @@ async function installRelease(version2, options = {}) {
|
|
|
25685
25600
|
try {
|
|
25686
25601
|
child = spawnInstaller(staging, version2);
|
|
25687
25602
|
} catch {
|
|
25688
|
-
await
|
|
25603
|
+
await rm4(staging, { recursive: true, force: true }).catch(() => void 0);
|
|
25689
25604
|
return null;
|
|
25690
25605
|
}
|
|
25691
25606
|
let resolveChildExited;
|
|
@@ -25835,8 +25750,8 @@ async function installRelease(version2, options = {}) {
|
|
|
25835
25750
|
await syncDirectory3(root);
|
|
25836
25751
|
return await validReleaseAtPrefix(prefix, version2) ? entry : null;
|
|
25837
25752
|
} finally {
|
|
25838
|
-
await
|
|
25839
|
-
await
|
|
25753
|
+
await rm4(staging, { recursive: true, force: true }).catch(() => void 0);
|
|
25754
|
+
await rm4(quarantine, { recursive: true, force: true }).catch(() => void 0);
|
|
25840
25755
|
}
|
|
25841
25756
|
}
|
|
25842
25757
|
async function pruneInstalledVersions(keep, root = versionsRoot()) {
|
|
@@ -25851,10 +25766,10 @@ async function pruneInstalledVersions(keep, root = versionsRoot()) {
|
|
|
25851
25766
|
const removed = [];
|
|
25852
25767
|
for (const name of entries) {
|
|
25853
25768
|
if (protectedDirs.has(name) || !VERSION_DIR.test(name)) continue;
|
|
25854
|
-
const dir =
|
|
25769
|
+
const dir = join7(root, name);
|
|
25855
25770
|
if (running && running.startsWith(`${dir}${sep4}`)) continue;
|
|
25856
25771
|
try {
|
|
25857
|
-
await
|
|
25772
|
+
await rm4(dir, { recursive: true, force: true });
|
|
25858
25773
|
removed.push(name);
|
|
25859
25774
|
} catch {
|
|
25860
25775
|
}
|
|
@@ -25865,7 +25780,7 @@ function durableState(phase, candidateVersion, fallbackVersion) {
|
|
|
25865
25780
|
return { schema: 1, phase, candidateVersion, fallbackVersion };
|
|
25866
25781
|
}
|
|
25867
25782
|
async function validInstalledRelease(version2, root = versionsRoot()) {
|
|
25868
|
-
return validReleaseAtPrefix(
|
|
25783
|
+
return validReleaseAtPrefix(join7(root, version2), version2);
|
|
25869
25784
|
}
|
|
25870
25785
|
async function recoverDurableReleaseState(store, runningVersion, activeBootVersion, activate, log2) {
|
|
25871
25786
|
const state = await store.load();
|
|
@@ -25984,7 +25899,7 @@ function defaultSpawn(command, argv, supervisorVersion, watchdog, compatibilityO
|
|
|
25984
25899
|
stdio: watchdog ? ["pipe", "inherit", "inherit", "ipc"] : ["pipe", "inherit", "inherit"],
|
|
25985
25900
|
env,
|
|
25986
25901
|
...containmentGateNonce ? {
|
|
25987
|
-
cwd: ownership?.ownershipFile ?
|
|
25902
|
+
cwd: ownership?.ownershipFile ? dirname4(ownership.ownershipFile) : dirname4(entry)
|
|
25988
25903
|
} : {},
|
|
25989
25904
|
// The launch nonce is not a user-facing CLI argument. Keeping it as
|
|
25990
25905
|
// argv[0] gives the stable launcher an exact cross-platform process
|
|
@@ -26081,10 +25996,10 @@ async function launchHostSupervisor(options = {}) {
|
|
|
26081
25996
|
delete env[WORKER_WATCHDOG_FILE_ENV];
|
|
26082
25997
|
delete env[WORKER_OWNERSHIP_FILE_ENV];
|
|
26083
25998
|
delete env[SUPERVISOR_OWNERSHIP_FILE_ENV];
|
|
26084
|
-
const generationNonce = ownershipDirectory ?
|
|
25999
|
+
const generationNonce = ownershipDirectory ? basename3(ownershipDirectory) : null;
|
|
26085
26000
|
if (ownershipDirectory && generationNonce) {
|
|
26086
26001
|
env[LAUNCHER_OWNERSHIP_DIR_ENV] = ownershipDirectory;
|
|
26087
|
-
env[SUPERVISOR_OWNERSHIP_FILE_ENV] =
|
|
26002
|
+
env[SUPERVISOR_OWNERSHIP_FILE_ENV] = join7(ownershipDirectory, `${generationNonce}.json`);
|
|
26088
26003
|
} else {
|
|
26089
26004
|
delete env[LAUNCHER_OWNERSHIP_DIR_ENV];
|
|
26090
26005
|
}
|
|
@@ -26095,7 +26010,7 @@ async function launchHostSupervisor(options = {}) {
|
|
|
26095
26010
|
const child2 = spawn5(process.execPath, [supervisorEntry, ...argv], {
|
|
26096
26011
|
stdio: ["pipe", "inherit", "inherit"],
|
|
26097
26012
|
env,
|
|
26098
|
-
...containmentGateNonce ? { cwd: ownershipDirectory ??
|
|
26013
|
+
...containmentGateNonce ? { cwd: ownershipDirectory ?? dirname4(supervisorEntry) } : {},
|
|
26099
26014
|
detached: platform !== "win32",
|
|
26100
26015
|
// The new launcher can discover the durable PID record and still has
|
|
26101
26016
|
// to bind it to this exact process before signalling a recycled PID.
|
|
@@ -26107,8 +26022,8 @@ async function launchHostSupervisor(options = {}) {
|
|
|
26107
26022
|
});
|
|
26108
26023
|
const customDelay = options.delay;
|
|
26109
26024
|
const ownsWorkerBoundary = options.spawnSupervisor === void 0 || options.ownershipRoot !== void 0;
|
|
26110
|
-
const ownershipRoot = options.ownershipRoot ??
|
|
26111
|
-
const runRegistryRoot2 = options.runRegistryRoot ?? (options.ownershipRoot ?
|
|
26025
|
+
const ownershipRoot = options.ownershipRoot ?? join7(versionsRoot(), "launcher-ownership");
|
|
26026
|
+
const runRegistryRoot2 = options.runRegistryRoot ?? (options.ownershipRoot ? join7(dirname4(options.ownershipRoot), "run-registry") : defaultRunRegistryRoot());
|
|
26112
26027
|
const terminateRecordedOwnership = options.terminateRecordedOwnership ?? terminateRecordedProcessTree;
|
|
26113
26028
|
const createSupervisorContainment = options.createSupervisorContainment ?? (platform === "win32" && options.spawnSupervisor === void 0 ? async (target, identityNonce, signal) => {
|
|
26114
26029
|
if (!target.pid) throw new Error("supervisor process id is unavailable");
|
|
@@ -26163,7 +26078,7 @@ async function launchHostSupervisor(options = {}) {
|
|
|
26163
26078
|
return false;
|
|
26164
26079
|
};
|
|
26165
26080
|
const cleanupOwnershipGeneration = async (directory) => {
|
|
26166
|
-
const generationNonce =
|
|
26081
|
+
const generationNonce = basename3(directory);
|
|
26167
26082
|
const firstRecords = await readWorkerOwnershipRecords(directory);
|
|
26168
26083
|
const supervisorRecord = firstRecords.find((record2) => record2.nonce === generationNonce);
|
|
26169
26084
|
if (firstRecords.length > 0 && !supervisorRecord) {
|
|
@@ -26254,23 +26169,7 @@ async function launchHostSupervisor(options = {}) {
|
|
|
26254
26169
|
}
|
|
26255
26170
|
return false;
|
|
26256
26171
|
};
|
|
26257
|
-
let releaseMachineClaim = null;
|
|
26258
26172
|
try {
|
|
26259
|
-
if (ownsWorkerBoundary) {
|
|
26260
|
-
const claim = await claimMachineLauncher(ownershipRoot);
|
|
26261
|
-
if (claim.kind === "busy") {
|
|
26262
|
-
log2(
|
|
26263
|
-
"Zixt Host: another Zixt Host is already running on this Machine, so this one is stopping instead of taking that Host and its Tasks down. Stop the running Host first if you meant to replace it."
|
|
26264
|
-
);
|
|
26265
|
-
return DO_NOT_RESTART_EXIT_CODE;
|
|
26266
|
-
}
|
|
26267
|
-
if (claim.kind === "held") releaseMachineClaim = claim.release;
|
|
26268
|
-
else {
|
|
26269
|
-
log2(
|
|
26270
|
-
`Zixt Host launcher: this Machine cannot be claimed for a single Host (${claim.reason}); continuing without that protection`
|
|
26271
|
-
);
|
|
26272
|
-
}
|
|
26273
|
-
}
|
|
26274
26173
|
if (!await recoverPriorOwnership()) return 1;
|
|
26275
26174
|
for (; ; ) {
|
|
26276
26175
|
if (stopping) return 0;
|
|
@@ -26302,7 +26201,7 @@ async function launchHostSupervisor(options = {}) {
|
|
|
26302
26201
|
let supervisorContainment = null;
|
|
26303
26202
|
try {
|
|
26304
26203
|
if (containmentGateNonce) {
|
|
26305
|
-
const supervisorIdentity = ownershipDirectory ?
|
|
26204
|
+
const supervisorIdentity = ownershipDirectory ? basename3(ownershipDirectory) : null;
|
|
26306
26205
|
if (!supervisorIdentity) {
|
|
26307
26206
|
throw new Error("supervisor containment identity is unavailable");
|
|
26308
26207
|
}
|
|
@@ -26377,7 +26276,6 @@ async function launchHostSupervisor(options = {}) {
|
|
|
26377
26276
|
process.stdin.off("data", onStdinData);
|
|
26378
26277
|
process.stdin.pause();
|
|
26379
26278
|
}
|
|
26380
|
-
if (releaseMachineClaim) await releaseMachineClaim();
|
|
26381
26279
|
}
|
|
26382
26280
|
}
|
|
26383
26281
|
async function superviseHost(options = {}) {
|
|
@@ -26394,8 +26292,8 @@ async function superviseHost(options = {}) {
|
|
|
26394
26292
|
const inheritedOwnershipDirectory = process.env[LAUNCHER_OWNERSHIP_DIR_ENV];
|
|
26395
26293
|
const launcherOwnershipDirectory = productionLifecycle && typeof inheritedOwnershipDirectory === "string" && isAbsolute8(inheritedOwnershipDirectory) ? inheritedOwnershipDirectory : null;
|
|
26396
26294
|
if (productionLifecycle && isSupervisorRole() && launcherOwnershipDirectory) {
|
|
26397
|
-
const generationNonce =
|
|
26398
|
-
const expectedOwnershipFile =
|
|
26295
|
+
const generationNonce = basename3(launcherOwnershipDirectory);
|
|
26296
|
+
const expectedOwnershipFile = join7(launcherOwnershipDirectory, `${generationNonce}.json`);
|
|
26399
26297
|
const configuredOwnershipFile = process.env[SUPERVISOR_OWNERSHIP_FILE_ENV];
|
|
26400
26298
|
if (process.argv0 !== generationNonce || configuredOwnershipFile !== expectedOwnershipFile || !recordWorkerOwnership(expectedOwnershipFile, generationNonce)) {
|
|
26401
26299
|
log2("Zixt Host: supervisor ownership could not be committed; refusing to start a worker");
|
|
@@ -26923,7 +26821,7 @@ import { homedir as homedir12, hostname as hostname3 } from "node:os";
|
|
|
26923
26821
|
import { existsSync } from "node:fs";
|
|
26924
26822
|
import { statfs } from "node:fs/promises";
|
|
26925
26823
|
import { cpus, freemem, homedir as homedir3, totalmem } from "node:os";
|
|
26926
|
-
import { dirname as
|
|
26824
|
+
import { dirname as dirname5, resolve as resolve6 } from "node:path";
|
|
26927
26825
|
async function machineHardware(workRoot = homedir3()) {
|
|
26928
26826
|
return {
|
|
26929
26827
|
// A container or cgroup can hide processors from this count; it is what
|
|
@@ -26952,7 +26850,7 @@ function nearestExistingPath(start) {
|
|
|
26952
26850
|
let candidate = resolve6(start);
|
|
26953
26851
|
for (let depth = 0; depth < 16; depth++) {
|
|
26954
26852
|
if (existsSync(candidate)) return candidate;
|
|
26955
|
-
const parent =
|
|
26853
|
+
const parent = dirname5(candidate);
|
|
26956
26854
|
if (parent === candidate) return null;
|
|
26957
26855
|
candidate = parent;
|
|
26958
26856
|
}
|
|
@@ -27146,17 +27044,17 @@ function createDemoBrowserAdapterFactory() {
|
|
|
27146
27044
|
}
|
|
27147
27045
|
|
|
27148
27046
|
// src/browser/manager.ts
|
|
27149
|
-
import { lstat as lstat6, mkdir as
|
|
27047
|
+
import { lstat as lstat6, mkdir as mkdir5, open as open5, opendir, readFile as readFile7, rename as rename4, rm as rm5 } from "node:fs/promises";
|
|
27150
27048
|
import { homedir as homedir4 } from "node:os";
|
|
27151
|
-
import { dirname as
|
|
27049
|
+
import { dirname as dirname6, join as join8, resolve as resolve7 } from "node:path";
|
|
27152
27050
|
var SAFE_SEGMENT2 = /^[A-Za-z0-9_-]{1,200}$/;
|
|
27153
27051
|
var FRAME_MIN_INTERVAL_MS = 100;
|
|
27154
27052
|
var IDLE_TIMEOUT_MS = 15 * 6e4;
|
|
27155
27053
|
var BrowserManager = class {
|
|
27156
27054
|
constructor(opts) {
|
|
27157
27055
|
this.opts = opts;
|
|
27158
|
-
this.profileRoot = opts.profileRoot ??
|
|
27159
|
-
this.profileStateRoot =
|
|
27056
|
+
this.profileRoot = opts.profileRoot ?? join8(homedir4(), ".zixt", "browser-profiles");
|
|
27057
|
+
this.profileStateRoot = join8(this.profileRoot, ".profile-state");
|
|
27160
27058
|
this.viewport = opts.viewport ?? BROWSER_DEFAULT_VIEWPORT;
|
|
27161
27059
|
this.idleTimeoutMs = opts.idleTimeoutMs ?? IDLE_TIMEOUT_MS;
|
|
27162
27060
|
this.frameMinIntervalMs = opts.frameMinIntervalMs ?? FRAME_MIN_INTERVAL_MS;
|
|
@@ -27248,13 +27146,13 @@ var BrowserManager = class {
|
|
|
27248
27146
|
exactChild(root, child) {
|
|
27249
27147
|
const canonicalRoot = resolve7(root);
|
|
27250
27148
|
const target = resolve7(canonicalRoot, child);
|
|
27251
|
-
if (
|
|
27149
|
+
if (dirname6(target) !== canonicalRoot) {
|
|
27252
27150
|
throw new Error("browser profile path escaped its owned root");
|
|
27253
27151
|
}
|
|
27254
27152
|
return target;
|
|
27255
27153
|
}
|
|
27256
27154
|
async ensureOwnedDirectory(path) {
|
|
27257
|
-
await
|
|
27155
|
+
await mkdir5(path, { recursive: true, mode: 448 });
|
|
27258
27156
|
const stat3 = await lstat6(path);
|
|
27259
27157
|
if (!stat3.isDirectory() || stat3.isSymbolicLink()) {
|
|
27260
27158
|
throw new Error("browser profile root must be an owned directory, not a symbolic link");
|
|
@@ -27320,7 +27218,7 @@ var BrowserManager = class {
|
|
|
27320
27218
|
await this.syncDirectory(this.profileStateRoot);
|
|
27321
27219
|
await this.syncDirectory(this.profileRoot);
|
|
27322
27220
|
} catch (error52) {
|
|
27323
|
-
await
|
|
27221
|
+
await rm5(temporary, { force: true }).catch(() => {
|
|
27324
27222
|
});
|
|
27325
27223
|
throw error52;
|
|
27326
27224
|
}
|
|
@@ -27396,7 +27294,7 @@ var BrowserManager = class {
|
|
|
27396
27294
|
} catch (error52) {
|
|
27397
27295
|
if (error52.code !== "ENOENT") throw error52;
|
|
27398
27296
|
}
|
|
27399
|
-
await
|
|
27297
|
+
await mkdir5(profileDir, { recursive: true, mode: 448 });
|
|
27400
27298
|
const adapter = await this.opts.factory.open({
|
|
27401
27299
|
agentId,
|
|
27402
27300
|
profileDir,
|
|
@@ -27475,7 +27373,7 @@ var BrowserManager = class {
|
|
|
27475
27373
|
purgeId
|
|
27476
27374
|
});
|
|
27477
27375
|
await this.closeLocked(agentId, "stopped");
|
|
27478
|
-
await
|
|
27376
|
+
await rm5(this.profilePath(agentId), { recursive: true, force: true, maxRetries: 3 });
|
|
27479
27377
|
await this.syncDirectory(this.profileRoot);
|
|
27480
27378
|
});
|
|
27481
27379
|
}
|
|
@@ -28166,9 +28064,9 @@ function createPlaywrightBrowserAdapterFactory(dependencies = {}) {
|
|
|
28166
28064
|
// src/runners/cli-runner.ts
|
|
28167
28065
|
import { spawn as spawn8 } from "node:child_process";
|
|
28168
28066
|
import { randomUUID as randomUUID10 } from "node:crypto";
|
|
28169
|
-
import { lstat as lstat11, mkdir as
|
|
28067
|
+
import { lstat as lstat11, mkdir as mkdir10, realpath as realpath8 } from "node:fs/promises";
|
|
28170
28068
|
import { homedir as homedir5 } from "node:os";
|
|
28171
|
-
import { dirname as
|
|
28069
|
+
import { dirname as dirname8, isAbsolute as isAbsolute14, join as join14, resolve as resolve10 } from "node:path";
|
|
28172
28070
|
|
|
28173
28071
|
// src/tool-packs/browser/authentication-wall.ts
|
|
28174
28072
|
var AUTH_PATH_SEGMENT = /(?:^|\/)(?:log[-_]?in|sign[-_]?in|sso|saml|auth|authorize|authenticate|oauth2?|session\/new|checkpoint)(?:\/|$)/i;
|
|
@@ -28455,7 +28353,7 @@ function createBrowserToolPack(deps) {
|
|
|
28455
28353
|
}
|
|
28456
28354
|
|
|
28457
28355
|
// src/tool-packs/provider-intents.ts
|
|
28458
|
-
import { createHash as
|
|
28356
|
+
import { createHash as createHash2, randomUUID as randomUUID3 } from "node:crypto";
|
|
28459
28357
|
|
|
28460
28358
|
// src/tool-packs/github/rest-transport.ts
|
|
28461
28359
|
var MAX_RESPONSE_BYTES = 2 * 1024 * 1024;
|
|
@@ -28701,7 +28599,7 @@ function canonicalJson(value) {
|
|
|
28701
28599
|
return `{${Object.entries(value).sort(([left], [right]) => left < right ? -1 : left > right ? 1 : 0).map(([key, child]) => `${JSON.stringify(key)}:${canonicalJson(child)}`).join(",")}}`;
|
|
28702
28600
|
}
|
|
28703
28601
|
function payloadFingerprint(value) {
|
|
28704
|
-
return
|
|
28602
|
+
return createHash2("sha256").update(canonicalJson(value)).digest("hex");
|
|
28705
28603
|
}
|
|
28706
28604
|
function claimResult(result) {
|
|
28707
28605
|
if (!result.ok || !result.result || typeof result.result !== "object") return null;
|
|
@@ -30893,14 +30791,14 @@ function createGithubPushOrchestrator(input) {
|
|
|
30893
30791
|
// src/tool-packs/github/git-bridge.ts
|
|
30894
30792
|
import { spawn as spawn6 } from "node:child_process";
|
|
30895
30793
|
import { randomUUID as randomUUID7 } from "node:crypto";
|
|
30896
|
-
import { chmod as chmod4, lstat as lstat8, mkdir as
|
|
30897
|
-
import { dirname as
|
|
30794
|
+
import { chmod as chmod4, lstat as lstat8, mkdir as mkdir6, realpath as realpath5, rm as rm6 } from "node:fs/promises";
|
|
30795
|
+
import { dirname as dirname7, isAbsolute as isAbsolute10, join as join10, relative as relative6 } from "node:path";
|
|
30898
30796
|
|
|
30899
30797
|
// src/tool-packs/github/git-credential-broker.ts
|
|
30900
|
-
import { createServer
|
|
30798
|
+
import { createServer } from "node:http";
|
|
30901
30799
|
import { randomBytes, randomUUID as randomUUID6, timingSafeEqual } from "node:crypto";
|
|
30902
30800
|
import { chmod as chmod3, lstat as lstat7, realpath as realpath4, writeFile as writeFile2 } from "node:fs/promises";
|
|
30903
|
-
import { isAbsolute as isAbsolute9, join as
|
|
30801
|
+
import { isAbsolute as isAbsolute9, join as join9, relative as relative5 } from "node:path";
|
|
30904
30802
|
var MAX_REQUEST_BYTES = 16 * 1024;
|
|
30905
30803
|
var FILE_MODE2 = 384;
|
|
30906
30804
|
var HELPER_SOURCE = String.raw`'use strict';
|
|
@@ -31029,14 +30927,14 @@ async function createGithubGitCredentialBroker(input) {
|
|
|
31029
30927
|
throw new Error("Git credential broker requires a private real run directory");
|
|
31030
30928
|
}
|
|
31031
30929
|
const runRoot = await realpath4(input.runArtifactsRoot);
|
|
31032
|
-
const helperPath =
|
|
30930
|
+
const helperPath = join9(runRoot, `git-credential-${randomUUID6()}.cjs`);
|
|
31033
30931
|
assertChildPath(runRoot, helperPath);
|
|
31034
30932
|
await writeFile2(helperPath, HELPER_SOURCE, { flag: "wx", mode: FILE_MODE2 });
|
|
31035
30933
|
await chmod3(helperPath, FILE_MODE2);
|
|
31036
30934
|
const capability2 = randomBytes(32).toString("base64url");
|
|
31037
30935
|
const expectedPath = `${input.repositoryFullName}.git`;
|
|
31038
30936
|
let closed = false;
|
|
31039
|
-
const server =
|
|
30937
|
+
const server = createServer(async (request, response) => {
|
|
31040
30938
|
try {
|
|
31041
30939
|
if (closed || input.authoritySignal.aborted || input.expiresAt !== null && input.expiresAt.getTime() <= Date.now()) {
|
|
31042
30940
|
reject(response, 410);
|
|
@@ -31145,7 +31043,7 @@ async function requireRealDirectory2(path, label) {
|
|
|
31145
31043
|
async function validateTokenlessPaths(command) {
|
|
31146
31044
|
if (command.kind === "clone-from-bridge") {
|
|
31147
31045
|
if (!isAbsolute10(command.destination)) throw new GithubGitProcessError("invalid_input");
|
|
31148
|
-
const parent = await requireRealDirectory2(
|
|
31046
|
+
const parent = await requireRealDirectory2(dirname7(command.destination), "clone parent");
|
|
31149
31047
|
assertBelow2(parent, command.destination, "clone destination");
|
|
31150
31048
|
const destination = await lstat8(command.destination).catch((error52) => {
|
|
31151
31049
|
if (error52.code === "ENOENT") return null;
|
|
@@ -31433,9 +31331,9 @@ function createGithubGitBridge(input) {
|
|
|
31433
31331
|
async createPrivateBridge() {
|
|
31434
31332
|
if (closed) throw new GithubGitProcessError("cancelled");
|
|
31435
31333
|
const current = await roots();
|
|
31436
|
-
const path =
|
|
31334
|
+
const path = join10(current.bridges, `${randomUUID7()}.git`);
|
|
31437
31335
|
assertBelow2(current.bridges, path, "git bridge");
|
|
31438
|
-
await
|
|
31336
|
+
await mkdir6(path, { mode: DIRECTORY_MODE2 });
|
|
31439
31337
|
await chmod4(path, DIRECTORY_MODE2);
|
|
31440
31338
|
try {
|
|
31441
31339
|
await runGit(
|
|
@@ -31451,16 +31349,16 @@ function createGithubGitBridge(input) {
|
|
|
31451
31349
|
);
|
|
31452
31350
|
const real = await requireRealDirectory2(path, "git bridge");
|
|
31453
31351
|
assertBelow2(current.bridges, real, "git bridge");
|
|
31454
|
-
const hooks =
|
|
31455
|
-
await
|
|
31456
|
-
await
|
|
31352
|
+
const hooks = join10(real, "hooks");
|
|
31353
|
+
await rm6(hooks, { recursive: true, force: true });
|
|
31354
|
+
await mkdir6(hooks, { mode: DIRECTORY_MODE2 });
|
|
31457
31355
|
await chmod4(hooks, DIRECTORY_MODE2);
|
|
31458
|
-
const config2 =
|
|
31356
|
+
const config2 = join10(real, "config");
|
|
31459
31357
|
await chmod4(config2, 384);
|
|
31460
31358
|
active.add(real);
|
|
31461
31359
|
return real;
|
|
31462
31360
|
} catch (error52) {
|
|
31463
|
-
await
|
|
31361
|
+
await rm6(path, { recursive: true, force: true }).catch(() => {
|
|
31464
31362
|
});
|
|
31465
31363
|
throw error52;
|
|
31466
31364
|
}
|
|
@@ -31554,7 +31452,7 @@ function createGithubGitBridge(input) {
|
|
|
31554
31452
|
},
|
|
31555
31453
|
async destroyPrivateBridge(path) {
|
|
31556
31454
|
const bridge = await requireBridge(path);
|
|
31557
|
-
await
|
|
31455
|
+
await rm6(bridge, { recursive: true, force: true });
|
|
31558
31456
|
active.delete(bridge);
|
|
31559
31457
|
credentialed2.delete(bridge);
|
|
31560
31458
|
},
|
|
@@ -31562,7 +31460,7 @@ function createGithubGitBridge(input) {
|
|
|
31562
31460
|
if (closed) return;
|
|
31563
31461
|
closed = true;
|
|
31564
31462
|
const paths = [...active];
|
|
31565
|
-
await Promise.all(paths.map((path) =>
|
|
31463
|
+
await Promise.all(paths.map((path) => rm6(path, { recursive: true, force: true })));
|
|
31566
31464
|
active.clear();
|
|
31567
31465
|
credentialed2.clear();
|
|
31568
31466
|
}
|
|
@@ -31903,8 +31801,8 @@ function createRepositoryTools(runtime) {
|
|
|
31903
31801
|
|
|
31904
31802
|
// src/tool-packs/github/workspace.ts
|
|
31905
31803
|
import { randomUUID as randomUUID8 } from "node:crypto";
|
|
31906
|
-
import { chmod as chmod5, lstat as lstat9, mkdir as
|
|
31907
|
-
import { isAbsolute as isAbsolute11, join as
|
|
31804
|
+
import { chmod as chmod5, lstat as lstat9, mkdir as mkdir7, readFile as readFile8, realpath as realpath6, rename as rename5, rm as rm7, writeFile as writeFile3 } from "node:fs/promises";
|
|
31805
|
+
import { isAbsolute as isAbsolute11, join as join11, relative as relative7, resolve as resolve8 } from "node:path";
|
|
31908
31806
|
var SAFE_LOCAL_ID = /^[A-Za-z0-9_-]{1,200}$/;
|
|
31909
31807
|
var FULL_NAME2 = /^[A-Za-z0-9_.-]{1,100}\/[A-Za-z0-9_.-]{1,100}$/;
|
|
31910
31808
|
var DIRECTORY_MODE3 = 448;
|
|
@@ -31941,10 +31839,10 @@ async function requireRealDirectory3(path, label) {
|
|
|
31941
31839
|
return real;
|
|
31942
31840
|
}
|
|
31943
31841
|
async function createOrRequirePrivateDirectory(parent, name, label) {
|
|
31944
|
-
const path =
|
|
31842
|
+
const path = join11(parent, name);
|
|
31945
31843
|
assertBelow3(parent, path, label);
|
|
31946
31844
|
try {
|
|
31947
|
-
await
|
|
31845
|
+
await mkdir7(path, { mode: DIRECTORY_MODE3 });
|
|
31948
31846
|
} catch (error52) {
|
|
31949
31847
|
if (error52.code !== "EEXIST") throw error52;
|
|
31950
31848
|
}
|
|
@@ -32024,8 +31922,8 @@ async function createGithubWorkspaceService(input) {
|
|
|
32024
31922
|
if (expectedFullName !== void 0 && repository.fullName !== expectedFullName) {
|
|
32025
31923
|
throw new Error("GitHub repository name does not match this task grant");
|
|
32026
31924
|
}
|
|
32027
|
-
const destination =
|
|
32028
|
-
const metadataPath =
|
|
31925
|
+
const destination = join11(repositoriesRoot, parsed.data);
|
|
31926
|
+
const metadataPath = join11(metadataRoot, `${parsed.data}.json`);
|
|
32029
31927
|
if (!await pathExists(destination) || !await pathExists(metadataPath)) {
|
|
32030
31928
|
throw new Error("GitHub repository workspace has not been prepared");
|
|
32031
31929
|
}
|
|
@@ -32042,14 +31940,14 @@ async function createGithubWorkspaceService(input) {
|
|
|
32042
31940
|
return real;
|
|
32043
31941
|
};
|
|
32044
31942
|
const cloneRepository = async (clone2) => {
|
|
32045
|
-
const destination =
|
|
32046
|
-
const metadataPath =
|
|
31943
|
+
const destination = join11(repositoriesRoot, clone2.repositoryId);
|
|
31944
|
+
const metadataPath = join11(metadataRoot, `${clone2.repositoryId}.json`);
|
|
32047
31945
|
assertBelow3(repositoriesRoot, destination, "repository path");
|
|
32048
31946
|
assertBelow3(metadataRoot, metadataPath, "repository metadata");
|
|
32049
31947
|
if (await pathExists(destination) || await pathExists(metadataPath)) {
|
|
32050
31948
|
throw new Error("GitHub repository workspace already exists or is inconsistent");
|
|
32051
31949
|
}
|
|
32052
|
-
const temporary =
|
|
31950
|
+
const temporary = join11(repositoriesRoot, `.clone-${randomUUID8()}`);
|
|
32053
31951
|
assertBelow3(repositoriesRoot, temporary, "temporary clone");
|
|
32054
31952
|
try {
|
|
32055
31953
|
await input.git.clone({
|
|
@@ -32074,7 +31972,7 @@ async function createGithubWorkspaceService(input) {
|
|
|
32074
31972
|
path: destination,
|
|
32075
31973
|
...clone2.createIntentId === void 0 ? {} : { createIntentId: clone2.createIntentId }
|
|
32076
31974
|
};
|
|
32077
|
-
const metadataTemporary =
|
|
31975
|
+
const metadataTemporary = join11(metadataRoot, `.${clone2.repositoryId}-${randomUUID8()}.tmp`);
|
|
32078
31976
|
assertBelow3(metadataRoot, metadataTemporary, "temporary repository metadata");
|
|
32079
31977
|
await writeFile3(metadataTemporary, `${JSON.stringify(metadata)}
|
|
32080
31978
|
`, {
|
|
@@ -32087,11 +31985,11 @@ async function createGithubWorkspaceService(input) {
|
|
|
32087
31985
|
try {
|
|
32088
31986
|
await rename5(metadataTemporary, metadataPath);
|
|
32089
31987
|
} catch (error52) {
|
|
32090
|
-
await
|
|
31988
|
+
await rm7(destination, { recursive: true, force: true });
|
|
32091
31989
|
throw error52;
|
|
32092
31990
|
}
|
|
32093
31991
|
} finally {
|
|
32094
|
-
await
|
|
31992
|
+
await rm7(metadataTemporary, { force: true }).catch(() => {
|
|
32095
31993
|
});
|
|
32096
31994
|
}
|
|
32097
31995
|
const path = await requireRealDirectory3(destination, "GitHub repository");
|
|
@@ -32103,14 +32001,14 @@ async function createGithubWorkspaceService(input) {
|
|
|
32103
32001
|
headSha
|
|
32104
32002
|
};
|
|
32105
32003
|
} finally {
|
|
32106
|
-
await
|
|
32004
|
+
await rm7(temporary, { recursive: true, force: true }).catch(() => {
|
|
32107
32005
|
});
|
|
32108
32006
|
}
|
|
32109
32007
|
};
|
|
32110
32008
|
const prepareRepository = async (authority) => {
|
|
32111
32009
|
const { repository } = authority;
|
|
32112
|
-
const destination =
|
|
32113
|
-
const metadataPath =
|
|
32010
|
+
const destination = join11(repositoriesRoot, repository.repositoryId);
|
|
32011
|
+
const metadataPath = join11(metadataRoot, `${repository.repositoryId}.json`);
|
|
32114
32012
|
assertBelow3(repositoriesRoot, destination, "repository path");
|
|
32115
32013
|
assertBelow3(metadataRoot, metadataPath, "repository metadata");
|
|
32116
32014
|
return withWorkspaceLock(destination, async () => {
|
|
@@ -32275,7 +32173,7 @@ async function createGithubWorkspaceService(input) {
|
|
|
32275
32173
|
throw new Error("GitHub created repository is outside this installation");
|
|
32276
32174
|
}
|
|
32277
32175
|
parseGitRef(cloneInput.repository.defaultBranch, "default branch");
|
|
32278
|
-
return withWorkspaceLock(
|
|
32176
|
+
return withWorkspaceLock(join11(repositoriesRoot, repositoryId2), async () => {
|
|
32279
32177
|
const prepared = await cloneRepository({
|
|
32280
32178
|
repositoryId: repositoryId2,
|
|
32281
32179
|
fullName: cloneInput.repository.fullName,
|
|
@@ -32682,7 +32580,7 @@ function createGithubToolPackFactory(options = {}) {
|
|
|
32682
32580
|
var githubToolPackFactory = createGithubToolPackFactory();
|
|
32683
32581
|
|
|
32684
32582
|
// src/runners/linear-api.ts
|
|
32685
|
-
import { createHash as
|
|
32583
|
+
import { createHash as createHash3, randomUUID as randomUUID9 } from "node:crypto";
|
|
32686
32584
|
var MAX_RESPONSE_BYTES2 = 2 * 1024 * 1024;
|
|
32687
32585
|
var MAX_RESULT_STRING = 1e5;
|
|
32688
32586
|
var MAX_RESULT_ARRAY = 100;
|
|
@@ -33253,7 +33151,7 @@ function operationFor(name, args, appUserId, heldBy) {
|
|
|
33253
33151
|
}
|
|
33254
33152
|
}
|
|
33255
33153
|
function fingerprint(value) {
|
|
33256
|
-
return
|
|
33154
|
+
return createHash3("sha256").update(canonicalLinearMutationPayload(value)).digest("hex");
|
|
33257
33155
|
}
|
|
33258
33156
|
function providerIntentFor(mutation, payloadFingerprint2) {
|
|
33259
33157
|
const common = {
|
|
@@ -33816,8 +33714,8 @@ function createDefaultToolPackRegistry() {
|
|
|
33816
33714
|
}
|
|
33817
33715
|
|
|
33818
33716
|
// src/runners/attachments.ts
|
|
33819
|
-
import { mkdir as
|
|
33820
|
-
import { join as
|
|
33717
|
+
import { mkdir as mkdir8, writeFile as writeFile4 } from "node:fs/promises";
|
|
33718
|
+
import { join as join12 } from "node:path";
|
|
33821
33719
|
var WINDOWS_RESERVED = /^(con|prn|aux|nul|com[1-9]|lpt[1-9])(\..*)?$/i;
|
|
33822
33720
|
function sanitizeAttachmentFileName(name) {
|
|
33823
33721
|
const base = name.split(/[/\\]/).pop() ?? "";
|
|
@@ -33846,9 +33744,9 @@ async function materializeAttachments(task, taskRoot) {
|
|
|
33846
33744
|
`attached file "${attachment.name}" arrived incomplete (${bytes.byteLength} of ${attachment.size} bytes)`
|
|
33847
33745
|
);
|
|
33848
33746
|
}
|
|
33849
|
-
const directory =
|
|
33850
|
-
await
|
|
33851
|
-
const path =
|
|
33747
|
+
const directory = join12(taskRoot, ".zixt-attachments", task.taskId, attachment.id);
|
|
33748
|
+
await mkdir8(directory, { recursive: true });
|
|
33749
|
+
const path = join12(directory, sanitizeAttachmentFileName(attachment.name));
|
|
33852
33750
|
await writeFile4(path, bytes);
|
|
33853
33751
|
materialized.push({
|
|
33854
33752
|
path,
|
|
@@ -33876,7 +33774,7 @@ function renderAttachmentSection(files) {
|
|
|
33876
33774
|
}
|
|
33877
33775
|
|
|
33878
33776
|
// src/runners/ask-user-server.ts
|
|
33879
|
-
import { createServer as
|
|
33777
|
+
import { createServer as createServer2 } from "node:http";
|
|
33880
33778
|
|
|
33881
33779
|
// src/runners/ask-user-secrets.ts
|
|
33882
33780
|
var SECRET_NOUN_SOURCE = "(?:passwords?|passphrases?|api[ -]?keys?|access tokens?|auth tokens?|api tokens?|bearer tokens?|refresh tokens?|tokens?|secret keys?|client secrets?|private keys?|one[- ]time (?:code|password)s?|otps?|2fa codes?|mfa codes?|verification codes?|security codes?|session cookies?)";
|
|
@@ -34546,7 +34444,7 @@ function createAskUserServer() {
|
|
|
34546
34444
|
let listening;
|
|
34547
34445
|
function ensureListening() {
|
|
34548
34446
|
listening ??= new Promise((resolve17, reject3) => {
|
|
34549
|
-
server =
|
|
34447
|
+
server = createServer2((req, res) => {
|
|
34550
34448
|
res.on("error", () => {
|
|
34551
34449
|
});
|
|
34552
34450
|
handle(req, res).catch(() => {
|
|
@@ -34953,9 +34851,9 @@ function buildRunnerEnv(input) {
|
|
|
34953
34851
|
// src/runners/github-shell-auth.ts
|
|
34954
34852
|
import { execFile } from "node:child_process";
|
|
34955
34853
|
import { randomBytes as randomBytes2, timingSafeEqual as timingSafeEqual2 } from "node:crypto";
|
|
34956
|
-
import { chmod as chmod6, lstat as lstat10, mkdir as
|
|
34957
|
-
import { createServer as
|
|
34958
|
-
import { isAbsolute as isAbsolute13, join as
|
|
34854
|
+
import { chmod as chmod6, lstat as lstat10, mkdir as mkdir9, realpath as realpath7, writeFile as writeFile5 } from "node:fs/promises";
|
|
34855
|
+
import { createServer as createServer3 } from "node:http";
|
|
34856
|
+
import { isAbsolute as isAbsolute13, join as join13, relative as relative8 } from "node:path";
|
|
34959
34857
|
var MAX_REQUEST_BYTES2 = 16 * 1024;
|
|
34960
34858
|
var DIRECTORY_MODE4 = 448;
|
|
34961
34859
|
var PRIVATE_FILE_MODE = 384;
|
|
@@ -35343,7 +35241,7 @@ async function prepareHelpers(input) {
|
|
|
35343
35241
|
throw new Error("GitHub shell authentication requires a private real run directory");
|
|
35344
35242
|
}
|
|
35345
35243
|
const runRoot = await realpath7(input.runRoot);
|
|
35346
|
-
const helperPath =
|
|
35244
|
+
const helperPath = join13(runRoot, "github-shell-git-credential.cjs");
|
|
35347
35245
|
assertChildPath2(runRoot, helperPath);
|
|
35348
35246
|
await writePrivate(helperPath, GIT_HELPER_SOURCE);
|
|
35349
35247
|
if (!input.ghExecutablePath) {
|
|
@@ -35354,14 +35252,14 @@ async function prepareHelpers(input) {
|
|
|
35354
35252
|
wrapperSourcePath: null
|
|
35355
35253
|
};
|
|
35356
35254
|
}
|
|
35357
|
-
const shellToolsDirectory =
|
|
35255
|
+
const shellToolsDirectory = join13(runRoot, "shell-tools");
|
|
35358
35256
|
assertChildPath2(runRoot, shellToolsDirectory);
|
|
35359
|
-
await
|
|
35257
|
+
await mkdir9(shellToolsDirectory, { mode: DIRECTORY_MODE4 });
|
|
35360
35258
|
await chmod6(shellToolsDirectory, DIRECTORY_MODE4);
|
|
35361
|
-
const wrapperSourcePath =
|
|
35259
|
+
const wrapperSourcePath = join13(runRoot, "github-shell-gh-wrapper.cjs");
|
|
35362
35260
|
assertChildPath2(runRoot, wrapperSourcePath);
|
|
35363
35261
|
await writePrivate(wrapperSourcePath, GH_WRAPPER_SOURCE);
|
|
35364
|
-
const wrapperPath =
|
|
35262
|
+
const wrapperPath = join13(shellToolsDirectory, process.platform === "win32" ? "gh.cmd" : "gh");
|
|
35365
35263
|
assertChildPath2(runRoot, wrapperPath);
|
|
35366
35264
|
const launcher = process.platform === "win32" ? `@"${process.execPath.replaceAll('"', '""')}" "${wrapperSourcePath.replaceAll('"', '""')}" %*\r
|
|
35367
35265
|
` : `#!/bin/sh
|
|
@@ -35481,7 +35379,7 @@ async function createGithubShellAuth(input) {
|
|
|
35481
35379
|
});
|
|
35482
35380
|
const capability2 = randomBytes2(32).toString("base64url");
|
|
35483
35381
|
let closed = false;
|
|
35484
|
-
const server =
|
|
35382
|
+
const server = createServer3(async (request, response) => {
|
|
35485
35383
|
try {
|
|
35486
35384
|
if (closed || input.authoritySignal.aborted) {
|
|
35487
35385
|
reject2(response, 410);
|
|
@@ -36155,7 +36053,7 @@ async function settlesWithin(promise2, timeoutMs) {
|
|
|
36155
36053
|
}
|
|
36156
36054
|
}
|
|
36157
36055
|
function defaultRunnerWorkspaceRoot() {
|
|
36158
|
-
return
|
|
36056
|
+
return join14(homedir5(), ".zixt", "workspaces");
|
|
36159
36057
|
}
|
|
36160
36058
|
function defaultRunnerArtifactRoot() {
|
|
36161
36059
|
return defaultRunArtifactRoot();
|
|
@@ -36204,7 +36102,7 @@ function createCliRunner(adapter, opts = {}) {
|
|
|
36204
36102
|
const prefixArgs = opts.commandPrefixArgs ?? [];
|
|
36205
36103
|
const maxWallTimeMs = opts.maxWallTimeMs;
|
|
36206
36104
|
const workspaceRoot = opts.workspaceRoot ?? defaultRunnerWorkspaceRoot();
|
|
36207
|
-
const artifactRoot = opts.artifactRoot ?? (opts.workspaceRoot === void 0 ? defaultRunnerArtifactRoot() :
|
|
36105
|
+
const artifactRoot = opts.artifactRoot ?? (opts.workspaceRoot === void 0 ? defaultRunnerArtifactRoot() : join14(dirname8(workspaceRoot), "run-artifacts"));
|
|
36208
36106
|
const runRegistryRoot2 = opts.runRegistryRoot ?? defaultRunRegistryRoot();
|
|
36209
36107
|
const createArtifacts = opts.createArtifacts ?? createRunArtifacts;
|
|
36210
36108
|
const toolPackRegistry2 = opts.toolPackRegistry ?? createDefaultToolPackRegistry();
|
|
@@ -36222,7 +36120,7 @@ function createCliRunner(adapter, opts = {}) {
|
|
|
36222
36120
|
};
|
|
36223
36121
|
const askUserServer = createAskUserServer();
|
|
36224
36122
|
const windowsRoot = process.env.SystemRoot ?? process.env.WINDIR;
|
|
36225
|
-
const windowsComspecCandidate = process.platform === "win32" && windowsRoot ?
|
|
36123
|
+
const windowsComspecCandidate = process.platform === "win32" && windowsRoot ? join14(windowsRoot, "System32", "cmd.exe") : void 0;
|
|
36226
36124
|
let safetyFailure;
|
|
36227
36125
|
return async (task) => {
|
|
36228
36126
|
if (safetyFailure) {
|
|
@@ -36262,8 +36160,8 @@ function createCliRunner(adapter, opts = {}) {
|
|
|
36262
36160
|
usage: { inputTokens: 0, outputTokens: 0 }
|
|
36263
36161
|
};
|
|
36264
36162
|
}
|
|
36265
|
-
const taskRoot =
|
|
36266
|
-
await
|
|
36163
|
+
const taskRoot = join14(workspaceRoot, task.agentId);
|
|
36164
|
+
await mkdir10(taskRoot, { recursive: true });
|
|
36267
36165
|
if (task.cancelledNow()) return cancelledBeforeRun();
|
|
36268
36166
|
const configuredWorkspace = task.spec.workspace;
|
|
36269
36167
|
let cwd = taskRoot;
|
|
@@ -36571,7 +36469,7 @@ ${attachmentSection}` : prompt;
|
|
|
36571
36469
|
for (const path of paths) {
|
|
36572
36470
|
if (!path || path.length > 4096) continue;
|
|
36573
36471
|
const absolutePath = isAbsolute14(path) ? path : resolve10(cwd, path);
|
|
36574
|
-
const directory =
|
|
36472
|
+
const directory = dirname8(absolutePath);
|
|
36575
36473
|
observedWorkingDirectories.delete(directory);
|
|
36576
36474
|
observedWorkingDirectories.add(directory);
|
|
36577
36475
|
while (observedWorkingDirectories.size > 19) {
|
|
@@ -37017,7 +36915,7 @@ function runCliProcess(options) {
|
|
|
37017
36915
|
// The idle pre-assignment guardian must never load from or depend
|
|
37018
36916
|
// on an untrusted Task checkout. Only the post-gate target enters
|
|
37019
36917
|
// the requested working directory from its private release frame.
|
|
37020
|
-
cwd:
|
|
36918
|
+
cwd: dirname8(options.guardian.scriptPath),
|
|
37021
36919
|
env: runnerGuardianEnv(process.env, containmentGateNonce),
|
|
37022
36920
|
stdio: ["pipe", "pipe", "pipe"],
|
|
37023
36921
|
windowsHide: true,
|
|
@@ -37299,7 +37197,7 @@ import { randomUUID as randomUUID11 } from "node:crypto";
|
|
|
37299
37197
|
// src/runners/runtime-observation.ts
|
|
37300
37198
|
import { open as open6, readdir as readdir4, realpath as realpath9 } from "node:fs/promises";
|
|
37301
37199
|
import { homedir as homedir6 } from "node:os";
|
|
37302
|
-
import { join as
|
|
37200
|
+
import { join as join15 } from "node:path";
|
|
37303
37201
|
var READ_WINDOW_BYTES = 1024 * 1024;
|
|
37304
37202
|
var CATALOG_TIMEOUT_MS = 15e3;
|
|
37305
37203
|
var CATALOG_OUTPUT_LIMIT_BYTES = 4 * 1024 * 1024;
|
|
@@ -37359,9 +37257,9 @@ function displayValue(value, maxLength) {
|
|
|
37359
37257
|
return trimmed;
|
|
37360
37258
|
}
|
|
37361
37259
|
function claudeTranscriptPath(input) {
|
|
37362
|
-
const configDir = input.env["CLAUDE_CONFIG_DIR"] ||
|
|
37260
|
+
const configDir = input.env["CLAUDE_CONFIG_DIR"] || join15(homeFrom(input.env), ".claude");
|
|
37363
37261
|
const slug = input.resolvedCwd.replace(/[^a-zA-Z0-9]/g, "-");
|
|
37364
|
-
return
|
|
37262
|
+
return join15(configDir, "projects", slug, `${input.sessionId}.jsonl`);
|
|
37365
37263
|
}
|
|
37366
37264
|
async function readClaudeSessionEffort(input) {
|
|
37367
37265
|
const resolvedCwd = await realpath9(input.cwd).catch(() => input.cwd);
|
|
@@ -37377,18 +37275,18 @@ async function readClaudeSessionEffort(input) {
|
|
|
37377
37275
|
}
|
|
37378
37276
|
async function newestDirectories(root, limit) {
|
|
37379
37277
|
const entries = await readdir4(root, { withFileTypes: true }).catch(() => []);
|
|
37380
|
-
return entries.filter((entry) => entry.isDirectory()).map((entry) => entry.name).sort((left, right) => right.localeCompare(left)).slice(0, limit).map((name) =>
|
|
37278
|
+
return entries.filter((entry) => entry.isDirectory()).map((entry) => entry.name).sort((left, right) => right.localeCompare(left)).slice(0, limit).map((name) => join15(root, name));
|
|
37381
37279
|
}
|
|
37382
37280
|
async function findCodexRolloutPath(input) {
|
|
37383
|
-
const codexHome = input.env["CODEX_HOME"] ||
|
|
37384
|
-
const sessions =
|
|
37281
|
+
const codexHome = input.env["CODEX_HOME"] || join15(homeFrom(input.env), ".codex");
|
|
37282
|
+
const sessions = join15(codexHome, "sessions");
|
|
37385
37283
|
const suffix = `-${input.threadId}.jsonl`;
|
|
37386
37284
|
for (const year of await newestDirectories(sessions, 2)) {
|
|
37387
37285
|
for (const month of await newestDirectories(year, 2)) {
|
|
37388
37286
|
for (const day of await newestDirectories(month, 3)) {
|
|
37389
37287
|
const files = await readdir4(day).catch(() => []);
|
|
37390
37288
|
const match = files.find((name) => name.endsWith(suffix));
|
|
37391
|
-
if (match) return
|
|
37289
|
+
if (match) return join15(day, match);
|
|
37392
37290
|
}
|
|
37393
37291
|
}
|
|
37394
37292
|
}
|
|
@@ -37772,18 +37670,18 @@ function improveErrorMessage(error52) {
|
|
|
37772
37670
|
}
|
|
37773
37671
|
|
|
37774
37672
|
// src/runners/codex.ts
|
|
37775
|
-
import { mkdir as
|
|
37673
|
+
import { mkdir as mkdir11, readFile as readFile9, writeFile as writeFile6 } from "node:fs/promises";
|
|
37776
37674
|
import { randomUUID as randomUUID12 } from "node:crypto";
|
|
37777
37675
|
import { homedir as homedir7 } from "node:os";
|
|
37778
|
-
import { join as
|
|
37676
|
+
import { join as join16 } from "node:path";
|
|
37779
37677
|
var CODEX_NOT_FOUND_MESSAGE = "The `codex` CLI was not found on this Machine. Install it (npm install -g @openai/codex) and sign in with `codex login`, or switch the agent to API-key auth.";
|
|
37780
37678
|
function defaultCodexThreadIndexRoot() {
|
|
37781
|
-
return
|
|
37679
|
+
return join16(homedir7(), ".zixt", "codex-threads");
|
|
37782
37680
|
}
|
|
37783
37681
|
var SAFE_SEGMENT3 = /^[A-Za-z0-9_-]{1,200}$/;
|
|
37784
37682
|
function threadIndexPath(root, agentId, sessionKey) {
|
|
37785
37683
|
if (!SAFE_SEGMENT3.test(agentId) || !SAFE_SEGMENT3.test(sessionKey)) return null;
|
|
37786
|
-
return
|
|
37684
|
+
return join16(root, agentId, `${sessionKey}.json`);
|
|
37787
37685
|
}
|
|
37788
37686
|
async function readThreadId(path) {
|
|
37789
37687
|
try {
|
|
@@ -37878,7 +37776,7 @@ ${value}` : value;
|
|
|
37878
37776
|
const recordedThreadId = indexPath ? await readThreadId(indexPath) : null;
|
|
37879
37777
|
const rememberThread = (threadId) => {
|
|
37880
37778
|
if (!indexPath) return;
|
|
37881
|
-
void
|
|
37779
|
+
void mkdir11(join16(threadIndexRoot, task.agentId), { recursive: true }).then(() => writeFile6(indexPath, JSON.stringify({ threadId }), "utf8")).catch(() => {
|
|
37882
37780
|
});
|
|
37883
37781
|
};
|
|
37884
37782
|
const observeRuntime = (threadId) => {
|
|
@@ -38614,9 +38512,9 @@ function run2(command, args) {
|
|
|
38614
38512
|
// src/linux-service.ts
|
|
38615
38513
|
import { spawn as spawn10 } from "node:child_process";
|
|
38616
38514
|
import { constants as constants2 } from "node:fs";
|
|
38617
|
-
import { access as access4, chmod as chmod7, mkdir as
|
|
38515
|
+
import { access as access4, chmod as chmod7, mkdir as mkdir12, open as open7, rename as rename6, rm as rm8 } from "node:fs/promises";
|
|
38618
38516
|
import { homedir as homedir8, userInfo } from "node:os";
|
|
38619
|
-
import { basename as
|
|
38517
|
+
import { basename as basename4, dirname as dirname9, join as join17, relative as relative9, resolve as resolve12, sep as sep5 } from "node:path";
|
|
38620
38518
|
var SERVICE_NAME = "zixt-host.service";
|
|
38621
38519
|
var SYSTEM_SERVICE_COMMAND_TIMEOUT_MS = 7e4;
|
|
38622
38520
|
var SERVICE_STABILITY_DELAY_MS = 2e3;
|
|
@@ -38717,22 +38615,22 @@ async function defaultSyncDirectory(path) {
|
|
|
38717
38615
|
}
|
|
38718
38616
|
}
|
|
38719
38617
|
async function ensureDirectory(path, mode, syncDirectory7) {
|
|
38720
|
-
const firstCreated = await
|
|
38618
|
+
const firstCreated = await mkdir12(path, { recursive: true, mode });
|
|
38721
38619
|
if (!firstCreated) return;
|
|
38722
38620
|
const first = resolve12(firstCreated);
|
|
38723
38621
|
const target = resolve12(path);
|
|
38724
|
-
await syncDirectory7(
|
|
38622
|
+
await syncDirectory7(dirname9(first));
|
|
38725
38623
|
let current = first;
|
|
38726
38624
|
const descendants = relative9(first, target);
|
|
38727
38625
|
for (const part of descendants ? descendants.split(sep5) : []) {
|
|
38728
38626
|
await syncDirectory7(current);
|
|
38729
|
-
current =
|
|
38627
|
+
current = join17(current, part);
|
|
38730
38628
|
}
|
|
38731
38629
|
}
|
|
38732
38630
|
async function replacePrivateFile(path, contents, mode, syncDirectory7) {
|
|
38733
|
-
const parent =
|
|
38631
|
+
const parent = dirname9(path);
|
|
38734
38632
|
await ensureDirectory(parent, 448, syncDirectory7);
|
|
38735
|
-
const temporary =
|
|
38633
|
+
const temporary = join17(parent, `.${basename4(path)}.${process.pid}.${crypto.randomUUID()}.tmp`);
|
|
38736
38634
|
const handle = await open7(temporary, "wx", mode);
|
|
38737
38635
|
try {
|
|
38738
38636
|
await handle.writeFile(contents, "utf8");
|
|
@@ -38743,7 +38641,7 @@ async function replacePrivateFile(path, contents, mode, syncDirectory7) {
|
|
|
38743
38641
|
await syncDirectory7(parent);
|
|
38744
38642
|
} catch (error52) {
|
|
38745
38643
|
await handle.close().catch(() => void 0);
|
|
38746
|
-
await
|
|
38644
|
+
await rm8(temporary, { force: true }).catch(() => void 0);
|
|
38747
38645
|
throw error52;
|
|
38748
38646
|
}
|
|
38749
38647
|
}
|
|
@@ -38784,11 +38682,11 @@ async function installLinuxService(options) {
|
|
|
38784
38682
|
"command search path"
|
|
38785
38683
|
);
|
|
38786
38684
|
const cloudUrl = options.cloudUrl ? oneLine(options.cloudUrl, "Zixt Cloud address") : void 0;
|
|
38787
|
-
const xdgConfigHome = env.XDG_CONFIG_HOME ? oneLine(env.XDG_CONFIG_HOME, "Linux configuration path") :
|
|
38788
|
-
const configRoot = options.serviceConfigRoot ??
|
|
38789
|
-
const unitRoot = options.userUnitRoot ??
|
|
38790
|
-
const environmentPath =
|
|
38791
|
-
const unitPath =
|
|
38685
|
+
const xdgConfigHome = env.XDG_CONFIG_HOME ? oneLine(env.XDG_CONFIG_HOME, "Linux configuration path") : join17(home, ".config");
|
|
38686
|
+
const configRoot = options.serviceConfigRoot ?? join17(xdgConfigHome, "zixt");
|
|
38687
|
+
const unitRoot = options.userUnitRoot ?? join17(xdgConfigHome, "systemd", "user");
|
|
38688
|
+
const environmentPath = join17(configRoot, "host.env");
|
|
38689
|
+
const unitPath = join17(unitRoot, SERVICE_NAME);
|
|
38792
38690
|
const installVersion = options.installVersion ?? installRelease;
|
|
38793
38691
|
const activateVersion = options.activateVersion ?? (options.installVersion ? async (entry) => entry : activateInstalledRelease);
|
|
38794
38692
|
const resolveCommand = options.resolveCommand ?? defaultResolveCommand;
|
|
@@ -38907,9 +38805,9 @@ async function installLinuxService(options) {
|
|
|
38907
38805
|
// src/macos-service.ts
|
|
38908
38806
|
import { spawn as spawn11 } from "node:child_process";
|
|
38909
38807
|
import { constants as constants3 } from "node:fs";
|
|
38910
|
-
import { access as access5, chmod as chmod8, mkdir as
|
|
38808
|
+
import { access as access5, chmod as chmod8, mkdir as mkdir13, open as open8, rename as rename7, rm as rm9 } from "node:fs/promises";
|
|
38911
38809
|
import { homedir as homedir9, userInfo as userInfo2 } from "node:os";
|
|
38912
|
-
import { basename as
|
|
38810
|
+
import { basename as basename5, dirname as dirname10, join as join18, relative as relative10, resolve as resolve13, sep as sep6 } from "node:path";
|
|
38913
38811
|
var LAUNCH_AGENT_LABEL = "ai.zixt.host";
|
|
38914
38812
|
var SERVICE_STABILITY_DELAY_MS2 = 2e3;
|
|
38915
38813
|
var COMMAND_TIMEOUT_MS2 = 7e4;
|
|
@@ -38933,21 +38831,21 @@ async function syncDirectory4(path) {
|
|
|
38933
38831
|
}
|
|
38934
38832
|
}
|
|
38935
38833
|
async function ensureDirectory2(path, sync) {
|
|
38936
|
-
const firstCreated = await
|
|
38834
|
+
const firstCreated = await mkdir13(path, { recursive: true, mode: 448 });
|
|
38937
38835
|
if (!firstCreated) return;
|
|
38938
38836
|
const first = resolve13(firstCreated);
|
|
38939
38837
|
const target = resolve13(path);
|
|
38940
|
-
await sync(
|
|
38838
|
+
await sync(dirname10(first));
|
|
38941
38839
|
let current = first;
|
|
38942
38840
|
for (const part of relative10(first, target).split(sep6).filter(Boolean)) {
|
|
38943
38841
|
await sync(current);
|
|
38944
|
-
current =
|
|
38842
|
+
current = join18(current, part);
|
|
38945
38843
|
}
|
|
38946
38844
|
}
|
|
38947
38845
|
async function replacePrivateFile2(path, contents, mode, sync) {
|
|
38948
|
-
const parent =
|
|
38846
|
+
const parent = dirname10(path);
|
|
38949
38847
|
await ensureDirectory2(parent, sync);
|
|
38950
|
-
const temporary =
|
|
38848
|
+
const temporary = join18(parent, `.${basename5(path)}.${process.pid}.${crypto.randomUUID()}.tmp`);
|
|
38951
38849
|
const handle = await open8(temporary, "wx", mode);
|
|
38952
38850
|
try {
|
|
38953
38851
|
await handle.writeFile(contents, "utf8");
|
|
@@ -38958,7 +38856,7 @@ async function replacePrivateFile2(path, contents, mode, sync) {
|
|
|
38958
38856
|
await sync(parent);
|
|
38959
38857
|
} catch (error52) {
|
|
38960
38858
|
await handle.close().catch(() => void 0);
|
|
38961
|
-
await
|
|
38859
|
+
await rm9(temporary, { force: true }).catch(() => void 0);
|
|
38962
38860
|
throw error52;
|
|
38963
38861
|
}
|
|
38964
38862
|
}
|
|
@@ -39044,14 +38942,14 @@ async function installMacosService(options) {
|
|
|
39044
38942
|
options.path ?? env.PATH ?? "/usr/local/bin:/opt/homebrew/bin:/usr/bin:/bin",
|
|
39045
38943
|
"command search path"
|
|
39046
38944
|
);
|
|
39047
|
-
const configRoot = options.configRoot ??
|
|
39048
|
-
const launchAgentsRoot = options.launchAgentsRoot ??
|
|
39049
|
-
const logRoot = options.logRoot ??
|
|
39050
|
-
const configPath =
|
|
39051
|
-
const launcherPath =
|
|
39052
|
-
const plistPath =
|
|
39053
|
-
const stdoutPath =
|
|
39054
|
-
const stderrPath =
|
|
38945
|
+
const configRoot = options.configRoot ?? join18(home, "Library", "Application Support", "Zixt");
|
|
38946
|
+
const launchAgentsRoot = options.launchAgentsRoot ?? join18(home, "Library", "LaunchAgents");
|
|
38947
|
+
const logRoot = options.logRoot ?? join18(home, "Library", "Logs", "Zixt");
|
|
38948
|
+
const configPath = join18(configRoot, "host.env");
|
|
38949
|
+
const launcherPath = join18(configRoot, "host-launcher.sh");
|
|
38950
|
+
const plistPath = join18(launchAgentsRoot, `${LAUNCH_AGENT_LABEL}.plist`);
|
|
38951
|
+
const stdoutPath = join18(logRoot, "host.log");
|
|
38952
|
+
const stderrPath = join18(logRoot, "host-error.log");
|
|
39055
38953
|
const installVersion = options.installVersion ?? installRelease;
|
|
39056
38954
|
const activateVersion = options.activateVersion ?? (options.installVersion ? async (entry) => entry : (entry) => activateInstalledRelease(entry));
|
|
39057
38955
|
const resolveCommand = options.resolveCommand ?? (async () => defaultResolveCommand2());
|
|
@@ -39138,9 +39036,9 @@ async function installMacosService(options) {
|
|
|
39138
39036
|
// src/windows-service.ts
|
|
39139
39037
|
import { spawn as spawn12 } from "node:child_process";
|
|
39140
39038
|
import { constants as constants4 } from "node:fs";
|
|
39141
|
-
import { access as access6, mkdir as
|
|
39039
|
+
import { access as access6, mkdir as mkdir14, open as open9, readFile as readFile10, rename as rename8, rm as rm10 } from "node:fs/promises";
|
|
39142
39040
|
import { homedir as homedir10 } from "node:os";
|
|
39143
|
-
import { basename as
|
|
39041
|
+
import { basename as basename6, dirname as dirname11, isAbsolute as isAbsolute16, join as join19, relative as relative11, resolve as resolve14, sep as sep7 } from "node:path";
|
|
39144
39042
|
var TASK_NAME = "Zixt Host";
|
|
39145
39043
|
var COMMAND_TIMEOUT_MS3 = 7e4;
|
|
39146
39044
|
var SERVICE_STABILITY_DELAY_MS3 = 2e3;
|
|
@@ -39166,21 +39064,21 @@ async function syncDirectory5(path) {
|
|
|
39166
39064
|
}
|
|
39167
39065
|
}
|
|
39168
39066
|
async function ensureDirectory3(path, sync) {
|
|
39169
|
-
const firstCreated = await
|
|
39067
|
+
const firstCreated = await mkdir14(path, { recursive: true, mode: 448 });
|
|
39170
39068
|
if (!firstCreated) return;
|
|
39171
39069
|
const first = resolve14(firstCreated);
|
|
39172
39070
|
const target = resolve14(path);
|
|
39173
|
-
await sync(
|
|
39071
|
+
await sync(dirname11(first));
|
|
39174
39072
|
let current = first;
|
|
39175
39073
|
for (const part of relative11(first, target).split(sep7).filter(Boolean)) {
|
|
39176
39074
|
await sync(current);
|
|
39177
|
-
current =
|
|
39075
|
+
current = join19(current, part);
|
|
39178
39076
|
}
|
|
39179
39077
|
}
|
|
39180
39078
|
async function replacePrivateFile3(path, contents, sync) {
|
|
39181
|
-
const parent =
|
|
39079
|
+
const parent = dirname11(path);
|
|
39182
39080
|
await ensureDirectory3(parent, sync);
|
|
39183
|
-
const temporary =
|
|
39081
|
+
const temporary = join19(parent, `.${basename6(path)}.${process.pid}.${crypto.randomUUID()}.tmp`);
|
|
39184
39082
|
const handle = await open9(temporary, "wx", 384);
|
|
39185
39083
|
try {
|
|
39186
39084
|
await handle.writeFile(contents, "utf8");
|
|
@@ -39190,7 +39088,7 @@ async function replacePrivateFile3(path, contents, sync) {
|
|
|
39190
39088
|
await sync(parent);
|
|
39191
39089
|
} catch (error52) {
|
|
39192
39090
|
await handle.close().catch(() => void 0);
|
|
39193
|
-
await
|
|
39091
|
+
await rm10(temporary, { force: true }).catch(() => void 0);
|
|
39194
39092
|
throw error52;
|
|
39195
39093
|
}
|
|
39196
39094
|
}
|
|
@@ -39235,7 +39133,7 @@ async function runChild(command, args, env, input) {
|
|
|
39235
39133
|
async function defaultResolveCommand3(name, env) {
|
|
39236
39134
|
const root = env.SYSTEMROOT ?? env.WINDIR;
|
|
39237
39135
|
if (!root || !isAbsolute16(root)) return null;
|
|
39238
|
-
const candidate = name === "powershell" ?
|
|
39136
|
+
const candidate = name === "powershell" ? join19(root, "System32", "WindowsPowerShell", "v1.0", "powershell.exe") : join19(root, "System32", `${name}.exe`);
|
|
39239
39137
|
return access6(candidate, constants4.X_OK).then(
|
|
39240
39138
|
() => candidate,
|
|
39241
39139
|
() => null
|
|
@@ -39372,11 +39270,11 @@ async function installWindowsService(options) {
|
|
|
39372
39270
|
const token2 = oneLine3(options.token, "pairing code");
|
|
39373
39271
|
const cloudUrl = options.cloudUrl ? oneLine3(options.cloudUrl, "Zixt Cloud address") : void 0;
|
|
39374
39272
|
const path = oneLine3(options.path ?? env.PATH ?? "", "command search path");
|
|
39375
|
-
const configRoot = options.configRoot ??
|
|
39376
|
-
const configPath =
|
|
39377
|
-
const launcherPath =
|
|
39378
|
-
const taskXmlPath =
|
|
39379
|
-
const statusPath =
|
|
39273
|
+
const configRoot = options.configRoot ?? join19(localAppData, "Zixt", "Host");
|
|
39274
|
+
const configPath = join19(configRoot, "host.json");
|
|
39275
|
+
const launcherPath = join19(configRoot, "host-launcher.ps1");
|
|
39276
|
+
const taskXmlPath = join19(configRoot, "host-task.xml");
|
|
39277
|
+
const statusPath = join19(configRoot, "host-status.json");
|
|
39380
39278
|
const installVersion = options.installVersion ?? installRelease;
|
|
39381
39279
|
const activateVersion = options.activateVersion ?? (options.installVersion ? async (entry) => entry : (entry) => activateInstalledRelease(entry));
|
|
39382
39280
|
const resolveCommand = options.resolveCommand ?? ((name) => defaultResolveCommand3(name, env));
|
|
@@ -39425,7 +39323,7 @@ async function installWindowsService(options) {
|
|
|
39425
39323
|
);
|
|
39426
39324
|
await replacePrivateFile3(launcherPath, launcherSource2(configPath, statusPath), sync);
|
|
39427
39325
|
await replacePrivateFile3(taskXmlPath, taskXml({ sid, powershell, launcherPath, home }), sync);
|
|
39428
|
-
await
|
|
39326
|
+
await rm10(statusPath, { force: true });
|
|
39429
39327
|
const acl = await run3(icacls, [
|
|
39430
39328
|
configRoot,
|
|
39431
39329
|
"/inheritance:r",
|
|
@@ -39477,23 +39375,23 @@ async function installSystemService(options) {
|
|
|
39477
39375
|
}
|
|
39478
39376
|
|
|
39479
39377
|
// src/terminal-outcomes.ts
|
|
39480
|
-
import { chmod as chmod9, lstat as lstat12, mkdir as
|
|
39378
|
+
import { chmod as chmod9, lstat as lstat12, mkdir as mkdir15, open as open10, readdir as readdir5, readFile as readFile11, rename as rename9, rm as rm11 } from "node:fs/promises";
|
|
39481
39379
|
import { homedir as homedir11 } from "node:os";
|
|
39482
|
-
import { dirname as
|
|
39380
|
+
import { dirname as dirname12, join as join20, relative as relative12, resolve as resolve15, sep as sep8 } from "node:path";
|
|
39483
39381
|
var DIRECTORY_MODE5 = 448;
|
|
39484
39382
|
var FILE_MODE4 = 384;
|
|
39485
39383
|
var MAX_OUTCOME_BYTES = 4 * 1024 * 1024;
|
|
39486
39384
|
var HOST_DIRECTORY = /^hst_[0-9a-f]{32}$/;
|
|
39487
39385
|
var OUTCOME_FILE = /^(tsk_[0-9a-f]{32})\.([1-9][0-9]*)\.json$/;
|
|
39488
39386
|
function defaultTerminalOutcomeRoot() {
|
|
39489
|
-
return
|
|
39387
|
+
return join20(homedir11(), ".zixt", "terminal-outcomes");
|
|
39490
39388
|
}
|
|
39491
39389
|
function hostOutcomeRoot(root, hostId) {
|
|
39492
39390
|
if (!HOST_DIRECTORY.test(hostId)) throw new Error("terminal outcome Host identity is malformed");
|
|
39493
|
-
return
|
|
39391
|
+
return join20(root, hostId);
|
|
39494
39392
|
}
|
|
39495
39393
|
function outcomePath(root, hostId, taskId, epoch) {
|
|
39496
|
-
return
|
|
39394
|
+
return join20(hostOutcomeRoot(root, hostId), `${taskId}.${epoch}.json`);
|
|
39497
39395
|
}
|
|
39498
39396
|
async function syncDirectory6(root) {
|
|
39499
39397
|
if (process.platform === "win32") return;
|
|
@@ -39505,15 +39403,15 @@ async function syncDirectory6(root) {
|
|
|
39505
39403
|
}
|
|
39506
39404
|
}
|
|
39507
39405
|
async function requirePrivateRoot(root, sync = syncDirectory6) {
|
|
39508
|
-
const firstCreated = await
|
|
39406
|
+
const firstCreated = await mkdir15(root, { recursive: true, mode: DIRECTORY_MODE5 });
|
|
39509
39407
|
if (firstCreated) {
|
|
39510
39408
|
const first = resolve15(firstCreated);
|
|
39511
39409
|
const target = resolve15(root);
|
|
39512
|
-
await sync(
|
|
39410
|
+
await sync(dirname12(first));
|
|
39513
39411
|
let current = first;
|
|
39514
39412
|
for (const part of relative12(first, target).split(sep8).filter(Boolean)) {
|
|
39515
39413
|
await sync(current);
|
|
39516
|
-
current =
|
|
39414
|
+
current = join20(current, part);
|
|
39517
39415
|
}
|
|
39518
39416
|
}
|
|
39519
39417
|
const stat3 = await lstat12(root);
|
|
@@ -39553,7 +39451,7 @@ async function recordTerminalOutcome(hostId, input, root = defaultTerminalOutcom
|
|
|
39553
39451
|
} catch (error52) {
|
|
39554
39452
|
if (error52.code !== "ENOENT") throw error52;
|
|
39555
39453
|
}
|
|
39556
|
-
const temporary =
|
|
39454
|
+
const temporary = join20(
|
|
39557
39455
|
scopedRoot,
|
|
39558
39456
|
`.${outcome.taskId}.${outcome.epoch}.${process.pid}.${Date.now()}.${outcome.resultId}.tmp`
|
|
39559
39457
|
);
|
|
@@ -39570,7 +39468,7 @@ async function recordTerminalOutcome(hostId, input, root = defaultTerminalOutcom
|
|
|
39570
39468
|
} finally {
|
|
39571
39469
|
await handle?.close().catch(() => {
|
|
39572
39470
|
});
|
|
39573
|
-
await
|
|
39471
|
+
await rm11(temporary, { force: true }).catch(() => {
|
|
39574
39472
|
});
|
|
39575
39473
|
}
|
|
39576
39474
|
}
|
|
@@ -39606,7 +39504,7 @@ async function readTerminalOutcomesStrict(root = defaultTerminalOutcomeRoot()) {
|
|
|
39606
39504
|
if (!match || !entry.isFile() || entry.isSymbolicLink()) {
|
|
39607
39505
|
throw new Error("committed terminal outcome is not a trusted regular file");
|
|
39608
39506
|
}
|
|
39609
|
-
const path =
|
|
39507
|
+
const path = join20(scopedRoot, entry.name);
|
|
39610
39508
|
const stat3 = await lstat12(path);
|
|
39611
39509
|
if (!stat3.isFile() || stat3.isSymbolicLink() || stat3.size > MAX_OUTCOME_BYTES) {
|
|
39612
39510
|
throw new Error("committed terminal outcome is not a trusted regular file");
|
|
@@ -39639,7 +39537,7 @@ async function forgetAcknowledgedTerminalOutcomes(refs, root = defaultTerminalOu
|
|
|
39639
39537
|
if (acknowledged.get(`${hostId}:${outcome.taskId}:${outcome.epoch}`) !== outcome.resultId) {
|
|
39640
39538
|
continue;
|
|
39641
39539
|
}
|
|
39642
|
-
await
|
|
39540
|
+
await rm11(outcomePath(root, hostId, outcome.taskId, outcome.epoch), { force: true });
|
|
39643
39541
|
changedHostRoots.add(hostOutcomeRoot(root, hostId));
|
|
39644
39542
|
}
|
|
39645
39543
|
for (const scopedRoot of changedHostRoots) await syncDirectory6(scopedRoot);
|
|
@@ -39651,7 +39549,7 @@ async function forgetSupersededTerminalOutcomes(hostId, taskId, epoch, root = de
|
|
|
39651
39549
|
if (scoped.hostId !== hostId) continue;
|
|
39652
39550
|
const { outcome } = scoped;
|
|
39653
39551
|
if (outcome.taskId !== taskId || outcome.epoch >= epoch) continue;
|
|
39654
|
-
await
|
|
39552
|
+
await rm11(outcomePath(root, hostId, outcome.taskId, outcome.epoch), { force: true });
|
|
39655
39553
|
removed = true;
|
|
39656
39554
|
}
|
|
39657
39555
|
if (removed) await syncDirectory6(hostOutcomeRoot(root, hostId));
|
|
@@ -39759,7 +39657,7 @@ function createHostLogger(options = {}) {
|
|
|
39759
39657
|
}
|
|
39760
39658
|
|
|
39761
39659
|
// src/demo-state.ts
|
|
39762
|
-
import { isAbsolute as isAbsolute17, join as
|
|
39660
|
+
import { isAbsolute as isAbsolute17, join as join21, parse as parse3, resolve as resolve16 } from "node:path";
|
|
39763
39661
|
var DEMO_STATE_ROOT_ENV = "ZIXT_DEMO_STATE_ROOT";
|
|
39764
39662
|
function resolveDemoHostStatePaths(env = process.env) {
|
|
39765
39663
|
const configured = env.ZIXT_RUNNER === "demo" ? env[DEMO_STATE_ROOT_ENV] : void 0;
|
|
@@ -39769,12 +39667,12 @@ function resolveDemoHostStatePaths(env = process.env) {
|
|
|
39769
39667
|
throw new Error(`${DEMO_STATE_ROOT_ENV} must be a dedicated absolute directory`);
|
|
39770
39668
|
}
|
|
39771
39669
|
return {
|
|
39772
|
-
runRegistryRoot:
|
|
39773
|
-
terminalOutcomeRoot:
|
|
39774
|
-
runArtifactRoot:
|
|
39775
|
-
browserProfileRoot:
|
|
39776
|
-
runnerWorkspaceRoot:
|
|
39777
|
-
codexThreadIndexRoot:
|
|
39670
|
+
runRegistryRoot: join21(root, "run-registry"),
|
|
39671
|
+
terminalOutcomeRoot: join21(root, "terminal-outcomes"),
|
|
39672
|
+
runArtifactRoot: join21(root, "run-artifacts"),
|
|
39673
|
+
browserProfileRoot: join21(root, "browser-profiles"),
|
|
39674
|
+
runnerWorkspaceRoot: join21(root, "workspaces"),
|
|
39675
|
+
codexThreadIndexRoot: join21(root, "codex-threads")
|
|
39778
39676
|
};
|
|
39779
39677
|
}
|
|
39780
39678
|
|