@ai-development-environment/control-agent 0.0.53 → 0.0.55
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/README.md +1 -1
- package/dist/control-agent.js +948 -463
- package/package.json +5 -4
package/dist/control-agent.js
CHANGED
|
@@ -1,4 +1,6 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
+
import { createRequire } from "node:module";
|
|
3
|
+
const require = createRequire(import.meta.url);
|
|
2
4
|
var __create = Object.create;
|
|
3
5
|
var __defProp = Object.defineProperty;
|
|
4
6
|
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
@@ -3728,15 +3730,15 @@ var require_windows = __commonJS({
|
|
|
3728
3730
|
}
|
|
3729
3731
|
return false;
|
|
3730
3732
|
}
|
|
3731
|
-
function checkStat(
|
|
3732
|
-
if (!
|
|
3733
|
+
function checkStat(stat10, path, options) {
|
|
3734
|
+
if (!stat10.isSymbolicLink() && !stat10.isFile()) {
|
|
3733
3735
|
return false;
|
|
3734
3736
|
}
|
|
3735
3737
|
return checkPathExt(path, options);
|
|
3736
3738
|
}
|
|
3737
3739
|
function isexe(path, options, cb2) {
|
|
3738
|
-
fs.stat(path, function(er2,
|
|
3739
|
-
cb2(er2, er2 ? false : checkStat(
|
|
3740
|
+
fs.stat(path, function(er2, stat10) {
|
|
3741
|
+
cb2(er2, er2 ? false : checkStat(stat10, path, options));
|
|
3740
3742
|
});
|
|
3741
3743
|
}
|
|
3742
3744
|
function sync(path, options) {
|
|
@@ -3752,20 +3754,20 @@ var require_mode = __commonJS({
|
|
|
3752
3754
|
isexe.sync = sync;
|
|
3753
3755
|
var fs = __require("fs");
|
|
3754
3756
|
function isexe(path, options, cb2) {
|
|
3755
|
-
fs.stat(path, function(er2,
|
|
3756
|
-
cb2(er2, er2 ? false : checkStat(
|
|
3757
|
+
fs.stat(path, function(er2, stat10) {
|
|
3758
|
+
cb2(er2, er2 ? false : checkStat(stat10, options));
|
|
3757
3759
|
});
|
|
3758
3760
|
}
|
|
3759
3761
|
function sync(path, options) {
|
|
3760
3762
|
return checkStat(fs.statSync(path), options);
|
|
3761
3763
|
}
|
|
3762
|
-
function checkStat(
|
|
3763
|
-
return
|
|
3764
|
+
function checkStat(stat10, options) {
|
|
3765
|
+
return stat10.isFile() && checkMode(stat10, options);
|
|
3764
3766
|
}
|
|
3765
|
-
function checkMode(
|
|
3766
|
-
var mod =
|
|
3767
|
-
var uid =
|
|
3768
|
-
var gid =
|
|
3767
|
+
function checkMode(stat10, options) {
|
|
3768
|
+
var mod = stat10.mode;
|
|
3769
|
+
var uid = stat10.uid;
|
|
3770
|
+
var gid = stat10.gid;
|
|
3769
3771
|
var myUid = options.uid !== void 0 ? options.uid : process.getuid && process.getuid();
|
|
3770
3772
|
var myGid = options.gid !== void 0 ? options.gid : process.getgid && process.getgid();
|
|
3771
3773
|
var u = parseInt("100", 8);
|
|
@@ -4182,7 +4184,7 @@ var require_cross_spawn = __commonJS({
|
|
|
4182
4184
|
var cp3 = __require("child_process");
|
|
4183
4185
|
var parse2 = require_parse();
|
|
4184
4186
|
var enoent = require_enoent();
|
|
4185
|
-
function
|
|
4187
|
+
function spawn8(command3, args, options) {
|
|
4186
4188
|
const parsed = parse2(command3, args, options);
|
|
4187
4189
|
const spawned = cp3.spawn(parsed.command, parsed.args, parsed.options);
|
|
4188
4190
|
enoent.hookChildProcess(spawned, parsed);
|
|
@@ -4194,18 +4196,14 @@ var require_cross_spawn = __commonJS({
|
|
|
4194
4196
|
result.error = result.error || enoent.verifyENOENTSync(result.status, parsed);
|
|
4195
4197
|
return result;
|
|
4196
4198
|
}
|
|
4197
|
-
module.exports =
|
|
4198
|
-
module.exports.spawn =
|
|
4199
|
+
module.exports = spawn8;
|
|
4200
|
+
module.exports.spawn = spawn8;
|
|
4199
4201
|
module.exports.sync = spawnSync2;
|
|
4200
4202
|
module.exports._parse = parse2;
|
|
4201
4203
|
module.exports._enoent = enoent;
|
|
4202
4204
|
}
|
|
4203
4205
|
});
|
|
4204
4206
|
|
|
4205
|
-
// src/index.ts
|
|
4206
|
-
import { execFile as execFile5 } from "node:child_process";
|
|
4207
|
-
import { promisify as promisify5 } from "node:util";
|
|
4208
|
-
|
|
4209
4207
|
// src/config.ts
|
|
4210
4208
|
import { chmod, mkdir, readFile, rename, writeFile } from "node:fs/promises";
|
|
4211
4209
|
import { homedir } from "node:os";
|
|
@@ -4252,8 +4250,6 @@ async function saveConfig(config, path = configPath()) {
|
|
|
4252
4250
|
}
|
|
4253
4251
|
|
|
4254
4252
|
// ../agent-contract/src/index.ts
|
|
4255
|
-
var TUNNEL_NAME_PATTERN = "[A-Za-z0-9][A-Za-z0-9_-]{0,127}";
|
|
4256
|
-
var TUNNEL_NAME_REGEX = new RegExp(`^${TUNNEL_NAME_PATTERN}$`);
|
|
4257
4253
|
var CCUSAGE_REPORT_JOB_KIND = "ccusage.report";
|
|
4258
4254
|
var DEFAULT_AGENT_HEARTBEAT_INTERVAL_SECONDS = 15;
|
|
4259
4255
|
var MIN_AGENT_HEARTBEAT_INTERVAL_SECONDS = 5;
|
|
@@ -5170,6 +5166,24 @@ var AgentGraphQLClient = class {
|
|
|
5170
5166
|
}
|
|
5171
5167
|
);
|
|
5172
5168
|
}
|
|
5169
|
+
async diskSpaceConfiguration() {
|
|
5170
|
+
const data = await this.request(`query AgentDiskSpaceConfiguration {
|
|
5171
|
+
agentDiskSpaceConfiguration {
|
|
5172
|
+
enabled pollIntervalSeconds baseRepoDirectory
|
|
5173
|
+
derivedDataLocationMode derivedDataPath
|
|
5174
|
+
worktrees { id folder }
|
|
5175
|
+
}
|
|
5176
|
+
}`);
|
|
5177
|
+
return data.agentDiskSpaceConfiguration;
|
|
5178
|
+
}
|
|
5179
|
+
reportDiskSpace(input) {
|
|
5180
|
+
return this.request(
|
|
5181
|
+
`mutation ReportAgentDiskSpace($input: AgentDiskSpaceReportInput!) {
|
|
5182
|
+
reportAgentDiskSpace(input: $input)
|
|
5183
|
+
}`,
|
|
5184
|
+
{ input }
|
|
5185
|
+
);
|
|
5186
|
+
}
|
|
5173
5187
|
async pendingJobs(agentId) {
|
|
5174
5188
|
const data = await this.request(
|
|
5175
5189
|
`query PendingJobs($agentId: ID!) {
|
|
@@ -5180,7 +5194,7 @@ var AgentGraphQLClient = class {
|
|
|
5180
5194
|
{ agentId }
|
|
5181
5195
|
);
|
|
5182
5196
|
return data.agentJobs.filter(
|
|
5183
|
-
(job) => job.status === "QUEUED" || job.status === "RUNNING" || job.status === "CANCELLED"
|
|
5197
|
+
(job) => job.status === "QUEUED" || job.status === "RUNNING" || job.status === "CANCELLING" || job.status === "CANCELLED"
|
|
5184
5198
|
);
|
|
5185
5199
|
}
|
|
5186
5200
|
async cadenceSettings(agentId) {
|
|
@@ -5236,6 +5250,14 @@ var AgentGraphQLClient = class {
|
|
|
5236
5250
|
{ jobId, logs: [log] }
|
|
5237
5251
|
);
|
|
5238
5252
|
}
|
|
5253
|
+
appendCommandOutput(jobId, attemptId, chunks) {
|
|
5254
|
+
return this.request(
|
|
5255
|
+
`mutation AppendCommandRunOutput($jobId: ID!, $attemptId: ID!, $chunks: [CommandRunOutputInput!]!) {
|
|
5256
|
+
appendCommandRunOutput(jobId: $jobId, attemptId: $attemptId, chunks: $chunks) { id }
|
|
5257
|
+
}`,
|
|
5258
|
+
{ jobId, attemptId, chunks }
|
|
5259
|
+
);
|
|
5260
|
+
}
|
|
5239
5261
|
reportBuildProgress(input) {
|
|
5240
5262
|
return this.request(
|
|
5241
5263
|
`mutation ReportBuildProgress($input: BuildProgressInput!) {
|
|
@@ -5244,12 +5266,12 @@ var AgentGraphQLClient = class {
|
|
|
5244
5266
|
{ input }
|
|
5245
5267
|
);
|
|
5246
5268
|
}
|
|
5247
|
-
|
|
5269
|
+
appendBuildLogChunks(buildId, chunks) {
|
|
5248
5270
|
return this.request(
|
|
5249
|
-
`mutation
|
|
5250
|
-
|
|
5271
|
+
`mutation AppendBuildLogChunks($buildId: ID!, $chunks: [BuildLogChunkInput!]!) {
|
|
5272
|
+
appendBuildLogChunks(buildId: $buildId, chunks: $chunks) { id }
|
|
5251
5273
|
}`,
|
|
5252
|
-
{ buildId,
|
|
5274
|
+
{ buildId, chunks }
|
|
5253
5275
|
);
|
|
5254
5276
|
}
|
|
5255
5277
|
async uploadBuildArtifact(input) {
|
|
@@ -5590,6 +5612,10 @@ function nullableString(value, name) {
|
|
|
5590
5612
|
if (value === null) return null;
|
|
5591
5613
|
return stringValue2(value, name);
|
|
5592
5614
|
}
|
|
5615
|
+
function optionalNullableString(value, name) {
|
|
5616
|
+
if (value === void 0 || value === null) return null;
|
|
5617
|
+
return stringValue2(value, name);
|
|
5618
|
+
}
|
|
5593
5619
|
function exactKeys(value, allowed, name) {
|
|
5594
5620
|
const unexpected = Object.keys(value).find((key) => !allowed.includes(key));
|
|
5595
5621
|
if (unexpected) throw new Error(`Unexpected ${name} field: ${unexpected}`);
|
|
@@ -5619,6 +5645,44 @@ function target(value, index) {
|
|
|
5619
5645
|
)
|
|
5620
5646
|
};
|
|
5621
5647
|
}
|
|
5648
|
+
function deleteTarget(value, index) {
|
|
5649
|
+
const item = objectValue2(value, `build data delete targets[${index}]`);
|
|
5650
|
+
exactKeys(
|
|
5651
|
+
item,
|
|
5652
|
+
["path", "rootPath", "name", "kind", "worktreeId", "worktreePath"],
|
|
5653
|
+
"build data delete target"
|
|
5654
|
+
);
|
|
5655
|
+
const kind = item.kind;
|
|
5656
|
+
if (kind !== void 0 && !["PROJECT", "PENDING", "SHARED_CACHE", "DEVICE_SUPPORT"].includes(kind)) {
|
|
5657
|
+
throw new Error(`build data delete targets[${index}].kind is invalid`);
|
|
5658
|
+
}
|
|
5659
|
+
return {
|
|
5660
|
+
path: stringValue2(item.path, `build data delete targets[${index}].path`),
|
|
5661
|
+
rootPath: stringValue2(
|
|
5662
|
+
item.rootPath,
|
|
5663
|
+
`build data delete targets[${index}].rootPath`
|
|
5664
|
+
),
|
|
5665
|
+
...item.name === void 0 ? {} : {
|
|
5666
|
+
name: stringValue2(
|
|
5667
|
+
item.name,
|
|
5668
|
+
`build data delete targets[${index}].name`
|
|
5669
|
+
)
|
|
5670
|
+
},
|
|
5671
|
+
...kind === void 0 ? {} : { kind },
|
|
5672
|
+
...item.worktreeId === void 0 ? {} : {
|
|
5673
|
+
worktreeId: optionalNullableString(
|
|
5674
|
+
item.worktreeId,
|
|
5675
|
+
`build data delete targets[${index}].worktreeId`
|
|
5676
|
+
)
|
|
5677
|
+
},
|
|
5678
|
+
...item.worktreePath === void 0 ? {} : {
|
|
5679
|
+
worktreePath: optionalNullableString(
|
|
5680
|
+
item.worktreePath,
|
|
5681
|
+
`build data delete targets[${index}].worktreePath`
|
|
5682
|
+
)
|
|
5683
|
+
}
|
|
5684
|
+
};
|
|
5685
|
+
}
|
|
5622
5686
|
function buildDataScanPayload(value) {
|
|
5623
5687
|
const payload = objectValue2(value, "build data scan payload");
|
|
5624
5688
|
exactKeys(payload, ["mode", "path", "worktrees"], "build data scan payload");
|
|
@@ -5649,6 +5713,23 @@ function buildDataTargetsPayload(value) {
|
|
|
5649
5713
|
}
|
|
5650
5714
|
return { targets: payload.targets.map(target) };
|
|
5651
5715
|
}
|
|
5716
|
+
function buildDataDeletePayload(value) {
|
|
5717
|
+
const payload = objectValue2(value, "build data delete payload");
|
|
5718
|
+
exactKeys(payload, ["targets", "source"], "build data delete payload");
|
|
5719
|
+
if (!Array.isArray(payload.targets) || payload.targets.length > 1e4) {
|
|
5720
|
+
throw new Error(
|
|
5721
|
+
"build data delete targets must be an array of at most 10,000 items"
|
|
5722
|
+
);
|
|
5723
|
+
}
|
|
5724
|
+
const source = payload.source ?? "USER";
|
|
5725
|
+
if (source !== "USER" && source !== "AUTOMATIC") {
|
|
5726
|
+
throw new Error("build data delete source is invalid");
|
|
5727
|
+
}
|
|
5728
|
+
return {
|
|
5729
|
+
targets: payload.targets.map(deleteTarget),
|
|
5730
|
+
source
|
|
5731
|
+
};
|
|
5732
|
+
}
|
|
5652
5733
|
|
|
5653
5734
|
// ../agent-contract/src/codebases.ts
|
|
5654
5735
|
var CODEBASE_BROWSE_JOB_KIND = "codebase.browse";
|
|
@@ -7782,10 +7863,58 @@ function parseWorkflowGitCheckpointPayload(value) {
|
|
|
7782
7863
|
};
|
|
7783
7864
|
}
|
|
7784
7865
|
|
|
7866
|
+
// ../agent-contract/src/commands.ts
|
|
7867
|
+
var COMMAND_RUN_JOB_KIND = "command.run";
|
|
7868
|
+
function objectValue10(value, name) {
|
|
7869
|
+
if (!value || typeof value !== "object" || Array.isArray(value)) {
|
|
7870
|
+
throw new Error(`${name} must be an object`);
|
|
7871
|
+
}
|
|
7872
|
+
return value;
|
|
7873
|
+
}
|
|
7874
|
+
function stringValue10(value, name, maximum) {
|
|
7875
|
+
if (typeof value !== "string" || !value.length || value.length > maximum) {
|
|
7876
|
+
throw new Error(
|
|
7877
|
+
`${name} must be a non-empty string of at most ${maximum} characters`
|
|
7878
|
+
);
|
|
7879
|
+
}
|
|
7880
|
+
return value;
|
|
7881
|
+
}
|
|
7882
|
+
function parseCommandRunPayload(value) {
|
|
7883
|
+
const payload = objectValue10(value, "command run payload");
|
|
7884
|
+
const targetKind = stringValue10(payload.targetKind, "targetKind", 20);
|
|
7885
|
+
if (targetKind !== "AGENT_HOME" && targetKind !== "WORKTREE") {
|
|
7886
|
+
throw new Error("targetKind must be AGENT_HOME or WORKTREE");
|
|
7887
|
+
}
|
|
7888
|
+
const cwd = payload.cwd === null || payload.cwd === void 0 ? null : stringValue10(payload.cwd, "cwd", 1e4);
|
|
7889
|
+
if (targetKind === "WORKTREE" && !cwd) {
|
|
7890
|
+
throw new Error("Worktree commands require cwd");
|
|
7891
|
+
}
|
|
7892
|
+
if (targetKind === "AGENT_HOME" && cwd !== null) {
|
|
7893
|
+
throw new Error("Agent-home commands cannot provide cwd");
|
|
7894
|
+
}
|
|
7895
|
+
const allowed = /* @__PURE__ */ new Set([
|
|
7896
|
+
"commandRunId",
|
|
7897
|
+
"attemptId",
|
|
7898
|
+
"targetKind",
|
|
7899
|
+
"cwd",
|
|
7900
|
+
"script"
|
|
7901
|
+
]);
|
|
7902
|
+
const unexpected = Object.keys(payload).find((key) => !allowed.has(key));
|
|
7903
|
+
if (unexpected)
|
|
7904
|
+
throw new Error(`Unsupported command payload field: ${unexpected}`);
|
|
7905
|
+
return {
|
|
7906
|
+
commandRunId: stringValue10(payload.commandRunId, "commandRunId", 200),
|
|
7907
|
+
attemptId: stringValue10(payload.attemptId, "attemptId", 200),
|
|
7908
|
+
targetKind,
|
|
7909
|
+
cwd,
|
|
7910
|
+
script: stringValue10(payload.script, "script", 1e6)
|
|
7911
|
+
};
|
|
7912
|
+
}
|
|
7913
|
+
|
|
7785
7914
|
// src/inventory.ts
|
|
7786
7915
|
var AGENT_VERSION = "0.1.0";
|
|
7787
7916
|
var AGENT_CAPABILITIES = [
|
|
7788
|
-
|
|
7917
|
+
COMMAND_RUN_JOB_KIND,
|
|
7789
7918
|
CCUSAGE_REPORT_JOB_KIND,
|
|
7790
7919
|
...BUILD_DATA_JOB_KINDS,
|
|
7791
7920
|
...CODEBASE_JOB_KINDS,
|
|
@@ -7817,148 +7946,186 @@ function collectInventory() {
|
|
|
7817
7946
|
};
|
|
7818
7947
|
}
|
|
7819
7948
|
|
|
7820
|
-
// src/
|
|
7949
|
+
// src/handlers/commands.ts
|
|
7821
7950
|
import { spawn } from "node:child_process";
|
|
7822
|
-
|
|
7823
|
-
|
|
7824
|
-
|
|
7825
|
-
|
|
7826
|
-
|
|
7827
|
-
|
|
7828
|
-
|
|
7829
|
-
|
|
7830
|
-
|
|
7831
|
-
|
|
7832
|
-
|
|
7833
|
-
|
|
7834
|
-
|
|
7835
|
-
|
|
7836
|
-
|
|
7837
|
-
|
|
7838
|
-
|
|
7839
|
-
|
|
7840
|
-
|
|
7841
|
-
|
|
7842
|
-
|
|
7843
|
-
|
|
7844
|
-
|
|
7845
|
-
|
|
7846
|
-
|
|
7951
|
+
import { chmod as chmod2, mkdtemp, realpath, rm as rm2, writeFile as writeFile2 } from "node:fs/promises";
|
|
7952
|
+
import { homedir as homedir2, tmpdir } from "node:os";
|
|
7953
|
+
import { join as join2 } from "node:path";
|
|
7954
|
+
var MAX_BATCH_BYTES = 128 * 1024;
|
|
7955
|
+
var FLUSH_DELAY_MS = 25;
|
|
7956
|
+
var runCommand = async (rawPayload, _timeoutMs, signal, _onLog, context) => {
|
|
7957
|
+
const payload = parseCommandRunPayload(rawPayload);
|
|
7958
|
+
if (!context?.appendCommandOutput) {
|
|
7959
|
+
throw new Error("Command output uploader is unavailable");
|
|
7960
|
+
}
|
|
7961
|
+
const directory = await mkdtemp(join2(tmpdir(), "aide-command-"));
|
|
7962
|
+
const scriptPath = join2(directory, "command.sh");
|
|
7963
|
+
await writeFile2(scriptPath, payload.script, {
|
|
7964
|
+
encoding: "utf8",
|
|
7965
|
+
mode: 384
|
|
7966
|
+
});
|
|
7967
|
+
await chmod2(scriptPath, 384);
|
|
7968
|
+
const cwd = payload.targetKind === "AGENT_HOME" ? homedir2() : await realpath(payload.cwd);
|
|
7969
|
+
let sequence = 0;
|
|
7970
|
+
let queuedBytes = 0;
|
|
7971
|
+
let pending = [];
|
|
7972
|
+
let timer;
|
|
7973
|
+
let uploadChain = Promise.resolve();
|
|
7974
|
+
const upload = (chunks) => {
|
|
7975
|
+
if (!chunks.length) return;
|
|
7976
|
+
const bytes = chunks.reduce((total, chunk) => total + chunk.byteLength, 0);
|
|
7977
|
+
uploadChain = uploadChain.then(async () => {
|
|
7978
|
+
let retry = 0;
|
|
7979
|
+
while (true) {
|
|
7847
7980
|
try {
|
|
7848
|
-
await
|
|
7981
|
+
await context.appendCommandOutput?.(payload.attemptId, chunks);
|
|
7982
|
+
queuedBytes -= bytes;
|
|
7983
|
+
return;
|
|
7849
7984
|
} catch (error) {
|
|
7985
|
+
if (signal.aborted) return;
|
|
7986
|
+
const delay = Math.min(3e4, 500 * 2 ** Math.min(retry++, 6));
|
|
7850
7987
|
console.error(
|
|
7851
|
-
`Could not append
|
|
7988
|
+
`Could not append command output; retrying in ${delay}ms:`,
|
|
7852
7989
|
error instanceof Error ? error.message : error
|
|
7853
7990
|
);
|
|
7991
|
+
await new Promise((resolve7) => {
|
|
7992
|
+
const onAbort = () => {
|
|
7993
|
+
clearTimeout(retryTimer);
|
|
7994
|
+
resolve7();
|
|
7995
|
+
};
|
|
7996
|
+
const retryTimer = setTimeout(() => {
|
|
7997
|
+
signal.removeEventListener("abort", onAbort);
|
|
7998
|
+
resolve7();
|
|
7999
|
+
}, delay);
|
|
8000
|
+
retryTimer.unref();
|
|
8001
|
+
signal.addEventListener("abort", onAbort, { once: true });
|
|
8002
|
+
if (signal.aborted) onAbort();
|
|
8003
|
+
});
|
|
8004
|
+
if (signal.aborted) return;
|
|
7854
8005
|
}
|
|
7855
|
-
}
|
|
8006
|
+
}
|
|
8007
|
+
});
|
|
8008
|
+
};
|
|
8009
|
+
const flush = () => {
|
|
8010
|
+
if (timer) clearTimeout(timer);
|
|
8011
|
+
timer = void 0;
|
|
8012
|
+
const batch = pending;
|
|
8013
|
+
pending = [];
|
|
8014
|
+
upload(batch);
|
|
8015
|
+
};
|
|
8016
|
+
const enqueue = (stream, bytes) => {
|
|
8017
|
+
const chunk = {
|
|
8018
|
+
sequence: sequence++,
|
|
8019
|
+
stream,
|
|
8020
|
+
dataBase64: bytes.toString("base64"),
|
|
8021
|
+
byteLength: bytes.length,
|
|
8022
|
+
createdAt: (/* @__PURE__ */ new Date()).toISOString()
|
|
7856
8023
|
};
|
|
7857
|
-
|
|
7858
|
-
|
|
7859
|
-
|
|
7860
|
-
|
|
7861
|
-
|
|
7862
|
-
|
|
7863
|
-
|
|
8024
|
+
pending.push(chunk);
|
|
8025
|
+
queuedBytes += bytes.length;
|
|
8026
|
+
if (pending.reduce((total, item) => total + item.byteLength, 0) >= MAX_BATCH_BYTES) {
|
|
8027
|
+
flush();
|
|
8028
|
+
} else if (!timer) {
|
|
8029
|
+
timer = setTimeout(flush, FLUSH_DELAY_MS);
|
|
8030
|
+
timer.unref();
|
|
8031
|
+
}
|
|
8032
|
+
};
|
|
8033
|
+
try {
|
|
8034
|
+
return await new Promise((resolve7, reject) => {
|
|
8035
|
+
let cancelled = false;
|
|
8036
|
+
let settled = false;
|
|
8037
|
+
const child = spawn(process.env.SHELL || "/bin/sh", ["-l", scriptPath], {
|
|
8038
|
+
cwd,
|
|
8039
|
+
detached: process.platform !== "win32",
|
|
8040
|
+
env: {
|
|
8041
|
+
...process.env,
|
|
8042
|
+
TERM: "xterm-256color",
|
|
8043
|
+
COLORTERM: "truecolor",
|
|
8044
|
+
FORCE_COLOR: "1",
|
|
8045
|
+
CLICOLOR_FORCE: "1"
|
|
8046
|
+
},
|
|
8047
|
+
shell: false,
|
|
8048
|
+
stdio: ["ignore", "pipe", "pipe"]
|
|
7864
8049
|
});
|
|
7865
|
-
|
|
7866
|
-
if (
|
|
8050
|
+
const pauseForPressure = () => {
|
|
8051
|
+
if (queuedBytes < 4 * 1024 * 1024) return;
|
|
8052
|
+
child.stdout.pause();
|
|
8053
|
+
child.stderr.pause();
|
|
8054
|
+
void uploadChain.finally(() => {
|
|
8055
|
+
child.stdout.resume();
|
|
8056
|
+
child.stderr.resume();
|
|
8057
|
+
});
|
|
8058
|
+
};
|
|
8059
|
+
child.stdout.on("data", (bytes) => {
|
|
8060
|
+
enqueue("STDOUT", bytes);
|
|
8061
|
+
pauseForPressure();
|
|
7867
8062
|
});
|
|
7868
|
-
|
|
7869
|
-
|
|
7870
|
-
|
|
7871
|
-
|
|
7872
|
-
|
|
8063
|
+
child.stderr.on("data", (bytes) => {
|
|
8064
|
+
enqueue("STDERR", bytes);
|
|
8065
|
+
pauseForPressure();
|
|
8066
|
+
});
|
|
8067
|
+
const sendSignal = (name) => {
|
|
8068
|
+
if (child.exitCode !== null) return;
|
|
7873
8069
|
try {
|
|
7874
|
-
process.
|
|
7875
|
-
|
|
8070
|
+
if (process.platform !== "win32" && child.pid)
|
|
8071
|
+
process.kill(-child.pid, name);
|
|
8072
|
+
else child.kill(name);
|
|
7876
8073
|
} catch (error) {
|
|
7877
8074
|
if (!(error instanceof Error) || !("code" in error) || error.code !== "ESRCH") {
|
|
7878
8075
|
throw error;
|
|
7879
8076
|
}
|
|
7880
8077
|
}
|
|
7881
|
-
}
|
|
7882
|
-
|
|
7883
|
-
|
|
7884
|
-
|
|
7885
|
-
|
|
7886
|
-
|
|
7887
|
-
|
|
7888
|
-
|
|
7889
|
-
|
|
7890
|
-
|
|
7891
|
-
|
|
7892
|
-
|
|
7893
|
-
|
|
7894
|
-
|
|
7895
|
-
|
|
7896
|
-
|
|
7897
|
-
|
|
7898
|
-
|
|
7899
|
-
|
|
7900
|
-
|
|
7901
|
-
|
|
7902
|
-
|
|
7903
|
-
|
|
7904
|
-
|
|
7905
|
-
|
|
7906
|
-
|
|
7907
|
-
|
|
7908
|
-
|
|
7909
|
-
|
|
7910
|
-
|
|
7911
|
-
|
|
7912
|
-
child.once("close", (exitCode, signal) => {
|
|
7913
|
-
if (settled) return;
|
|
7914
|
-
settled = true;
|
|
7915
|
-
clearTimeout(timeout);
|
|
7916
|
-
options.signal.removeEventListener("abort", abort);
|
|
7917
|
-
void logChain.then(
|
|
7918
|
-
() => resolve7({ exitCode, signal, timedOut, cancelled })
|
|
7919
|
-
);
|
|
8078
|
+
};
|
|
8079
|
+
const abort = () => {
|
|
8080
|
+
if (cancelled) return;
|
|
8081
|
+
cancelled = true;
|
|
8082
|
+
enqueue("SYSTEM", Buffer.from("\r\nCancellation requested\r\n"));
|
|
8083
|
+
sendSignal("SIGTERM");
|
|
8084
|
+
const killTimer = setTimeout(() => sendSignal("SIGKILL"), 5e3);
|
|
8085
|
+
killTimer.unref();
|
|
8086
|
+
};
|
|
8087
|
+
signal.addEventListener("abort", abort, { once: true });
|
|
8088
|
+
if (signal.aborted) abort();
|
|
8089
|
+
child.once("error", (error) => {
|
|
8090
|
+
if (settled) return;
|
|
8091
|
+
settled = true;
|
|
8092
|
+
signal.removeEventListener("abort", abort);
|
|
8093
|
+
reject(error);
|
|
8094
|
+
});
|
|
8095
|
+
child.once("close", (exitCode, closeSignal) => {
|
|
8096
|
+
if (settled) return;
|
|
8097
|
+
settled = true;
|
|
8098
|
+
signal.removeEventListener("abort", abort);
|
|
8099
|
+
flush();
|
|
8100
|
+
void uploadChain.then(
|
|
8101
|
+
() => resolve7({
|
|
8102
|
+
exitCode,
|
|
8103
|
+
signal: closeSignal,
|
|
8104
|
+
timedOut: false,
|
|
8105
|
+
cancelled
|
|
8106
|
+
})
|
|
8107
|
+
);
|
|
8108
|
+
});
|
|
7920
8109
|
});
|
|
7921
|
-
}
|
|
7922
|
-
|
|
7923
|
-
|
|
7924
|
-
// src/handlers/cloudflared.ts
|
|
7925
|
-
function validateCloudflaredPayload(payload) {
|
|
7926
|
-
if (!payload || typeof payload !== "object" || Array.isArray(payload)) {
|
|
7927
|
-
throw new Error("Cloudflared payload must be an object");
|
|
7928
|
-
}
|
|
7929
|
-
const value = payload;
|
|
7930
|
-
if (typeof value.tunnelName !== "string" || !TUNNEL_NAME_REGEX.test(value.tunnelName)) {
|
|
7931
|
-
throw new Error("Invalid Cloudflared tunnel name");
|
|
7932
|
-
}
|
|
7933
|
-
if (Object.keys(value).some((key) => key !== "tunnelName")) {
|
|
7934
|
-
throw new Error("Cloudflared payload contains an unsupported field");
|
|
8110
|
+
} finally {
|
|
8111
|
+
if (timer) clearTimeout(timer);
|
|
8112
|
+
await rm2(directory, { force: true, recursive: true });
|
|
7935
8113
|
}
|
|
7936
|
-
|
|
7937
|
-
}
|
|
7938
|
-
function runCloudflared(payload, timeoutMs, signal, onLog) {
|
|
7939
|
-
const { tunnelName } = validateCloudflaredPayload(payload);
|
|
7940
|
-
return runProcess({
|
|
7941
|
-
command: "cloudflared",
|
|
7942
|
-
args: ["tunnel", "run", tunnelName],
|
|
7943
|
-
timeoutMs,
|
|
7944
|
-
signal,
|
|
7945
|
-
onLog
|
|
7946
|
-
});
|
|
7947
|
-
}
|
|
8114
|
+
};
|
|
7948
8115
|
|
|
7949
8116
|
// src/handlers/signing.ts
|
|
7950
8117
|
import { createHash as createHash3, randomUUID, X509Certificate } from "node:crypto";
|
|
7951
8118
|
import {
|
|
7952
8119
|
mkdir as mkdir2,
|
|
7953
|
-
mkdtemp,
|
|
8120
|
+
mkdtemp as mkdtemp2,
|
|
7954
8121
|
readFile as readFile2,
|
|
7955
8122
|
readdir,
|
|
7956
|
-
rm as
|
|
8123
|
+
rm as rm3,
|
|
7957
8124
|
stat as stat2,
|
|
7958
|
-
writeFile as
|
|
8125
|
+
writeFile as writeFile3
|
|
7959
8126
|
} from "node:fs/promises";
|
|
7960
|
-
import { homedir as
|
|
7961
|
-
import { basename, join as
|
|
8127
|
+
import { homedir as homedir3, tmpdir as tmpdir2 } from "node:os";
|
|
8128
|
+
import { basename, join as join3, relative, sep } from "node:path";
|
|
7962
8129
|
|
|
7963
8130
|
// ../agent-contract/src/plist.ts
|
|
7964
8131
|
function xmlEscape(value) {
|
|
@@ -8193,15 +8360,15 @@ function captureCommand(options) {
|
|
|
8193
8360
|
|
|
8194
8361
|
// src/handlers/signing.ts
|
|
8195
8362
|
var PROFILE_DIRECTORIES = [
|
|
8196
|
-
|
|
8197
|
-
|
|
8363
|
+
join3(
|
|
8364
|
+
homedir3(),
|
|
8198
8365
|
"Library",
|
|
8199
8366
|
"Developer",
|
|
8200
8367
|
"Xcode",
|
|
8201
8368
|
"UserData",
|
|
8202
8369
|
"Provisioning Profiles"
|
|
8203
8370
|
),
|
|
8204
|
-
|
|
8371
|
+
join3(homedir3(), "Library", "MobileDevice", "Provisioning Profiles")
|
|
8205
8372
|
];
|
|
8206
8373
|
var PROFILE_EXTENSIONS = [".mobileprovision", ".provisionprofile"];
|
|
8207
8374
|
function text(value) {
|
|
@@ -8294,7 +8461,7 @@ async function readProfiles(timeoutMs, signal) {
|
|
|
8294
8461
|
continue;
|
|
8295
8462
|
signal.throwIfAborted();
|
|
8296
8463
|
const raw = await decodeProfile(
|
|
8297
|
-
|
|
8464
|
+
join3(directory, entry),
|
|
8298
8465
|
timeoutMs,
|
|
8299
8466
|
signal
|
|
8300
8467
|
);
|
|
@@ -8328,7 +8495,7 @@ async function decodedProfiles(timeoutMs, signal, strict = false) {
|
|
|
8328
8495
|
continue;
|
|
8329
8496
|
}
|
|
8330
8497
|
signal.throwIfAborted();
|
|
8331
|
-
const path =
|
|
8498
|
+
const path = join3(directory, entry);
|
|
8332
8499
|
const raw = await decodeProfile(path, timeoutMs, signal, strict);
|
|
8333
8500
|
if (!raw) continue;
|
|
8334
8501
|
let content;
|
|
@@ -8484,7 +8651,7 @@ async function readCertificates(timeoutMs, signal, strict = false) {
|
|
|
8484
8651
|
);
|
|
8485
8652
|
}
|
|
8486
8653
|
async function readArchiveBundles(archivePath, timeoutMs, signal) {
|
|
8487
|
-
const products =
|
|
8654
|
+
const products = join3(archivePath, "Products");
|
|
8488
8655
|
const bundles = [];
|
|
8489
8656
|
const queue = [products];
|
|
8490
8657
|
while (queue.length) {
|
|
@@ -8498,7 +8665,7 @@ async function readArchiveBundles(archivePath, timeoutMs, signal) {
|
|
|
8498
8665
|
}
|
|
8499
8666
|
for (const entry of entries) {
|
|
8500
8667
|
if (entry.isSymbolicLink() || !entry.isDirectory()) continue;
|
|
8501
|
-
const path =
|
|
8668
|
+
const path = join3(current, entry.name);
|
|
8502
8669
|
const signable = /\.(app|appex)$/.test(entry.name);
|
|
8503
8670
|
if (!signable) {
|
|
8504
8671
|
if (!/\.[A-Za-z0-9]+$/.test(entry.name)) queue.push(path);
|
|
@@ -8530,7 +8697,7 @@ async function bundleIdentifier(bundlePath, timeoutMs, signal) {
|
|
|
8530
8697
|
"raw",
|
|
8531
8698
|
"-o",
|
|
8532
8699
|
"-",
|
|
8533
|
-
|
|
8700
|
+
join3(bundlePath, "Info.plist")
|
|
8534
8701
|
],
|
|
8535
8702
|
timeoutMs: Math.min(timeoutMs, 5e3),
|
|
8536
8703
|
signal
|
|
@@ -8546,7 +8713,7 @@ async function embeddedProfile(bundlePath, timeoutMs, signal) {
|
|
|
8546
8713
|
"embedded.mobileprovision",
|
|
8547
8714
|
"embedded.provisionprofile"
|
|
8548
8715
|
]) {
|
|
8549
|
-
const path =
|
|
8716
|
+
const path = join3(bundlePath, name);
|
|
8550
8717
|
try {
|
|
8551
8718
|
await stat2(path);
|
|
8552
8719
|
} catch {
|
|
@@ -8593,7 +8760,7 @@ async function inspectSigningAssets(archivePath, timeoutMs, signal) {
|
|
|
8593
8760
|
}
|
|
8594
8761
|
var inspectIosSigning = async (payload, timeoutMs, signal) => {
|
|
8595
8762
|
const input = parseBuildSigningInspectPayload(payload);
|
|
8596
|
-
const archivePath =
|
|
8763
|
+
const archivePath = join3(input.artifactDirectory, input.archiveRelativePath);
|
|
8597
8764
|
const inspection = await inspectSigningAssets(archivePath, timeoutMs, signal);
|
|
8598
8765
|
return {
|
|
8599
8766
|
exitCode: 0,
|
|
@@ -8655,21 +8822,21 @@ var installSigningProfile = async (payload, timeoutMs, signal) => {
|
|
|
8655
8822
|
const { contentBase64 } = signingProfileInstallPayload(payload);
|
|
8656
8823
|
const content = Buffer.from(contentBase64, "base64");
|
|
8657
8824
|
if (!content.length) throw new Error("Provisioning profile is empty");
|
|
8658
|
-
const temporaryRoot = await
|
|
8659
|
-
const temporaryPath =
|
|
8825
|
+
const temporaryRoot = await mkdtemp2(join3(tmpdir2(), "ade-profile-"));
|
|
8826
|
+
const temporaryPath = join3(temporaryRoot, `${randomUUID()}.mobileprovision`);
|
|
8660
8827
|
try {
|
|
8661
|
-
await
|
|
8828
|
+
await writeFile3(temporaryPath, content, { mode: 384 });
|
|
8662
8829
|
const raw = await decodeProfile(temporaryPath, timeoutMs, signal);
|
|
8663
8830
|
if (!raw) throw new Error("Provisioning profile is invalid or unsigned");
|
|
8664
8831
|
const uuid = text(raw.UUID);
|
|
8665
8832
|
if (!uuid) throw new Error("Provisioning profile UUID is missing");
|
|
8666
8833
|
const directory = PROFILE_DIRECTORIES[0];
|
|
8667
8834
|
await mkdir2(directory, { recursive: true, mode: 448 });
|
|
8668
|
-
const destination =
|
|
8669
|
-
await
|
|
8835
|
+
const destination = join3(directory, `${uuid}.mobileprovision`);
|
|
8836
|
+
await writeFile3(destination, content, { mode: 384 });
|
|
8670
8837
|
return { ...successfulProcess, uuid };
|
|
8671
8838
|
} finally {
|
|
8672
|
-
await
|
|
8839
|
+
await rm3(temporaryRoot, { recursive: true, force: true });
|
|
8673
8840
|
}
|
|
8674
8841
|
};
|
|
8675
8842
|
var deleteSigningProfile = async (payload, timeoutMs, signal) => {
|
|
@@ -8679,7 +8846,7 @@ var deleteSigningProfile = async (payload, timeoutMs, signal) => {
|
|
|
8679
8846
|
);
|
|
8680
8847
|
for (const profile of matches) {
|
|
8681
8848
|
signal.throwIfAborted();
|
|
8682
|
-
await
|
|
8849
|
+
await rm3(profile.path, { force: false });
|
|
8683
8850
|
}
|
|
8684
8851
|
return { ...successfulProcess, uuid, deleted: matches.length };
|
|
8685
8852
|
};
|
|
@@ -8693,10 +8860,10 @@ var importSigningIdentity = async (payload, timeoutMs, signal, _onLog, context)
|
|
|
8693
8860
|
const hash = createHash3("sha256").update(p12).digest("hex").toUpperCase();
|
|
8694
8861
|
if (hash !== input.sha256)
|
|
8695
8862
|
throw new Error("Signing identity transfer changed");
|
|
8696
|
-
const temporaryRoot = await
|
|
8697
|
-
const path =
|
|
8863
|
+
const temporaryRoot = await mkdtemp2(join3(tmpdir2(), "ade-identity-"));
|
|
8864
|
+
const path = join3(temporaryRoot, "identity.p12");
|
|
8698
8865
|
try {
|
|
8699
|
-
await
|
|
8866
|
+
await writeFile3(path, p12, { mode: 384 });
|
|
8700
8867
|
const result = await captureCommand({
|
|
8701
8868
|
command: "/usr/bin/security",
|
|
8702
8869
|
args: [
|
|
@@ -8719,7 +8886,7 @@ var importSigningIdentity = async (payload, timeoutMs, signal, _onLog, context)
|
|
|
8719
8886
|
}
|
|
8720
8887
|
return { ...successfulProcess, sha256: input.sha256 };
|
|
8721
8888
|
} finally {
|
|
8722
|
-
await
|
|
8889
|
+
await rm3(temporaryRoot, { recursive: true, force: true });
|
|
8723
8890
|
}
|
|
8724
8891
|
};
|
|
8725
8892
|
var deleteSigningIdentity = async (payload, timeoutMs, signal) => {
|
|
@@ -8740,6 +8907,112 @@ var deleteSigningIdentity = async (payload, timeoutMs, signal) => {
|
|
|
8740
8907
|
|
|
8741
8908
|
// src/handlers/ccusage.ts
|
|
8742
8909
|
import { Buffer as Buffer2 } from "node:buffer";
|
|
8910
|
+
|
|
8911
|
+
// src/process-runner.ts
|
|
8912
|
+
import { spawn as spawn3 } from "node:child_process";
|
|
8913
|
+
async function runProcess(options) {
|
|
8914
|
+
return new Promise((resolve7, reject) => {
|
|
8915
|
+
let sequence = 0;
|
|
8916
|
+
let timedOut = false;
|
|
8917
|
+
let cancelled = false;
|
|
8918
|
+
let settled = false;
|
|
8919
|
+
let logChain = Promise.resolve();
|
|
8920
|
+
const detached = process.platform !== "win32";
|
|
8921
|
+
const child = spawn3(options.command, options.args, {
|
|
8922
|
+
shell: false,
|
|
8923
|
+
stdio: ["ignore", "pipe", "pipe"],
|
|
8924
|
+
cwd: options.cwd,
|
|
8925
|
+
env: options.env ?? process.env,
|
|
8926
|
+
// A separate process group lets cancellation terminate scripts and all
|
|
8927
|
+
// descendants instead of leaving a child holding stdout/stderr open.
|
|
8928
|
+
detached
|
|
8929
|
+
});
|
|
8930
|
+
const emit = (stream, message) => {
|
|
8931
|
+
const log = {
|
|
8932
|
+
sequence: sequence++,
|
|
8933
|
+
stream,
|
|
8934
|
+
message,
|
|
8935
|
+
createdAt: (/* @__PURE__ */ new Date()).toISOString()
|
|
8936
|
+
};
|
|
8937
|
+
logChain = logChain.then(async () => {
|
|
8938
|
+
try {
|
|
8939
|
+
await options.onLog(log);
|
|
8940
|
+
} catch (error) {
|
|
8941
|
+
console.error(
|
|
8942
|
+
`Could not append process log ${log.sequence}:`,
|
|
8943
|
+
error instanceof Error ? error.message : error
|
|
8944
|
+
);
|
|
8945
|
+
}
|
|
8946
|
+
});
|
|
8947
|
+
};
|
|
8948
|
+
const attach = (stream, kind) => {
|
|
8949
|
+
let remainder = "";
|
|
8950
|
+
stream.setEncoding("utf8");
|
|
8951
|
+
stream.on("data", (chunk) => {
|
|
8952
|
+
const parts = `${remainder}${chunk}`.split(/\r?\n/);
|
|
8953
|
+
remainder = parts.pop() ?? "";
|
|
8954
|
+
for (const line of parts) emit(kind, line);
|
|
8955
|
+
});
|
|
8956
|
+
stream.on("end", () => {
|
|
8957
|
+
if (remainder) emit(kind, remainder);
|
|
8958
|
+
});
|
|
8959
|
+
};
|
|
8960
|
+
attach(child.stdout, "STDOUT");
|
|
8961
|
+
attach(child.stderr, "STDERR");
|
|
8962
|
+
const sendSignal = (signal) => {
|
|
8963
|
+
if (detached && child.pid) {
|
|
8964
|
+
try {
|
|
8965
|
+
process.kill(-child.pid, signal);
|
|
8966
|
+
return;
|
|
8967
|
+
} catch (error) {
|
|
8968
|
+
if (!(error instanceof Error) || !("code" in error) || error.code !== "ESRCH") {
|
|
8969
|
+
throw error;
|
|
8970
|
+
}
|
|
8971
|
+
}
|
|
8972
|
+
}
|
|
8973
|
+
child.kill(signal);
|
|
8974
|
+
};
|
|
8975
|
+
const terminate = () => {
|
|
8976
|
+
if (child.exitCode !== null || child.killed) return;
|
|
8977
|
+
sendSignal("SIGTERM");
|
|
8978
|
+
const killTimer = setTimeout(() => sendSignal("SIGKILL"), 5e3);
|
|
8979
|
+
killTimer.unref();
|
|
8980
|
+
};
|
|
8981
|
+
const timeout = setTimeout(() => {
|
|
8982
|
+
timedOut = true;
|
|
8983
|
+
emit(
|
|
8984
|
+
"SYSTEM",
|
|
8985
|
+
`Process exceeded its ${Math.round(options.timeoutMs / 1e3)} second timeout`
|
|
8986
|
+
);
|
|
8987
|
+
terminate();
|
|
8988
|
+
}, options.timeoutMs);
|
|
8989
|
+
timeout.unref();
|
|
8990
|
+
const abort = () => {
|
|
8991
|
+
cancelled = true;
|
|
8992
|
+
emit("SYSTEM", "Cancellation requested");
|
|
8993
|
+
terminate();
|
|
8994
|
+
};
|
|
8995
|
+
options.signal.addEventListener("abort", abort, { once: true });
|
|
8996
|
+
child.once("error", (error) => {
|
|
8997
|
+
if (settled) return;
|
|
8998
|
+
settled = true;
|
|
8999
|
+
clearTimeout(timeout);
|
|
9000
|
+
options.signal.removeEventListener("abort", abort);
|
|
9001
|
+
reject(error);
|
|
9002
|
+
});
|
|
9003
|
+
child.once("close", (exitCode, signal) => {
|
|
9004
|
+
if (settled) return;
|
|
9005
|
+
settled = true;
|
|
9006
|
+
clearTimeout(timeout);
|
|
9007
|
+
options.signal.removeEventListener("abort", abort);
|
|
9008
|
+
void logChain.then(
|
|
9009
|
+
() => resolve7({ exitCode, signal, timedOut, cancelled })
|
|
9010
|
+
);
|
|
9011
|
+
});
|
|
9012
|
+
});
|
|
9013
|
+
}
|
|
9014
|
+
|
|
9015
|
+
// src/handlers/ccusage.ts
|
|
8743
9016
|
var MAX_CCUSAGE_STDOUT_BYTES = 16 * 1024 * 1024;
|
|
8744
9017
|
function validateCcusagePayload(payload) {
|
|
8745
9018
|
if (!payload || typeof payload !== "object" || Array.isArray(payload)) {
|
|
@@ -8793,9 +9066,17 @@ async function runCcusage(payload, timeoutMs, signal, onLog) {
|
|
|
8793
9066
|
}
|
|
8794
9067
|
|
|
8795
9068
|
// src/handlers/build-data.ts
|
|
8796
|
-
import {
|
|
8797
|
-
|
|
8798
|
-
|
|
9069
|
+
import {
|
|
9070
|
+
lstat,
|
|
9071
|
+
opendir,
|
|
9072
|
+
readdir as readdir2,
|
|
9073
|
+
realpath as realpath2,
|
|
9074
|
+
rm as rm4,
|
|
9075
|
+
stat as stat3,
|
|
9076
|
+
statfs
|
|
9077
|
+
} from "node:fs/promises";
|
|
9078
|
+
import { homedir as homedir4 } from "node:os";
|
|
9079
|
+
import { basename as basename2, dirname as dirname2, isAbsolute, join as join4, resolve } from "node:path";
|
|
8799
9080
|
var successfulProcess2 = {
|
|
8800
9081
|
exitCode: 0,
|
|
8801
9082
|
signal: null,
|
|
@@ -8812,7 +9093,7 @@ function safeRelativePath3(value) {
|
|
|
8812
9093
|
}
|
|
8813
9094
|
async function configuredRoots(payload) {
|
|
8814
9095
|
if (payload.mode === "DEFAULT") {
|
|
8815
|
-
return [
|
|
9096
|
+
return [join4(homedir4(), "Library", "Developer", "Xcode", "DerivedData")];
|
|
8816
9097
|
}
|
|
8817
9098
|
if (payload.mode === "ABSOLUTE") {
|
|
8818
9099
|
if (!payload.path || !isAbsolute(payload.path)) {
|
|
@@ -8849,7 +9130,7 @@ async function scanRoot(configuredRoot, timeoutMs, signal) {
|
|
|
8849
9130
|
signal.throwIfAborted();
|
|
8850
9131
|
let rootPath2;
|
|
8851
9132
|
try {
|
|
8852
|
-
rootPath2 = await
|
|
9133
|
+
rootPath2 = await realpath2(configuredRoot);
|
|
8853
9134
|
} catch (error) {
|
|
8854
9135
|
if (error.code === "ENOENT") {
|
|
8855
9136
|
return { entries: [], warning: null };
|
|
@@ -8869,12 +9150,15 @@ async function scanRoot(configuredRoot, timeoutMs, signal) {
|
|
|
8869
9150
|
};
|
|
8870
9151
|
}
|
|
8871
9152
|
const entries = [];
|
|
9153
|
+
const rootStats = await stat3(rootPath2);
|
|
9154
|
+
const volumeId = String(rootStats.dev);
|
|
8872
9155
|
for (const child of children) {
|
|
8873
9156
|
signal.throwIfAborted();
|
|
8874
9157
|
if (!child.isDirectory()) continue;
|
|
8875
|
-
const path =
|
|
9158
|
+
const path = join4(rootPath2, child.name);
|
|
9159
|
+
const information = await lstat(path);
|
|
8876
9160
|
const projectPath = await workspacePath(
|
|
8877
|
-
|
|
9161
|
+
join4(path, "info.plist"),
|
|
8878
9162
|
timeoutMs,
|
|
8879
9163
|
signal
|
|
8880
9164
|
);
|
|
@@ -8883,21 +9167,23 @@ async function scanRoot(configuredRoot, timeoutMs, signal) {
|
|
|
8883
9167
|
rootPath: rootPath2,
|
|
8884
9168
|
name: child.name,
|
|
8885
9169
|
kind: projectPath ? "PROJECT" : child.name.toLocaleLowerCase().endsWith(".noindex") ? "SHARED_CACHE" : "PENDING",
|
|
8886
|
-
workspacePath: projectPath
|
|
9170
|
+
workspacePath: projectPath,
|
|
9171
|
+
modifiedAt: information.mtime.toISOString(),
|
|
9172
|
+
volumeId
|
|
8887
9173
|
});
|
|
8888
9174
|
}
|
|
8889
9175
|
entries.sort((first, second) => first.name.localeCompare(second.name));
|
|
8890
9176
|
return { entries, warning: null };
|
|
8891
9177
|
}
|
|
8892
9178
|
async function scanDeviceSupport(signal) {
|
|
8893
|
-
const configuredRoot =
|
|
8894
|
-
process.env.ADE_IOS_DEVICE_SUPPORT_DIRECTORY ??
|
|
9179
|
+
const configuredRoot = join4(
|
|
9180
|
+
process.env.ADE_IOS_DEVICE_SUPPORT_DIRECTORY ?? homedir4(),
|
|
8895
9181
|
...process.env.ADE_IOS_DEVICE_SUPPORT_DIRECTORY ? [] : ["Library", "Developer", "Xcode", "iOS DeviceSupport"]
|
|
8896
9182
|
);
|
|
8897
9183
|
signal.throwIfAborted();
|
|
8898
9184
|
let rootPath2;
|
|
8899
9185
|
try {
|
|
8900
|
-
rootPath2 = await
|
|
9186
|
+
rootPath2 = await realpath2(configuredRoot);
|
|
8901
9187
|
} catch (error) {
|
|
8902
9188
|
if (error.code === "ENOENT") {
|
|
8903
9189
|
return { entries: [], warning: null };
|
|
@@ -8911,11 +9197,13 @@ async function scanDeviceSupport(signal) {
|
|
|
8911
9197
|
const children = await readdir2(rootPath2, { withFileTypes: true });
|
|
8912
9198
|
return {
|
|
8913
9199
|
entries: children.filter((child) => child.isDirectory() && !child.isSymbolicLink()).map((child) => ({
|
|
8914
|
-
path:
|
|
9200
|
+
path: join4(rootPath2, child.name),
|
|
8915
9201
|
rootPath: rootPath2,
|
|
8916
9202
|
name: child.name,
|
|
8917
9203
|
kind: "DEVICE_SUPPORT",
|
|
8918
|
-
workspacePath: null
|
|
9204
|
+
workspacePath: null,
|
|
9205
|
+
modifiedAt: null,
|
|
9206
|
+
volumeId: null
|
|
8919
9207
|
})).sort((first, second) => first.name.localeCompare(second.name)),
|
|
8920
9208
|
warning: null
|
|
8921
9209
|
};
|
|
@@ -8936,7 +9224,7 @@ var scanBuildData = async (rawPayload, timeoutMs, signal) => {
|
|
|
8936
9224
|
signal.throwIfAborted();
|
|
8937
9225
|
let canonical = root;
|
|
8938
9226
|
try {
|
|
8939
|
-
canonical = await
|
|
9227
|
+
canonical = await realpath2(root);
|
|
8940
9228
|
} catch {
|
|
8941
9229
|
}
|
|
8942
9230
|
if (canonicalRoots.has(canonical)) continue;
|
|
@@ -8970,7 +9258,7 @@ async function allocatedBytes(path, signal) {
|
|
|
8970
9258
|
try {
|
|
8971
9259
|
for await (const entry of directory) {
|
|
8972
9260
|
signal.throwIfAborted();
|
|
8973
|
-
total += await allocatedBytes(
|
|
9261
|
+
total += await allocatedBytes(join4(path, entry.name), signal);
|
|
8974
9262
|
}
|
|
8975
9263
|
} finally {
|
|
8976
9264
|
await directory.close().catch(() => void 0);
|
|
@@ -8984,7 +9272,7 @@ var sizeBuildData = async (rawPayload, _timeoutMs, signal) => {
|
|
|
8984
9272
|
signal.throwIfAborted();
|
|
8985
9273
|
try {
|
|
8986
9274
|
assertDirectChild(target2.rootPath, target2.path);
|
|
8987
|
-
const rootPath2 = await
|
|
9275
|
+
const rootPath2 = await realpath2(target2.rootPath);
|
|
8988
9276
|
if (rootPath2 !== resolve(target2.rootPath) || dirname2(resolve(target2.path)) !== rootPath2) {
|
|
8989
9277
|
throw new Error("Build Data root changed since the scan");
|
|
8990
9278
|
}
|
|
@@ -9009,13 +9297,13 @@ var sizeBuildData = async (rawPayload, _timeoutMs, signal) => {
|
|
|
9009
9297
|
return { ...successfulProcess2, sizes };
|
|
9010
9298
|
};
|
|
9011
9299
|
var deleteBuildData = async (rawPayload, _timeoutMs, signal) => {
|
|
9012
|
-
const payload =
|
|
9300
|
+
const payload = buildDataDeletePayload(rawPayload);
|
|
9013
9301
|
const deleted = [];
|
|
9014
9302
|
for (const target2 of payload.targets) {
|
|
9015
9303
|
signal.throwIfAborted();
|
|
9016
9304
|
try {
|
|
9017
9305
|
assertDirectChild(target2.rootPath, target2.path);
|
|
9018
|
-
const rootPath2 = await
|
|
9306
|
+
const rootPath2 = await realpath2(target2.rootPath);
|
|
9019
9307
|
if (rootPath2 !== resolve(target2.rootPath) || dirname2(resolve(target2.path)) !== rootPath2) {
|
|
9020
9308
|
throw new Error("Build Data root changed since the scan");
|
|
9021
9309
|
}
|
|
@@ -9023,7 +9311,7 @@ var deleteBuildData = async (rawPayload, _timeoutMs, signal) => {
|
|
|
9023
9311
|
if (!stats.isDirectory() || stats.isSymbolicLink()) {
|
|
9024
9312
|
throw new Error("Build Data target is not a directory");
|
|
9025
9313
|
}
|
|
9026
|
-
await
|
|
9314
|
+
await rm4(target2.path, { recursive: true, force: false, maxRetries: 3 });
|
|
9027
9315
|
deleted.push({ path: target2.path, deleted: true, error: null });
|
|
9028
9316
|
} catch (error) {
|
|
9029
9317
|
signal.throwIfAborted();
|
|
@@ -9036,11 +9324,122 @@ var deleteBuildData = async (rawPayload, _timeoutMs, signal) => {
|
|
|
9036
9324
|
}
|
|
9037
9325
|
return { ...successfulProcess2, deleted };
|
|
9038
9326
|
};
|
|
9327
|
+
async function sharedCapacityId(canonicalPath, volumeId, signal) {
|
|
9328
|
+
try {
|
|
9329
|
+
const result = await captureCommand({
|
|
9330
|
+
command: "/usr/sbin/diskutil",
|
|
9331
|
+
args: ["info", "-plist", canonicalPath],
|
|
9332
|
+
timeoutMs: 5e3,
|
|
9333
|
+
signal
|
|
9334
|
+
});
|
|
9335
|
+
signal.throwIfAborted();
|
|
9336
|
+
if (result.exitCode !== 0) return volumeId;
|
|
9337
|
+
const information = parsePlist(result.stdout);
|
|
9338
|
+
if (!information || typeof information !== "object") return volumeId;
|
|
9339
|
+
const container = information.APFSContainerReference;
|
|
9340
|
+
return typeof container === "string" && container.trim() ? `apfs:${container.trim()}` : volumeId;
|
|
9341
|
+
} catch {
|
|
9342
|
+
signal.throwIfAborted();
|
|
9343
|
+
return volumeId;
|
|
9344
|
+
}
|
|
9345
|
+
}
|
|
9346
|
+
async function inspectVolume(configuredPath, role, signal) {
|
|
9347
|
+
signal.throwIfAborted();
|
|
9348
|
+
const canonicalPath = await realpath2(configuredPath);
|
|
9349
|
+
const [information, filesystem] = await Promise.all([
|
|
9350
|
+
stat3(canonicalPath),
|
|
9351
|
+
statfs(canonicalPath, { bigint: true })
|
|
9352
|
+
]);
|
|
9353
|
+
const id2 = String(information.dev);
|
|
9354
|
+
return {
|
|
9355
|
+
canonicalPath,
|
|
9356
|
+
volume: {
|
|
9357
|
+
id: id2,
|
|
9358
|
+
capacityId: id2,
|
|
9359
|
+
totalBytes: Number(filesystem.blocks * filesystem.bsize),
|
|
9360
|
+
freeBytes: Number(filesystem.bavail * filesystem.bsize),
|
|
9361
|
+
roles: /* @__PURE__ */ new Set([role]),
|
|
9362
|
+
paths: /* @__PURE__ */ new Set([canonicalPath])
|
|
9363
|
+
}
|
|
9364
|
+
};
|
|
9365
|
+
}
|
|
9366
|
+
async function collectAgentDiskSpace(configuration, signal) {
|
|
9367
|
+
const scanPayload = buildDataScanPayload({
|
|
9368
|
+
mode: configuration.derivedDataLocationMode,
|
|
9369
|
+
path: configuration.derivedDataPath,
|
|
9370
|
+
worktrees: configuration.worktrees
|
|
9371
|
+
});
|
|
9372
|
+
const roots = await configuredRoots(scanPayload);
|
|
9373
|
+
const requested = [
|
|
9374
|
+
{ path: "/", role: "MAIN" },
|
|
9375
|
+
...configuration.baseRepoDirectory ? [{ path: configuration.baseRepoDirectory, role: "BASE_REPO" }] : [],
|
|
9376
|
+
...roots.map((path) => ({ path, role: "DERIVED_DATA" }))
|
|
9377
|
+
];
|
|
9378
|
+
const warnings = [];
|
|
9379
|
+
const volumes = /* @__PURE__ */ new Map();
|
|
9380
|
+
for (const request of requested) {
|
|
9381
|
+
signal.throwIfAborted();
|
|
9382
|
+
try {
|
|
9383
|
+
const inspected = await inspectVolume(request.path, request.role, signal);
|
|
9384
|
+
const existing = volumes.get(inspected.volume.id);
|
|
9385
|
+
if (existing) {
|
|
9386
|
+
existing.roles.add(request.role);
|
|
9387
|
+
existing.paths.add(inspected.canonicalPath);
|
|
9388
|
+
existing.totalBytes = inspected.volume.totalBytes;
|
|
9389
|
+
existing.freeBytes = inspected.volume.freeBytes;
|
|
9390
|
+
} else {
|
|
9391
|
+
inspected.volume.capacityId = await sharedCapacityId(
|
|
9392
|
+
inspected.canonicalPath,
|
|
9393
|
+
inspected.volume.id,
|
|
9394
|
+
signal
|
|
9395
|
+
);
|
|
9396
|
+
volumes.set(inspected.volume.id, inspected.volume);
|
|
9397
|
+
}
|
|
9398
|
+
} catch (error) {
|
|
9399
|
+
warnings.push(`${request.path}: ${errorMessage(error)}`);
|
|
9400
|
+
}
|
|
9401
|
+
}
|
|
9402
|
+
const entries = [];
|
|
9403
|
+
const scannedRoots = /* @__PURE__ */ new Set();
|
|
9404
|
+
for (const root of roots) {
|
|
9405
|
+
signal.throwIfAborted();
|
|
9406
|
+
let canonical = root;
|
|
9407
|
+
try {
|
|
9408
|
+
canonical = await realpath2(root);
|
|
9409
|
+
} catch {
|
|
9410
|
+
}
|
|
9411
|
+
if (scannedRoots.has(canonical)) continue;
|
|
9412
|
+
scannedRoots.add(canonical);
|
|
9413
|
+
const result = await scanRoot(root, 45e3, signal);
|
|
9414
|
+
if (result.warning) warnings.push(result.warning);
|
|
9415
|
+
for (const entry of result.entries) {
|
|
9416
|
+
if (!entry.modifiedAt || !entry.volumeId) continue;
|
|
9417
|
+
entries.push({
|
|
9418
|
+
...entry,
|
|
9419
|
+
modifiedAt: entry.modifiedAt,
|
|
9420
|
+
volumeId: entry.volumeId
|
|
9421
|
+
});
|
|
9422
|
+
}
|
|
9423
|
+
}
|
|
9424
|
+
return {
|
|
9425
|
+
observedAt: (/* @__PURE__ */ new Date()).toISOString(),
|
|
9426
|
+
volumes: [...volumes.values()].map((volume) => ({
|
|
9427
|
+
id: volume.id,
|
|
9428
|
+
capacityId: volume.capacityId,
|
|
9429
|
+
totalBytes: volume.totalBytes,
|
|
9430
|
+
freeBytes: volume.freeBytes,
|
|
9431
|
+
roles: [...volume.roles],
|
|
9432
|
+
paths: [...volume.paths]
|
|
9433
|
+
})),
|
|
9434
|
+
entries,
|
|
9435
|
+
warnings: [...new Set(warnings)]
|
|
9436
|
+
};
|
|
9437
|
+
}
|
|
9039
9438
|
|
|
9040
9439
|
// src/handlers/codebases.ts
|
|
9041
|
-
import { readdir as readdir3, realpath as
|
|
9042
|
-
import { homedir as
|
|
9043
|
-
import { dirname as dirname3, join as
|
|
9440
|
+
import { readdir as readdir3, realpath as realpath3, stat as stat4 } from "node:fs/promises";
|
|
9441
|
+
import { homedir as homedir5 } from "node:os";
|
|
9442
|
+
import { dirname as dirname3, join as join5, resolve as resolve2 } from "node:path";
|
|
9044
9443
|
var successfulProcess3 = {
|
|
9045
9444
|
exitCode: 0,
|
|
9046
9445
|
signal: null,
|
|
@@ -9117,7 +9516,7 @@ function baseSnapshot(folder) {
|
|
|
9117
9516
|
}
|
|
9118
9517
|
async function fetchedAt(commonDirectory) {
|
|
9119
9518
|
try {
|
|
9120
|
-
return (await
|
|
9519
|
+
return (await stat4(join5(commonDirectory, "FETCH_HEAD"))).mtime.toISOString();
|
|
9121
9520
|
} catch {
|
|
9122
9521
|
return null;
|
|
9123
9522
|
}
|
|
@@ -9127,8 +9526,8 @@ async function inspectCodebaseProcess(selectedFolder, timeoutMs, signal, expecte
|
|
|
9127
9526
|
const base = baseSnapshot(fallbackFolder);
|
|
9128
9527
|
let selected;
|
|
9129
9528
|
try {
|
|
9130
|
-
selected = await
|
|
9131
|
-
if (!(await
|
|
9529
|
+
selected = await realpath3(fallbackFolder);
|
|
9530
|
+
if (!(await stat4(selected)).isDirectory())
|
|
9132
9531
|
throw new Error("Folder is not a directory");
|
|
9133
9532
|
} catch (error) {
|
|
9134
9533
|
return {
|
|
@@ -9160,7 +9559,7 @@ async function inspectCodebaseProcess(selectedFolder, timeoutMs, signal, expecte
|
|
|
9160
9559
|
}
|
|
9161
9560
|
};
|
|
9162
9561
|
}
|
|
9163
|
-
const folder = await
|
|
9562
|
+
const folder = await realpath3(rootResult.stdout.trim());
|
|
9164
9563
|
const bare = await git(
|
|
9165
9564
|
folder,
|
|
9166
9565
|
["rev-parse", "--is-bare-repository"],
|
|
@@ -9211,8 +9610,8 @@ async function inspectCodebaseProcess(selectedFolder, timeoutMs, signal, expecte
|
|
|
9211
9610
|
};
|
|
9212
9611
|
}
|
|
9213
9612
|
const origin2 = normalizeGitOrigin(originResult.stdout.trim());
|
|
9214
|
-
const gitDirectory2 = await
|
|
9215
|
-
const commonDirectory = await
|
|
9613
|
+
const gitDirectory2 = await realpath3(gitDirectoryResult.stdout.trim());
|
|
9614
|
+
const commonDirectory = await realpath3(commonDirectoryResult.stdout.trim());
|
|
9216
9615
|
const linkedWorktree = gitDirectory2 !== commonDirectory;
|
|
9217
9616
|
const branchResult = await git(
|
|
9218
9617
|
folder,
|
|
@@ -9296,9 +9695,9 @@ async function inspectCodebase(selectedFolder, timeoutMs, signal, expectedOrigin
|
|
|
9296
9695
|
}
|
|
9297
9696
|
var browseCodebaseDirectories = async (payload) => {
|
|
9298
9697
|
const input = codebaseBrowsePayload(payload);
|
|
9299
|
-
const homePath = await
|
|
9300
|
-
const path = await
|
|
9301
|
-
if (!(await
|
|
9698
|
+
const homePath = await realpath3(homedir5());
|
|
9699
|
+
const path = await realpath3(input.path ? resolve2(input.path) : homePath);
|
|
9700
|
+
if (!(await stat4(path)).isDirectory())
|
|
9302
9701
|
throw new Error("Path is not a directory");
|
|
9303
9702
|
const candidates = await readdir3(path, { withFileTypes: true });
|
|
9304
9703
|
const entries = [];
|
|
@@ -9306,13 +9705,13 @@ var browseCodebaseDirectories = async (payload) => {
|
|
|
9306
9705
|
if (candidate.isDirectory()) {
|
|
9307
9706
|
entries.push({
|
|
9308
9707
|
name: candidate.name,
|
|
9309
|
-
path:
|
|
9708
|
+
path: join5(path, candidate.name),
|
|
9310
9709
|
hidden: candidate.name.startsWith(".")
|
|
9311
9710
|
});
|
|
9312
9711
|
} else if (candidate.isSymbolicLink()) {
|
|
9313
9712
|
try {
|
|
9314
|
-
const target2 =
|
|
9315
|
-
if ((await
|
|
9713
|
+
const target2 = join5(path, candidate.name);
|
|
9714
|
+
if ((await stat4(target2)).isDirectory()) {
|
|
9316
9715
|
entries.push({
|
|
9317
9716
|
name: candidate.name,
|
|
9318
9717
|
path: target2,
|
|
@@ -9913,19 +10312,19 @@ import { execFile } from "node:child_process";
|
|
|
9913
10312
|
import { randomUUID as randomUUID2 } from "node:crypto";
|
|
9914
10313
|
import {
|
|
9915
10314
|
access,
|
|
9916
|
-
chmod as
|
|
10315
|
+
chmod as chmod3,
|
|
9917
10316
|
lstat as lstat2,
|
|
9918
10317
|
mkdir as mkdir3,
|
|
9919
10318
|
readFile as readFile3,
|
|
9920
|
-
realpath as
|
|
10319
|
+
realpath as realpath4,
|
|
9921
10320
|
readdir as readdir4,
|
|
9922
10321
|
rename as rename2,
|
|
9923
|
-
rm as
|
|
9924
|
-
stat as
|
|
9925
|
-
writeFile as
|
|
10322
|
+
rm as rm5,
|
|
10323
|
+
stat as stat5,
|
|
10324
|
+
writeFile as writeFile4
|
|
9926
10325
|
} from "node:fs/promises";
|
|
9927
|
-
import { homedir as
|
|
9928
|
-
import { dirname as dirname4, isAbsolute as isAbsolute2, join as
|
|
10326
|
+
import { homedir as homedir6 } from "node:os";
|
|
10327
|
+
import { dirname as dirname4, isAbsolute as isAbsolute2, join as join6, relative as relative2, resolve as resolve3, sep as sep2 } from "node:path";
|
|
9929
10328
|
import { promisify } from "node:util";
|
|
9930
10329
|
var executeFile = promisify(execFile);
|
|
9931
10330
|
var successfulProcess4 = {
|
|
@@ -9980,23 +10379,23 @@ var PROJECT_ROOTS = {
|
|
|
9980
10379
|
};
|
|
9981
10380
|
async function directoryExists(path) {
|
|
9982
10381
|
try {
|
|
9983
|
-
return (await
|
|
10382
|
+
return (await stat5(path)).isDirectory();
|
|
9984
10383
|
} catch {
|
|
9985
10384
|
return false;
|
|
9986
10385
|
}
|
|
9987
10386
|
}
|
|
9988
10387
|
async function configuredTools(tools) {
|
|
9989
|
-
const homePath =
|
|
10388
|
+
const homePath = homedir6();
|
|
9990
10389
|
return Promise.all(
|
|
9991
10390
|
AI_TOOLS.filter((tool) => tools.includes(tool)).map(async (tool) => ({
|
|
9992
10391
|
tool,
|
|
9993
|
-
configured: await directoryExists(
|
|
10392
|
+
configured: await directoryExists(join6(homePath, ...CONFIG_PATHS[tool])),
|
|
9994
10393
|
homePath
|
|
9995
10394
|
}))
|
|
9996
10395
|
);
|
|
9997
10396
|
}
|
|
9998
10397
|
function rootPath(location) {
|
|
9999
|
-
const base = location.scope === "GLOBAL" ?
|
|
10398
|
+
const base = location.scope === "GLOBAL" ? homedir6() : location.folder;
|
|
10000
10399
|
const parts = location.scope === "GLOBAL" ? GLOBAL_ROOTS[location.rootKind] : PROJECT_ROOTS[location.rootKind];
|
|
10001
10400
|
const path = resolve3(base, ...parts);
|
|
10002
10401
|
const normalizedBase = resolve3(base);
|
|
@@ -10013,7 +10412,7 @@ async function listPackageFiles(skillDirectory) {
|
|
|
10013
10412
|
let totalBytes = 0;
|
|
10014
10413
|
const visit = async (directory) => {
|
|
10015
10414
|
for (const entry of await readdir4(directory, { withFileTypes: true })) {
|
|
10016
|
-
const path =
|
|
10415
|
+
const path = join6(directory, entry.name);
|
|
10017
10416
|
const metadata = await lstat2(path);
|
|
10018
10417
|
if (metadata.isSymbolicLink()) {
|
|
10019
10418
|
throw new Error(
|
|
@@ -10049,7 +10448,7 @@ async function readPackage(directory) {
|
|
|
10049
10448
|
const metadata = await lstat2(directory);
|
|
10050
10449
|
let resolvedDirectory = directory;
|
|
10051
10450
|
if (metadata.isSymbolicLink()) {
|
|
10052
|
-
resolvedDirectory = await
|
|
10451
|
+
resolvedDirectory = await realpath4(directory);
|
|
10053
10452
|
} else if (!metadata.isDirectory()) {
|
|
10054
10453
|
throw new Error("Skill path is not a directory");
|
|
10055
10454
|
}
|
|
@@ -10102,7 +10501,7 @@ async function scanRoot2(location, configured, targets, warnings) {
|
|
|
10102
10501
|
const installations = [];
|
|
10103
10502
|
for (const entry of await readdir4(root, { withFileTypes: true })) {
|
|
10104
10503
|
if (!entry.isDirectory() && !entry.isSymbolicLink()) continue;
|
|
10105
|
-
const directory =
|
|
10504
|
+
const directory = join6(root, entry.name);
|
|
10106
10505
|
try {
|
|
10107
10506
|
const skillPackage = await readPackage(directory);
|
|
10108
10507
|
const relativeDirectory = location.folder ? relative2(location.folder, directory).split(sep2).join("/") : "";
|
|
@@ -10181,7 +10580,7 @@ var readSkills = async (payload) => {
|
|
|
10181
10580
|
}
|
|
10182
10581
|
packages.push({
|
|
10183
10582
|
...request,
|
|
10184
|
-
package: await readPackage(
|
|
10583
|
+
package: await readPackage(join6(root, request.skillName))
|
|
10185
10584
|
});
|
|
10186
10585
|
}
|
|
10187
10586
|
return { ...successfulProcess4, packages };
|
|
@@ -10222,7 +10621,7 @@ async function updateManagedExclude(folder, relativeSkillPath, present) {
|
|
|
10222
10621
|
const block = managed.size ? `${MANAGED_EXCLUDE_START}
|
|
10223
10622
|
${[...managed].sort().join("\n")}
|
|
10224
10623
|
${MANAGED_EXCLUDE_END}` : "";
|
|
10225
|
-
await
|
|
10624
|
+
await writeFile4(
|
|
10226
10625
|
excludePath,
|
|
10227
10626
|
`${[before, block, after].filter(Boolean).join("\n\n")}
|
|
10228
10627
|
`,
|
|
@@ -10243,11 +10642,11 @@ async function writePackage(location, skillPackage) {
|
|
|
10243
10642
|
throw new Error("New skill copies may only be written to shared roots");
|
|
10244
10643
|
}
|
|
10245
10644
|
const root = rootPath(location);
|
|
10246
|
-
const destination =
|
|
10645
|
+
const destination = join6(root, skillPackage.name);
|
|
10247
10646
|
await assertUntracked(location, destination);
|
|
10248
10647
|
await mkdir3(root, { recursive: true });
|
|
10249
|
-
const temporary =
|
|
10250
|
-
const backup =
|
|
10648
|
+
const temporary = join6(root, `.${skillPackage.name}.${randomUUID2()}.tmp`);
|
|
10649
|
+
const backup = join6(root, `.${skillPackage.name}.${randomUUID2()}.bak`);
|
|
10251
10650
|
await mkdir3(temporary, { recursive: true });
|
|
10252
10651
|
try {
|
|
10253
10652
|
for (const file of skillPackage.files) {
|
|
@@ -10255,8 +10654,8 @@ async function writePackage(location, skillPackage) {
|
|
|
10255
10654
|
if (!path.startsWith(`${temporary}${sep2}`))
|
|
10256
10655
|
throw new Error("Skill file escaped temporary directory");
|
|
10257
10656
|
await mkdir3(dirname4(path), { recursive: true });
|
|
10258
|
-
await
|
|
10259
|
-
await
|
|
10657
|
+
await writeFile4(path, Buffer.from(file.contentsBase64, "base64"));
|
|
10658
|
+
await chmod3(path, file.executable ? 493 : 420);
|
|
10260
10659
|
}
|
|
10261
10660
|
let hadDestination = false;
|
|
10262
10661
|
try {
|
|
@@ -10268,14 +10667,14 @@ async function writePackage(location, skillPackage) {
|
|
|
10268
10667
|
}
|
|
10269
10668
|
try {
|
|
10270
10669
|
await rename2(temporary, destination);
|
|
10271
|
-
if (hadDestination) await
|
|
10670
|
+
if (hadDestination) await rm5(backup, { recursive: true, force: true });
|
|
10272
10671
|
} catch (error) {
|
|
10273
10672
|
if (hadDestination) await rename2(backup, destination);
|
|
10274
10673
|
throw error;
|
|
10275
10674
|
}
|
|
10276
10675
|
} finally {
|
|
10277
|
-
await
|
|
10278
|
-
await
|
|
10676
|
+
await rm5(temporary, { recursive: true, force: true });
|
|
10677
|
+
await rm5(backup, { recursive: true, force: true });
|
|
10279
10678
|
}
|
|
10280
10679
|
return destination;
|
|
10281
10680
|
}
|
|
@@ -10285,7 +10684,7 @@ var applySkills = async (payload) => {
|
|
|
10285
10684
|
for (const operation of operations) {
|
|
10286
10685
|
const root = rootPath(operation);
|
|
10287
10686
|
const skillName = operation.kind === "WRITE" ? operation.package.name : operation.skillName;
|
|
10288
|
-
const destination =
|
|
10687
|
+
const destination = join6(root, skillName);
|
|
10289
10688
|
await assertUntracked(operation, destination);
|
|
10290
10689
|
if (operation.kind === "WRITE") {
|
|
10291
10690
|
await writePackage(operation, operation.package);
|
|
@@ -10295,7 +10694,7 @@ var applySkills = async (payload) => {
|
|
|
10295
10694
|
packageHash: operation.package.packageHash
|
|
10296
10695
|
});
|
|
10297
10696
|
} else {
|
|
10298
|
-
await
|
|
10697
|
+
await rm5(destination, { recursive: true, force: true });
|
|
10299
10698
|
results.push({
|
|
10300
10699
|
kind: operation.kind,
|
|
10301
10700
|
path: destination,
|
|
@@ -10314,9 +10713,9 @@ var applySkills = async (payload) => {
|
|
|
10314
10713
|
};
|
|
10315
10714
|
|
|
10316
10715
|
// src/handlers/runs.ts
|
|
10317
|
-
import { readFile as readFile4, readdir as readdir5, stat as
|
|
10318
|
-
import { homedir as
|
|
10319
|
-
import { join as
|
|
10716
|
+
import { readFile as readFile4, readdir as readdir5, stat as stat6 } from "node:fs/promises";
|
|
10717
|
+
import { homedir as homedir7 } from "node:os";
|
|
10718
|
+
import { join as join7 } from "node:path";
|
|
10320
10719
|
var successfulProcess5 = {
|
|
10321
10720
|
exitCode: 0,
|
|
10322
10721
|
signal: null,
|
|
@@ -10325,13 +10724,13 @@ var successfulProcess5 = {
|
|
|
10325
10724
|
};
|
|
10326
10725
|
async function fileExists(path) {
|
|
10327
10726
|
try {
|
|
10328
|
-
return (await
|
|
10727
|
+
return (await stat6(path)).isFile();
|
|
10329
10728
|
} catch {
|
|
10330
10729
|
return false;
|
|
10331
10730
|
}
|
|
10332
10731
|
}
|
|
10333
10732
|
async function findClaudeSessionFile(nativeId, home) {
|
|
10334
|
-
const projectsDir =
|
|
10733
|
+
const projectsDir = join7(home, ".claude", "projects");
|
|
10335
10734
|
let entries;
|
|
10336
10735
|
try {
|
|
10337
10736
|
entries = await readdir5(projectsDir, { withFileTypes: true });
|
|
@@ -10341,13 +10740,13 @@ async function findClaudeSessionFile(nativeId, home) {
|
|
|
10341
10740
|
const target2 = `${nativeId}.jsonl`;
|
|
10342
10741
|
for (const entry of entries) {
|
|
10343
10742
|
if (!entry.isDirectory()) continue;
|
|
10344
|
-
const candidate =
|
|
10743
|
+
const candidate = join7(projectsDir, entry.name, target2);
|
|
10345
10744
|
if (await fileExists(candidate)) return candidate;
|
|
10346
10745
|
}
|
|
10347
10746
|
return null;
|
|
10348
10747
|
}
|
|
10349
10748
|
async function findCodexSessionFile(nativeId, home) {
|
|
10350
|
-
const sessionsDir =
|
|
10749
|
+
const sessionsDir = join7(home, ".codex", "sessions");
|
|
10351
10750
|
const suffix = `-${nativeId}.jsonl`;
|
|
10352
10751
|
const walk = async (dir) => {
|
|
10353
10752
|
let entries;
|
|
@@ -10357,7 +10756,7 @@ async function findCodexSessionFile(nativeId, home) {
|
|
|
10357
10756
|
return null;
|
|
10358
10757
|
}
|
|
10359
10758
|
for (const entry of entries) {
|
|
10360
|
-
const path =
|
|
10759
|
+
const path = join7(dir, entry.name);
|
|
10361
10760
|
if (entry.isDirectory()) {
|
|
10362
10761
|
const found = await walk(path);
|
|
10363
10762
|
if (found) return found;
|
|
@@ -10374,13 +10773,13 @@ async function locateSessionFile(payload, home) {
|
|
|
10374
10773
|
}
|
|
10375
10774
|
var readRunSession = async (payload) => {
|
|
10376
10775
|
const input = parseRunSessionReadPayload(payload);
|
|
10377
|
-
const path = await locateSessionFile(input,
|
|
10776
|
+
const path = await locateSessionFile(input, homedir7());
|
|
10378
10777
|
if (!path) {
|
|
10379
10778
|
throw new Error(
|
|
10380
10779
|
`No ${input.provider === "CLAUDE" ? "Claude" : "Codex"} session file found for this run on this agent`
|
|
10381
10780
|
);
|
|
10382
10781
|
}
|
|
10383
|
-
const { size } = await
|
|
10782
|
+
const { size } = await stat6(path);
|
|
10384
10783
|
if (size > MAX_RUN_SESSION_FILE_BYTES) {
|
|
10385
10784
|
throw new Error(
|
|
10386
10785
|
`Session file is too large to export (${size} bytes exceeds the ${MAX_RUN_SESSION_FILE_BYTES} byte limit)`
|
|
@@ -10396,21 +10795,21 @@ var readRunSession = async (payload) => {
|
|
|
10396
10795
|
|
|
10397
10796
|
// src/handlers/workflows.ts
|
|
10398
10797
|
import {
|
|
10399
|
-
mkdtemp as
|
|
10798
|
+
mkdtemp as mkdtemp5,
|
|
10400
10799
|
readFile as readFile6,
|
|
10401
|
-
realpath as
|
|
10402
|
-
rm as
|
|
10403
|
-
stat as
|
|
10404
|
-
writeFile as
|
|
10800
|
+
realpath as realpath6,
|
|
10801
|
+
rm as rm8,
|
|
10802
|
+
stat as stat8,
|
|
10803
|
+
writeFile as writeFile6
|
|
10405
10804
|
} from "node:fs/promises";
|
|
10406
|
-
import { tmpdir as
|
|
10407
|
-
import { join as
|
|
10805
|
+
import { tmpdir as tmpdir5 } from "node:os";
|
|
10806
|
+
import { join as join10 } from "node:path";
|
|
10408
10807
|
|
|
10409
10808
|
// src/runs/git-checkpoint.ts
|
|
10410
10809
|
import { execFile as execFile2 } from "node:child_process";
|
|
10411
|
-
import { copyFile, mkdtemp as
|
|
10412
|
-
import { tmpdir as
|
|
10413
|
-
import { join as
|
|
10810
|
+
import { copyFile, mkdtemp as mkdtemp3, rm as rm6 } from "node:fs/promises";
|
|
10811
|
+
import { tmpdir as tmpdir3 } from "node:os";
|
|
10812
|
+
import { join as join8 } from "node:path";
|
|
10414
10813
|
import { promisify as promisify2 } from "node:util";
|
|
10415
10814
|
var execFileAsync = promisify2(execFile2);
|
|
10416
10815
|
async function git2(cwd, args, env) {
|
|
@@ -10525,12 +10924,12 @@ async function captureGitCheckpoint(cwd, runId, kind) {
|
|
|
10525
10924
|
const manifest = await optionalGit(cwd, ["status", "--porcelain=v2", "-z"]);
|
|
10526
10925
|
const staged = await optionalGit(cwd, ["diff", "--cached", "--stat", "HEAD"]);
|
|
10527
10926
|
const unstaged = await optionalGit(cwd, ["diff", "--stat", "HEAD"]);
|
|
10528
|
-
const directory = await
|
|
10927
|
+
const directory = await mkdtemp3(join8(tmpdir3(), "aide-run-index-"));
|
|
10529
10928
|
let worktreeTree = null;
|
|
10530
10929
|
let refName = null;
|
|
10531
10930
|
try {
|
|
10532
10931
|
const actualIndex = await git2(cwd, ["rev-parse", "--git-path", "index"]);
|
|
10533
|
-
const temporaryIndex =
|
|
10932
|
+
const temporaryIndex = join8(directory, "index");
|
|
10534
10933
|
try {
|
|
10535
10934
|
await copyFile(actualIndex, temporaryIndex);
|
|
10536
10935
|
} catch {
|
|
@@ -10562,7 +10961,7 @@ async function captureGitCheckpoint(cwd, runId, kind) {
|
|
|
10562
10961
|
refName = `refs/aide/runs/${runId}/${Date.now()}-${kind.toLowerCase()}`;
|
|
10563
10962
|
await git2(cwd, ["update-ref", refName, checkpointCommit]);
|
|
10564
10963
|
} finally {
|
|
10565
|
-
await
|
|
10964
|
+
await rm6(directory, { recursive: true, force: true });
|
|
10566
10965
|
}
|
|
10567
10966
|
return {
|
|
10568
10967
|
kind,
|
|
@@ -10591,36 +10990,37 @@ import { createHash as createHash5, randomUUID as randomUUID3 } from "node:crypt
|
|
|
10591
10990
|
import {
|
|
10592
10991
|
cp,
|
|
10593
10992
|
mkdir as mkdir4,
|
|
10594
|
-
mkdtemp as
|
|
10993
|
+
mkdtemp as mkdtemp4,
|
|
10595
10994
|
open,
|
|
10596
10995
|
readdir as readdir6,
|
|
10597
10996
|
readFile as readFile5,
|
|
10598
|
-
realpath as
|
|
10997
|
+
realpath as realpath5,
|
|
10599
10998
|
rename as rename3,
|
|
10600
|
-
rm as
|
|
10601
|
-
stat as
|
|
10602
|
-
writeFile as
|
|
10999
|
+
rm as rm7,
|
|
11000
|
+
stat as stat7,
|
|
11001
|
+
writeFile as writeFile5
|
|
10603
11002
|
} from "node:fs/promises";
|
|
10604
11003
|
import { createReadStream as createReadStream3, createWriteStream } from "node:fs";
|
|
10605
|
-
import { tmpdir as
|
|
11004
|
+
import { tmpdir as tmpdir4 } from "node:os";
|
|
10606
11005
|
import { pipeline } from "node:stream/promises";
|
|
11006
|
+
import { StringDecoder } from "node:string_decoder";
|
|
10607
11007
|
import {
|
|
10608
11008
|
basename as basename3,
|
|
10609
11009
|
dirname as dirname5,
|
|
10610
11010
|
isAbsolute as isAbsolute4,
|
|
10611
|
-
join as
|
|
11011
|
+
join as join9,
|
|
10612
11012
|
relative as relative4,
|
|
10613
11013
|
resolve as resolve5,
|
|
10614
11014
|
sep as sep4
|
|
10615
11015
|
} from "node:path";
|
|
10616
|
-
import { spawn as
|
|
11016
|
+
import { spawn as spawn5 } from "node:child_process";
|
|
10617
11017
|
|
|
10618
11018
|
// src/git-code-state.ts
|
|
10619
11019
|
import { createHash as createHash4 } from "node:crypto";
|
|
10620
11020
|
import { createReadStream as createReadStream2 } from "node:fs";
|
|
10621
11021
|
import { lstat as lstat3, readlink } from "node:fs/promises";
|
|
10622
11022
|
import { isAbsolute as isAbsolute3, relative as relative3, resolve as resolve4, sep as sep3 } from "node:path";
|
|
10623
|
-
import { spawn as
|
|
11023
|
+
import { spawn as spawn4 } from "node:child_process";
|
|
10624
11024
|
function gitEnvironment() {
|
|
10625
11025
|
return {
|
|
10626
11026
|
...process.env,
|
|
@@ -10643,7 +11043,7 @@ function hashGitDiff(hash, folder, timeoutMs, signal) {
|
|
|
10643
11043
|
return new Promise((resolveResult, reject) => {
|
|
10644
11044
|
let settled = false;
|
|
10645
11045
|
let timedOut = false;
|
|
10646
|
-
const child =
|
|
11046
|
+
const child = spawn4(
|
|
10647
11047
|
"git",
|
|
10648
11048
|
[
|
|
10649
11049
|
"-C",
|
|
@@ -10862,8 +11262,8 @@ function requireSuccess2(result, fallback) {
|
|
|
10862
11262
|
return result;
|
|
10863
11263
|
}
|
|
10864
11264
|
async function validateWorktree(input, timeoutMs, signal) {
|
|
10865
|
-
const folder = await
|
|
10866
|
-
if (!(await
|
|
11265
|
+
const folder = await realpath5(input.folder);
|
|
11266
|
+
if (!(await stat7(folder)).isDirectory())
|
|
10867
11267
|
throw new Error("Worktree is missing");
|
|
10868
11268
|
const gitDirectory2 = requireSuccess2(
|
|
10869
11269
|
await command(
|
|
@@ -10876,7 +11276,7 @@ async function validateWorktree(input, timeoutMs, signal) {
|
|
|
10876
11276
|
),
|
|
10877
11277
|
"Could not resolve the worktree Git directory"
|
|
10878
11278
|
).stdout.trim();
|
|
10879
|
-
if (await
|
|
11279
|
+
if (await realpath5(gitDirectory2) !== input.gitDirectory) {
|
|
10880
11280
|
throw new Error("Worktree identity changed; refresh the page");
|
|
10881
11281
|
}
|
|
10882
11282
|
const origin2 = requireSuccess2(
|
|
@@ -10905,12 +11305,12 @@ function containedPath2(root, relativePath) {
|
|
|
10905
11305
|
}
|
|
10906
11306
|
async function validateSource(root, source) {
|
|
10907
11307
|
const target2 = containedPath2(root, source.relativePath);
|
|
10908
|
-
const resolved = await
|
|
11308
|
+
const resolved = await realpath5(target2);
|
|
10909
11309
|
const difference = relative4(root, resolved);
|
|
10910
11310
|
if (difference === ".." || difference.startsWith(`..${sep4}`) || isAbsolute4(difference)) {
|
|
10911
11311
|
throw new Error("Build source resolves outside the worktree");
|
|
10912
11312
|
}
|
|
10913
|
-
const information = await
|
|
11313
|
+
const information = await stat7(resolved);
|
|
10914
11314
|
if (source.kind === "PACKAGE" && !information.isFile()) {
|
|
10915
11315
|
throw new Error("Package.swift is missing");
|
|
10916
11316
|
}
|
|
@@ -10926,7 +11326,7 @@ async function discoverSourcesInFolder(folder) {
|
|
|
10926
11326
|
const current = queue.shift();
|
|
10927
11327
|
for (const entry of await readdir6(current, { withFileTypes: true })) {
|
|
10928
11328
|
if (entry.isSymbolicLink()) continue;
|
|
10929
|
-
const absolute =
|
|
11329
|
+
const absolute = join9(current, entry.name);
|
|
10930
11330
|
const path = relative4(folder, absolute).split(sep4).join("/");
|
|
10931
11331
|
if (entry.isDirectory()) {
|
|
10932
11332
|
if (entry.name.endsWith(".xcodeproj")) {
|
|
@@ -10997,7 +11397,7 @@ function metadataFromList(value) {
|
|
|
10997
11397
|
};
|
|
10998
11398
|
}
|
|
10999
11399
|
async function workspaceProjectPaths(workspacePath2, folder) {
|
|
11000
|
-
const contentsPath =
|
|
11400
|
+
const contentsPath = join9(workspacePath2, "contents.xcworkspacedata");
|
|
11001
11401
|
let contents;
|
|
11002
11402
|
try {
|
|
11003
11403
|
contents = await readFile5(contentsPath, "utf8");
|
|
@@ -11024,9 +11424,9 @@ async function workspaceProjectPaths(workspacePath2, folder) {
|
|
|
11024
11424
|
continue;
|
|
11025
11425
|
}
|
|
11026
11426
|
try {
|
|
11027
|
-
const resolved = await
|
|
11427
|
+
const resolved = await realpath5(candidate);
|
|
11028
11428
|
const resolvedDifference = relative4(folder, resolved);
|
|
11029
|
-
if (resolvedDifference === ".." || resolvedDifference.startsWith(`..${sep4}`) || isAbsolute4(resolvedDifference) || !(await
|
|
11429
|
+
if (resolvedDifference === ".." || resolvedDifference.startsWith(`..${sep4}`) || isAbsolute4(resolvedDifference) || !(await stat7(resolved)).isDirectory()) {
|
|
11030
11430
|
continue;
|
|
11031
11431
|
}
|
|
11032
11432
|
projects.push(resolved);
|
|
@@ -11217,7 +11617,7 @@ async function dependentSigningRequirements(source, absolutePath, folder, rootTa
|
|
|
11217
11617
|
for (const project of projects.slice(0, 50)) {
|
|
11218
11618
|
const converted = await command(
|
|
11219
11619
|
"plutil",
|
|
11220
|
-
["-convert", "json", "-o", "-",
|
|
11620
|
+
["-convert", "json", "-o", "-", join9(project, "project.pbxproj")],
|
|
11221
11621
|
Math.min(timeoutMs, 15e3),
|
|
11222
11622
|
signal,
|
|
11223
11623
|
folder
|
|
@@ -11454,8 +11854,8 @@ function genericBuildDestinations(action) {
|
|
|
11454
11854
|
];
|
|
11455
11855
|
}
|
|
11456
11856
|
async function listPhysicalDevices(timeoutMs, signal) {
|
|
11457
|
-
const directory = await
|
|
11458
|
-
const output =
|
|
11857
|
+
const directory = await mkdtemp4(join9(tmpdir4(), "ade-devices-"));
|
|
11858
|
+
const output = join9(directory, "devices.json");
|
|
11459
11859
|
try {
|
|
11460
11860
|
const result = await command(
|
|
11461
11861
|
"xcrun",
|
|
@@ -11475,7 +11875,7 @@ async function listPhysicalDevices(timeoutMs, signal) {
|
|
|
11475
11875
|
if (result.exitCode !== 0) return [];
|
|
11476
11876
|
return physicalDestinations(JSON.parse(await readFile5(output, "utf8")));
|
|
11477
11877
|
} finally {
|
|
11478
|
-
await
|
|
11878
|
+
await rm7(directory, { recursive: true, force: true });
|
|
11479
11879
|
}
|
|
11480
11880
|
}
|
|
11481
11881
|
var inspectBuildDestinations = async (payload, timeoutMs, signal) => {
|
|
@@ -11562,7 +11962,7 @@ function createRedactor(env) {
|
|
|
11562
11962
|
);
|
|
11563
11963
|
};
|
|
11564
11964
|
}
|
|
11565
|
-
var BuildLogger = class {
|
|
11965
|
+
var BuildLogger = class _BuildLogger {
|
|
11566
11966
|
constructor(buildId, context, rawLogPath, env) {
|
|
11567
11967
|
this.buildId = buildId;
|
|
11568
11968
|
this.context = context;
|
|
@@ -11571,51 +11971,67 @@ var BuildLogger = class {
|
|
|
11571
11971
|
}
|
|
11572
11972
|
buildId;
|
|
11573
11973
|
context;
|
|
11974
|
+
static MAX_CHUNK_BYTES = 128 * 1024;
|
|
11975
|
+
static MAX_BATCH_BYTES = 128 * 1024;
|
|
11574
11976
|
stream;
|
|
11575
11977
|
redact;
|
|
11576
11978
|
sequence = 0;
|
|
11577
11979
|
pending = [];
|
|
11980
|
+
pendingBytes = 0;
|
|
11578
11981
|
flushChain = Promise.resolve();
|
|
11579
11982
|
timer = null;
|
|
11580
11983
|
closePromise = null;
|
|
11581
11984
|
redactingPrivateKey = false;
|
|
11582
11985
|
emit(phase, stream, message, scope = "BUILD", scopeId = this.buildId, extraStream) {
|
|
11986
|
+
this.write(phase, stream, `${message}\r
|
|
11987
|
+
`, scope, scopeId, extraStream);
|
|
11988
|
+
}
|
|
11989
|
+
write(phase, stream, output, scope = "BUILD", scopeId = this.buildId, extraStream) {
|
|
11990
|
+
const ending = output.match(/(?:\r\n|\r|\n)$/)?.[0] ?? "";
|
|
11991
|
+
const message = ending ? output.slice(0, -ending.length) : output;
|
|
11583
11992
|
const startsPrivateKey = /-----BEGIN [^-]*PRIVATE KEY-----/i.test(message);
|
|
11584
11993
|
const endsPrivateKey = /-----END [^-]*PRIVATE KEY-----/i.test(message);
|
|
11585
11994
|
if (startsPrivateKey) this.redactingPrivateKey = true;
|
|
11586
11995
|
const sanitized = this.redactingPrivateKey ? "[REDACTED PRIVATE KEY]" : this.redact(message);
|
|
11587
11996
|
if (endsPrivateKey) this.redactingPrivateKey = false;
|
|
11588
11997
|
const createdAt = (/* @__PURE__ */ new Date()).toISOString();
|
|
11589
|
-
const
|
|
11590
|
-
`;
|
|
11998
|
+
const terminalOutput = `${sanitized}${ending}`;
|
|
11999
|
+
const line = `[${createdAt}] [${phase}] [${stream}] ${sanitized}${ending || "\n"}`;
|
|
11591
12000
|
this.stream.write(line);
|
|
11592
12001
|
extraStream?.write(line);
|
|
11593
|
-
|
|
11594
|
-
|
|
11595
|
-
|
|
11596
|
-
|
|
11597
|
-
|
|
11598
|
-
|
|
11599
|
-
|
|
11600
|
-
|
|
11601
|
-
|
|
11602
|
-
|
|
11603
|
-
|
|
11604
|
-
|
|
11605
|
-
this.
|
|
12002
|
+
for (const data of splitUtf8(terminalOutput, _BuildLogger.MAX_CHUNK_BYTES)) {
|
|
12003
|
+
const bytes = Buffer.from(data, "utf8");
|
|
12004
|
+
this.pending.push({
|
|
12005
|
+
scope,
|
|
12006
|
+
scopeId,
|
|
12007
|
+
sequence: this.sequence++,
|
|
12008
|
+
phase,
|
|
12009
|
+
stream,
|
|
12010
|
+
dataBase64: bytes.toString("base64"),
|
|
12011
|
+
byteLength: bytes.byteLength,
|
|
12012
|
+
createdAt
|
|
12013
|
+
});
|
|
12014
|
+
this.pendingBytes += bytes.byteLength;
|
|
12015
|
+
if (this.pending.length >= 200 || this.pendingBytes >= _BuildLogger.MAX_BATCH_BYTES) {
|
|
12016
|
+
this.flush();
|
|
12017
|
+
}
|
|
12018
|
+
}
|
|
12019
|
+
if (this.pending.length && !this.timer) {
|
|
12020
|
+
this.timer = setTimeout(() => this.flush(), 25);
|
|
11606
12021
|
this.timer.unref();
|
|
11607
12022
|
}
|
|
11608
12023
|
}
|
|
11609
12024
|
flush() {
|
|
11610
12025
|
if (this.timer) clearTimeout(this.timer);
|
|
11611
12026
|
this.timer = null;
|
|
11612
|
-
const
|
|
11613
|
-
|
|
12027
|
+
const chunks = this.pending.splice(0);
|
|
12028
|
+
this.pendingBytes = 0;
|
|
12029
|
+
if (!chunks.length || !this.context?.appendBuildLogChunks) return;
|
|
11614
12030
|
this.flushChain = this.flushChain.then(async () => {
|
|
11615
12031
|
try {
|
|
11616
|
-
await this.context.
|
|
12032
|
+
await this.context.appendBuildLogChunks(this.buildId, chunks);
|
|
11617
12033
|
} catch (error) {
|
|
11618
|
-
console.error("Could not append build
|
|
12034
|
+
console.error("Could not append build log chunks:", cleanError2(error));
|
|
11619
12035
|
}
|
|
11620
12036
|
});
|
|
11621
12037
|
}
|
|
@@ -11628,6 +12044,24 @@ var BuildLogger = class {
|
|
|
11628
12044
|
return this.closePromise;
|
|
11629
12045
|
}
|
|
11630
12046
|
};
|
|
12047
|
+
function splitUtf8(value, maximumBytes) {
|
|
12048
|
+
if (!value) return [];
|
|
12049
|
+
const parts = [];
|
|
12050
|
+
let part = "";
|
|
12051
|
+
let byteLength = 0;
|
|
12052
|
+
for (const character of value) {
|
|
12053
|
+
const characterBytes = Buffer.byteLength(character, "utf8");
|
|
12054
|
+
if (part && byteLength + characterBytes > maximumBytes) {
|
|
12055
|
+
parts.push(part);
|
|
12056
|
+
part = "";
|
|
12057
|
+
byteLength = 0;
|
|
12058
|
+
}
|
|
12059
|
+
part += character;
|
|
12060
|
+
byteLength += characterBytes;
|
|
12061
|
+
}
|
|
12062
|
+
if (part) parts.push(part);
|
|
12063
|
+
return parts;
|
|
12064
|
+
}
|
|
11631
12065
|
function terminateProcess(child) {
|
|
11632
12066
|
if (child.exitCode !== null || child.killed) return null;
|
|
11633
12067
|
try {
|
|
@@ -11661,9 +12095,15 @@ function runLoggedCommand(options) {
|
|
|
11661
12095
|
mode: 384
|
|
11662
12096
|
});
|
|
11663
12097
|
}
|
|
11664
|
-
const child =
|
|
12098
|
+
const child = spawn5(options.command, options.args, {
|
|
11665
12099
|
cwd: options.cwd,
|
|
11666
|
-
env:
|
|
12100
|
+
env: {
|
|
12101
|
+
...options.env,
|
|
12102
|
+
TERM: "xterm-256color",
|
|
12103
|
+
COLORTERM: "truecolor",
|
|
12104
|
+
FORCE_COLOR: "1",
|
|
12105
|
+
CLICOLOR_FORCE: "1"
|
|
12106
|
+
},
|
|
11667
12107
|
shell: false,
|
|
11668
12108
|
detached: true,
|
|
11669
12109
|
stdio: ["ignore", "pipe", "pipe"]
|
|
@@ -11677,36 +12117,36 @@ function runLoggedCommand(options) {
|
|
|
11677
12117
|
extraStream
|
|
11678
12118
|
);
|
|
11679
12119
|
const attach = (stream, kind) => {
|
|
12120
|
+
const decoder = new StringDecoder("utf8");
|
|
11680
12121
|
let remainder = "";
|
|
11681
|
-
|
|
11682
|
-
|
|
11683
|
-
|
|
11684
|
-
|
|
11685
|
-
|
|
11686
|
-
|
|
11687
|
-
|
|
11688
|
-
|
|
12122
|
+
const drain = (final = false) => {
|
|
12123
|
+
while (remainder) {
|
|
12124
|
+
const delimiter = remainder.search(/[\r\n]/);
|
|
12125
|
+
if (delimiter < 0 && !final) return;
|
|
12126
|
+
let end = delimiter < 0 ? remainder.length : delimiter + 1;
|
|
12127
|
+
if (remainder[delimiter] === "\r" && remainder[delimiter + 1] === "\n") {
|
|
12128
|
+
end += 1;
|
|
12129
|
+
}
|
|
12130
|
+
const record = remainder.slice(0, end);
|
|
12131
|
+
remainder = remainder.slice(end);
|
|
12132
|
+
output = `${output}${record}`.slice(-64e3);
|
|
12133
|
+
options.logger.write(
|
|
11689
12134
|
options.phase,
|
|
11690
12135
|
kind,
|
|
11691
|
-
|
|
12136
|
+
record,
|
|
11692
12137
|
options.scope,
|
|
11693
12138
|
options.scopeId,
|
|
11694
12139
|
extraStream
|
|
11695
12140
|
);
|
|
11696
12141
|
}
|
|
12142
|
+
};
|
|
12143
|
+
stream.on("data", (chunk) => {
|
|
12144
|
+
remainder += decoder.write(chunk);
|
|
12145
|
+
drain();
|
|
11697
12146
|
});
|
|
11698
12147
|
stream.on("end", () => {
|
|
11699
|
-
|
|
11700
|
-
|
|
11701
|
-
options.logger.emit(
|
|
11702
|
-
options.phase,
|
|
11703
|
-
kind,
|
|
11704
|
-
remainder,
|
|
11705
|
-
options.scope,
|
|
11706
|
-
options.scopeId,
|
|
11707
|
-
extraStream
|
|
11708
|
-
);
|
|
11709
|
-
}
|
|
12148
|
+
remainder += decoder.end();
|
|
12149
|
+
drain(true);
|
|
11710
12150
|
});
|
|
11711
12151
|
};
|
|
11712
12152
|
attach(child.stdout, "STDOUT");
|
|
@@ -11853,7 +12293,7 @@ function actionArgument(action) {
|
|
|
11853
12293
|
}[action];
|
|
11854
12294
|
}
|
|
11855
12295
|
function xcodeBuildArguments(input) {
|
|
11856
|
-
const resultBundle =
|
|
12296
|
+
const resultBundle = join9(input.artifactDirectory, "result.xcresult");
|
|
11857
12297
|
const sourcePath = containedPath2(input.folder, input.source.relativePath);
|
|
11858
12298
|
const usesCapturedTestProducts = input.action === "TEST_WITHOUT_BUILDING";
|
|
11859
12299
|
const args = [
|
|
@@ -11875,13 +12315,13 @@ function xcodeBuildArguments(input) {
|
|
|
11875
12315
|
if (input.action === "ARCHIVE") {
|
|
11876
12316
|
args.push(
|
|
11877
12317
|
"-archivePath",
|
|
11878
|
-
|
|
12318
|
+
join9(input.artifactDirectory, "archive.xcarchive")
|
|
11879
12319
|
);
|
|
11880
12320
|
}
|
|
11881
12321
|
if (input.action === "BUILD_FOR_TESTING") {
|
|
11882
12322
|
args.push(
|
|
11883
12323
|
"-testProductsPath",
|
|
11884
|
-
|
|
12324
|
+
join9(input.artifactDirectory, "test-products.xctestproducts")
|
|
11885
12325
|
);
|
|
11886
12326
|
}
|
|
11887
12327
|
if (input.action === "TEST_WITHOUT_BUILDING" && input.advancedSettings.priorTestProductsPath) {
|
|
@@ -11944,27 +12384,27 @@ function classifyFailure(output) {
|
|
|
11944
12384
|
}
|
|
11945
12385
|
async function runHook(options) {
|
|
11946
12386
|
const phaseDirectory = options.phase === "PRE_BUILD" ? "pre" : "post";
|
|
11947
|
-
const directory =
|
|
12387
|
+
const directory = join9(
|
|
11948
12388
|
options.input.artifactDirectory,
|
|
11949
12389
|
"hooks",
|
|
11950
12390
|
phaseDirectory
|
|
11951
12391
|
);
|
|
11952
12392
|
const prefix = `${String(options.script.position).padStart(3, "0")}-${options.script.id}`;
|
|
11953
|
-
const file =
|
|
11954
|
-
const runner =
|
|
11955
|
-
const log =
|
|
12393
|
+
const file = join9(directory, `${prefix}.mjs`);
|
|
12394
|
+
const runner = join9(directory, `${prefix}.runner.mjs`);
|
|
12395
|
+
const log = join9(directory, `${prefix}.log`);
|
|
11956
12396
|
const started = Date.now();
|
|
11957
12397
|
try {
|
|
11958
12398
|
await mkdir4(directory, { recursive: true, mode: 448 });
|
|
11959
|
-
await
|
|
12399
|
+
await writeFile5(file, `${options.source}
|
|
11960
12400
|
`, { mode: 384 });
|
|
11961
|
-
await
|
|
12401
|
+
await writeFile5(
|
|
11962
12402
|
options.contextPath,
|
|
11963
12403
|
`${JSON.stringify(options.hookContext, null, 2)}
|
|
11964
12404
|
`,
|
|
11965
12405
|
{ mode: 384 }
|
|
11966
12406
|
);
|
|
11967
|
-
await
|
|
12407
|
+
await writeFile5(
|
|
11968
12408
|
runner,
|
|
11969
12409
|
`import { readFile } from "node:fs/promises";
|
|
11970
12410
|
const hookModule = await import(${JSON.stringify(`./${basename3(file)}`)});
|
|
@@ -12037,26 +12477,26 @@ if (typeof hookModule.default === "function") {
|
|
|
12037
12477
|
}
|
|
12038
12478
|
async function pathExists(path) {
|
|
12039
12479
|
try {
|
|
12040
|
-
await
|
|
12480
|
+
await stat7(path);
|
|
12041
12481
|
return true;
|
|
12042
12482
|
} catch {
|
|
12043
12483
|
return false;
|
|
12044
12484
|
}
|
|
12045
12485
|
}
|
|
12046
12486
|
async function pathSize(path) {
|
|
12047
|
-
const information = await
|
|
12487
|
+
const information = await stat7(path);
|
|
12048
12488
|
if (information.isFile()) return information.size;
|
|
12049
12489
|
if (!information.isDirectory()) return 0;
|
|
12050
12490
|
let size = 0;
|
|
12051
12491
|
for (const entry of await readdir6(path, { withFileTypes: true })) {
|
|
12052
12492
|
if (entry.isSymbolicLink()) continue;
|
|
12053
|
-
size += await pathSize(
|
|
12493
|
+
size += await pathSize(join9(path, entry.name));
|
|
12054
12494
|
}
|
|
12055
12495
|
return size;
|
|
12056
12496
|
}
|
|
12057
12497
|
async function fileChecksum(path) {
|
|
12058
12498
|
try {
|
|
12059
|
-
const information = await
|
|
12499
|
+
const information = await stat7(path);
|
|
12060
12500
|
if (!information.isFile()) return null;
|
|
12061
12501
|
const hash = createHash5("sha256");
|
|
12062
12502
|
await pipeline(createReadStream3(path), hash);
|
|
@@ -12080,7 +12520,7 @@ async function plistString(plistPath, keyPath, timeoutMs, signal) {
|
|
|
12080
12520
|
}
|
|
12081
12521
|
}
|
|
12082
12522
|
async function archiveApplicationProperties(archivePath, timeoutMs, signal) {
|
|
12083
|
-
const plistPath =
|
|
12523
|
+
const plistPath = join9(archivePath, "Info.plist");
|
|
12084
12524
|
const read = (key) => plistString(plistPath, `ApplicationProperties.${key}`, timeoutMs, signal);
|
|
12085
12525
|
const [bundleIdentifier2, bundleShortVersion, bundleVersion, applicationPath] = await Promise.all([
|
|
12086
12526
|
read("CFBundleIdentifier"),
|
|
@@ -12239,9 +12679,9 @@ function normalizeCoverage(value) {
|
|
|
12239
12679
|
};
|
|
12240
12680
|
}
|
|
12241
12681
|
async function writeJsonReport(input, kind, timeoutMs, signal) {
|
|
12242
|
-
const resultBundle =
|
|
12682
|
+
const resultBundle = join9(input.artifactDirectory, "result.xcresult");
|
|
12243
12683
|
const filename = kind === "TEST_RESULTS" ? "test-results.json" : "code-coverage.json";
|
|
12244
|
-
const destination =
|
|
12684
|
+
const destination = join9(input.artifactDirectory, filename);
|
|
12245
12685
|
const temporary = `${destination}.tmp-${randomUUID3()}`;
|
|
12246
12686
|
try {
|
|
12247
12687
|
if (!await pathExists(resultBundle)) {
|
|
@@ -12285,7 +12725,7 @@ async function writeJsonReport(input, kind, timeoutMs, signal) {
|
|
|
12285
12725
|
error: null
|
|
12286
12726
|
};
|
|
12287
12727
|
} catch (error) {
|
|
12288
|
-
await
|
|
12728
|
+
await rm7(temporary, { force: true });
|
|
12289
12729
|
return {
|
|
12290
12730
|
kind,
|
|
12291
12731
|
status: "FAILED",
|
|
@@ -12376,7 +12816,7 @@ async function snapshotCoverageChanges(input, folder, timeoutMs, signal) {
|
|
|
12376
12816
|
const types = changeTypesFromStatus(status2.stdout);
|
|
12377
12817
|
for (const path of untracked.stdout.split("\0").filter(Boolean)) {
|
|
12378
12818
|
try {
|
|
12379
|
-
const contents = await readFile5(
|
|
12819
|
+
const contents = await readFile5(join9(folder, path));
|
|
12380
12820
|
if (contents.includes(0)) continue;
|
|
12381
12821
|
const lineCount = contents.length ? contents.toString("utf8").split("\n").length - (contents.toString("utf8").endsWith("\n") ? 1 : 0) : 0;
|
|
12382
12822
|
lines.set(
|
|
@@ -12410,7 +12850,7 @@ async function addChangedCoverage(report, changes, input, folder, timeoutMs, sig
|
|
|
12410
12850
|
let covered = 0;
|
|
12411
12851
|
let executable = 0;
|
|
12412
12852
|
if (coveragePath && change.lines.length) {
|
|
12413
|
-
const temporary2 =
|
|
12853
|
+
const temporary2 = join9(
|
|
12414
12854
|
input.artifactDirectory,
|
|
12415
12855
|
`.changed-coverage-${randomUUID3()}.json`
|
|
12416
12856
|
);
|
|
@@ -12451,7 +12891,7 @@ async function addChangedCoverage(report, changes, input, folder, timeoutMs, sig
|
|
|
12451
12891
|
}
|
|
12452
12892
|
}
|
|
12453
12893
|
} finally {
|
|
12454
|
-
await
|
|
12894
|
+
await rm7(temporary2, { force: true });
|
|
12455
12895
|
}
|
|
12456
12896
|
}
|
|
12457
12897
|
changedCoveredLines += covered;
|
|
@@ -12471,9 +12911,9 @@ async function addChangedCoverage(report, changes, input, folder, timeoutMs, sig
|
|
|
12471
12911
|
changedLineCoverage: changedExecutableLines ? changedCoveredLines / changedExecutableLines : null
|
|
12472
12912
|
};
|
|
12473
12913
|
const data = { ...report.data, changedFiles };
|
|
12474
|
-
const destination =
|
|
12914
|
+
const destination = join9(input.artifactDirectory, "worktree-coverage.json");
|
|
12475
12915
|
const temporary = `${destination}.tmp-${randomUUID3()}`;
|
|
12476
|
-
await
|
|
12916
|
+
await writeFile5(temporary, JSON.stringify({ summary, data }, null, 2), {
|
|
12477
12917
|
mode: 384
|
|
12478
12918
|
});
|
|
12479
12919
|
await rename3(temporary, destination);
|
|
@@ -12525,7 +12965,7 @@ async function findFiles(root, predicate, limit = 20) {
|
|
|
12525
12965
|
}
|
|
12526
12966
|
for (const entry of entries) {
|
|
12527
12967
|
if (entry.isSymbolicLink()) continue;
|
|
12528
|
-
const path =
|
|
12968
|
+
const path = join9(current, entry.name);
|
|
12529
12969
|
if (entry.isDirectory()) queue.push(path);
|
|
12530
12970
|
else if (entry.isFile() && predicate(entry.name)) results.push(path);
|
|
12531
12971
|
if (results.length >= limit) break;
|
|
@@ -12535,7 +12975,7 @@ async function findFiles(root, predicate, limit = 20) {
|
|
|
12535
12975
|
}
|
|
12536
12976
|
async function captureArtifacts(input, folder, signal, includeProducts = true) {
|
|
12537
12977
|
const artifacts = [];
|
|
12538
|
-
const resultBundle =
|
|
12978
|
+
const resultBundle = join9(input.artifactDirectory, "result.xcresult");
|
|
12539
12979
|
if (await pathExists(resultBundle)) {
|
|
12540
12980
|
const coverageProbe = await command(
|
|
12541
12981
|
"xcrun",
|
|
@@ -12562,7 +13002,7 @@ async function captureArtifacts(input, folder, signal, includeProducts = true) {
|
|
|
12562
13002
|
);
|
|
12563
13003
|
}
|
|
12564
13004
|
if (!includeProducts) return artifacts;
|
|
12565
|
-
const archivePath =
|
|
13005
|
+
const archivePath = join9(input.artifactDirectory, "archive.xcarchive");
|
|
12566
13006
|
if (await pathExists(archivePath)) {
|
|
12567
13007
|
artifacts.push(
|
|
12568
13008
|
await artifact(input.artifactDirectory, "ARCHIVE", archivePath)
|
|
@@ -12585,12 +13025,12 @@ async function captureArtifacts(input, folder, signal, includeProducts = true) {
|
|
|
12585
13025
|
if (apps.length === 1) {
|
|
12586
13026
|
const settings = apps[0].buildSettings;
|
|
12587
13027
|
const productName = settings.FULL_PRODUCT_NAME ?? settings.WRAPPER_NAME;
|
|
12588
|
-
const source = settings.TARGET_BUILD_DIR && productName ?
|
|
13028
|
+
const source = settings.TARGET_BUILD_DIR && productName ? join9(settings.TARGET_BUILD_DIR, productName) : null;
|
|
12589
13029
|
if (source && await pathExists(source)) {
|
|
12590
|
-
const productDirectory =
|
|
12591
|
-
const destination =
|
|
13030
|
+
const productDirectory = join9(input.artifactDirectory, "products");
|
|
13031
|
+
const destination = join9(productDirectory, basename3(source));
|
|
12592
13032
|
await mkdir4(productDirectory, { recursive: true, mode: 448 });
|
|
12593
|
-
await
|
|
13033
|
+
await rm7(destination, { recursive: true, force: true });
|
|
12594
13034
|
await cp(source, destination, {
|
|
12595
13035
|
recursive: true,
|
|
12596
13036
|
preserveTimestamps: true
|
|
@@ -12605,7 +13045,7 @@ async function captureArtifacts(input, folder, signal, includeProducts = true) {
|
|
|
12605
13045
|
}
|
|
12606
13046
|
}
|
|
12607
13047
|
if (input.action === "BUILD_FOR_TESTING") {
|
|
12608
|
-
const testDirectory =
|
|
13048
|
+
const testDirectory = join9(
|
|
12609
13049
|
input.artifactDirectory,
|
|
12610
13050
|
"test-products.xctestproducts"
|
|
12611
13051
|
);
|
|
@@ -12640,10 +13080,10 @@ var runIosBuild = async (payload, timeoutMs, signal, onLog, context) => {
|
|
|
12640
13080
|
const testProductsPath = input.advancedSettings.priorTestProductsPath;
|
|
12641
13081
|
const xctestrunPath = input.advancedSettings.priorXctestrunPath;
|
|
12642
13082
|
if (testProductsPath) {
|
|
12643
|
-
if (!testProductsPath.endsWith(".xctestproducts") || !await pathExists(testProductsPath) || !(await
|
|
13083
|
+
if (!testProductsPath.endsWith(".xctestproducts") || !await pathExists(testProductsPath) || !(await stat7(testProductsPath)).isDirectory()) {
|
|
12644
13084
|
throw new Error("The captured test-products artifact is unavailable");
|
|
12645
13085
|
}
|
|
12646
|
-
} else if (!xctestrunPath?.endsWith(".xctestrun") || !await pathExists(xctestrunPath) || !(await
|
|
13086
|
+
} else if (!xctestrunPath?.endsWith(".xctestrun") || !await pathExists(xctestrunPath) || !(await stat7(xctestrunPath)).isFile()) {
|
|
12647
13087
|
throw new Error("The captured .xctestrun artifact is unavailable");
|
|
12648
13088
|
}
|
|
12649
13089
|
}
|
|
@@ -12656,11 +13096,11 @@ var runIosBuild = async (payload, timeoutMs, signal, onLog, context) => {
|
|
|
12656
13096
|
signal
|
|
12657
13097
|
);
|
|
12658
13098
|
await mkdir4(input.artifactDirectory, { recursive: true, mode: 448 });
|
|
12659
|
-
const rawLog =
|
|
13099
|
+
const rawLog = join9(input.artifactDirectory, "build.log");
|
|
12660
13100
|
const logger = new BuildLogger(input.buildId, context, rawLog, process.env);
|
|
12661
13101
|
try {
|
|
12662
13102
|
const scriptExecutions = [];
|
|
12663
|
-
const contextPath =
|
|
13103
|
+
const contextPath = join9(input.artifactDirectory, "context.json");
|
|
12664
13104
|
const baseHookContext = {
|
|
12665
13105
|
buildId: input.buildId,
|
|
12666
13106
|
branch: input.branch ?? null,
|
|
@@ -12919,7 +13359,7 @@ var generateIosBuildReport = async (payload, timeoutMs, signal, onLog) => {
|
|
|
12919
13359
|
var deleteIosBuild = async (payload, _timeoutMs, signal, onLog) => {
|
|
12920
13360
|
const input = parseBuildDeletePayload(payload);
|
|
12921
13361
|
if (signal.aborted) return { ...successfulProcess6, cancelled: true };
|
|
12922
|
-
await
|
|
13362
|
+
await rm7(input.artifactDirectory, { recursive: true, force: true });
|
|
12923
13363
|
await onLog({
|
|
12924
13364
|
sequence: 0,
|
|
12925
13365
|
stream: "SYSTEM",
|
|
@@ -12933,23 +13373,23 @@ var downloadIosBuildArtifact = async (payload, timeoutMs, signal, onLog, context
|
|
|
12933
13373
|
if (!context?.uploadBuildArtifact) {
|
|
12934
13374
|
throw new Error("This agent cannot upload build artifacts");
|
|
12935
13375
|
}
|
|
12936
|
-
const root = await
|
|
12937
|
-
const target2 = await
|
|
13376
|
+
const root = await realpath5(input.artifactDirectory);
|
|
13377
|
+
const target2 = await realpath5(
|
|
12938
13378
|
containedPath2(root, input.artifactRelativePath)
|
|
12939
13379
|
);
|
|
12940
13380
|
const difference = relative4(root, target2);
|
|
12941
13381
|
if (!difference || difference === ".." || difference.startsWith(`..${sep4}`) || isAbsolute4(difference)) {
|
|
12942
13382
|
throw new Error("Build artifact resolves outside the build folder");
|
|
12943
13383
|
}
|
|
12944
|
-
const information = await
|
|
13384
|
+
const information = await stat7(target2);
|
|
12945
13385
|
let uploadPath = target2;
|
|
12946
13386
|
let filename = basename3(target2);
|
|
12947
13387
|
let contentType = "application/octet-stream";
|
|
12948
13388
|
let temporaryArchive = null;
|
|
12949
13389
|
try {
|
|
12950
13390
|
if (information.isDirectory()) {
|
|
12951
|
-
temporaryArchive =
|
|
12952
|
-
|
|
13391
|
+
temporaryArchive = join9(
|
|
13392
|
+
tmpdir4(),
|
|
12953
13393
|
`ade-build-artifact-${randomUUID3()}.tar.gz`
|
|
12954
13394
|
);
|
|
12955
13395
|
requireSuccess2(
|
|
@@ -12982,7 +13422,7 @@ var downloadIosBuildArtifact = async (payload, timeoutMs, signal, onLog, context
|
|
|
12982
13422
|
return successfulProcess6;
|
|
12983
13423
|
} finally {
|
|
12984
13424
|
if (temporaryArchive) {
|
|
12985
|
-
await
|
|
13425
|
+
await rm7(temporaryArchive, { force: true });
|
|
12986
13426
|
}
|
|
12987
13427
|
}
|
|
12988
13428
|
};
|
|
@@ -13018,24 +13458,24 @@ var deployIosBuild = async (payload, timeoutMs, signal, _onLog, context) => {
|
|
|
13018
13458
|
if (!await pathExists(appPath) || !appPath.endsWith(".app")) {
|
|
13019
13459
|
throw new Error("Runnable app artifact is missing");
|
|
13020
13460
|
}
|
|
13021
|
-
const deploymentsDirectory =
|
|
13461
|
+
const deploymentsDirectory = join9(input.artifactDirectory, "deployments");
|
|
13022
13462
|
await mkdir4(deploymentsDirectory, { recursive: true, mode: 448 });
|
|
13023
13463
|
const logger = new BuildLogger(
|
|
13024
13464
|
input.buildId,
|
|
13025
13465
|
context,
|
|
13026
|
-
|
|
13466
|
+
join9(deploymentsDirectory, "deployments.log"),
|
|
13027
13467
|
process.env
|
|
13028
13468
|
);
|
|
13029
13469
|
try {
|
|
13030
13470
|
const outcomes = [];
|
|
13031
13471
|
for (const deployment of input.deployments) {
|
|
13032
|
-
const directory =
|
|
13472
|
+
const directory = join9(
|
|
13033
13473
|
input.artifactDirectory,
|
|
13034
13474
|
"deployments",
|
|
13035
13475
|
deployment.id
|
|
13036
13476
|
);
|
|
13037
13477
|
await mkdir4(directory, { recursive: true, mode: 448 });
|
|
13038
|
-
const logPath =
|
|
13478
|
+
const logPath = join9(directory, "deployment.log");
|
|
13039
13479
|
const started = Date.now();
|
|
13040
13480
|
let failure = null;
|
|
13041
13481
|
try {
|
|
@@ -13250,15 +13690,15 @@ var exportIosArchive = async (payload, timeoutMs, signal, _onLog, context) => {
|
|
|
13250
13690
|
if (!await pathExists(archivePath) || !archivePath.endsWith(".xcarchive")) {
|
|
13251
13691
|
throw new Error("Archive artifact is missing");
|
|
13252
13692
|
}
|
|
13253
|
-
const exportDirectory =
|
|
13693
|
+
const exportDirectory = join9(
|
|
13254
13694
|
input.artifactDirectory,
|
|
13255
13695
|
"exports",
|
|
13256
13696
|
input.exportId
|
|
13257
13697
|
);
|
|
13258
13698
|
await mkdir4(exportDirectory, { recursive: true, mode: 448 });
|
|
13259
|
-
const plistPath =
|
|
13260
|
-
const logPath =
|
|
13261
|
-
await
|
|
13699
|
+
const plistPath = join9(exportDirectory, "ExportOptions.plist");
|
|
13700
|
+
const logPath = join9(exportDirectory, "export.log");
|
|
13701
|
+
await writeFile5(plistPath, exportPlist(input.settings), { mode: 384 });
|
|
13262
13702
|
const logger = new BuildLogger(input.buildId, context, logPath, process.env);
|
|
13263
13703
|
try {
|
|
13264
13704
|
const result = await runLoggedCommand({
|
|
@@ -13324,18 +13764,18 @@ var success = {
|
|
|
13324
13764
|
};
|
|
13325
13765
|
var runWorkflowTerminal = async (payloadValue, timeoutMs, signal, onLog, context) => {
|
|
13326
13766
|
const payload = parseWorkflowTerminalPayload(payloadValue);
|
|
13327
|
-
const cwd = await
|
|
13328
|
-
const information = await
|
|
13767
|
+
const cwd = await realpath6(payload.cwd);
|
|
13768
|
+
const information = await stat8(cwd);
|
|
13329
13769
|
if (!information.isDirectory())
|
|
13330
13770
|
throw new Error("Workflow working directory is not a directory");
|
|
13331
|
-
const directory = await
|
|
13771
|
+
const directory = await mkdtemp5(join10(tmpdir5(), "aide-workflow-"));
|
|
13332
13772
|
const extension2 = payload.interpreter === "NODE" ? "mjs" : "sh";
|
|
13333
|
-
const scriptPath =
|
|
13334
|
-
const sessionPath =
|
|
13773
|
+
const scriptPath = join10(directory, `step.${extension2}`);
|
|
13774
|
+
const sessionPath = join10(directory, "session.json");
|
|
13335
13775
|
try {
|
|
13336
|
-
await
|
|
13776
|
+
await writeFile6(scriptPath, `${payload.script}
|
|
13337
13777
|
`, { mode: 384 });
|
|
13338
|
-
await
|
|
13778
|
+
await writeFile6(
|
|
13339
13779
|
sessionPath,
|
|
13340
13780
|
`${JSON.stringify(payload.sessionData, null, 2)}
|
|
13341
13781
|
`,
|
|
@@ -13379,13 +13819,13 @@ var runWorkflowTerminal = async (payloadValue, timeoutMs, signal, onLog, context
|
|
|
13379
13819
|
}
|
|
13380
13820
|
return { ...result, sessionData };
|
|
13381
13821
|
} finally {
|
|
13382
|
-
await
|
|
13822
|
+
await rm8(directory, { recursive: true, force: true });
|
|
13383
13823
|
}
|
|
13384
13824
|
};
|
|
13385
13825
|
var runWorkflowGitCheckpoint = async (payloadValue, _timeoutMs, signal) => {
|
|
13386
13826
|
const payload = parseWorkflowGitCheckpointPayload(payloadValue);
|
|
13387
13827
|
if (signal.aborted) return { ...success, exitCode: null, cancelled: true };
|
|
13388
|
-
const cwd = await
|
|
13828
|
+
const cwd = await realpath6(payload.cwd);
|
|
13389
13829
|
if (payload.operation === "CAPTURE") {
|
|
13390
13830
|
const checkpoint2 = await captureGitCheckpoint(
|
|
13391
13831
|
cwd,
|
|
@@ -13422,10 +13862,10 @@ var runWorkflowGitCheckpoint = async (payloadValue, _timeoutMs, signal) => {
|
|
|
13422
13862
|
|
|
13423
13863
|
// src/handlers/worktrees.ts
|
|
13424
13864
|
import { createWriteStream as createWriteStream2, watch } from "node:fs";
|
|
13425
|
-
import { mkdtemp as
|
|
13426
|
-
import { tmpdir as
|
|
13427
|
-
import { basename as basename4, dirname as dirname6, isAbsolute as isAbsolute5, join as
|
|
13428
|
-
import { spawn as
|
|
13865
|
+
import { mkdtemp as mkdtemp6, open as open2, readFile as readFile7, realpath as realpath7, rm as rm9, stat as stat9 } from "node:fs/promises";
|
|
13866
|
+
import { tmpdir as tmpdir6 } from "node:os";
|
|
13867
|
+
import { basename as basename4, dirname as dirname6, isAbsolute as isAbsolute5, join as join11, relative as relative5 } from "node:path";
|
|
13868
|
+
import { spawn as spawn6 } from "node:child_process";
|
|
13429
13869
|
var successfulProcess7 = {
|
|
13430
13870
|
exitCode: 0,
|
|
13431
13871
|
signal: null,
|
|
@@ -13479,7 +13919,7 @@ async function rebaseInProgress(folder, timeoutMs, signal) {
|
|
|
13479
13919
|
const candidate = pathResult.stdout.trim();
|
|
13480
13920
|
if (!candidate) continue;
|
|
13481
13921
|
try {
|
|
13482
|
-
await
|
|
13922
|
+
await stat9(isAbsolute5(candidate) ? candidate : join11(folder, candidate));
|
|
13483
13923
|
return true;
|
|
13484
13924
|
} catch {
|
|
13485
13925
|
}
|
|
@@ -13499,7 +13939,7 @@ async function rebaseBranch(folder, timeoutMs, signal) {
|
|
|
13499
13939
|
if (!candidate) continue;
|
|
13500
13940
|
try {
|
|
13501
13941
|
const headName = (await readFile7(
|
|
13502
|
-
isAbsolute5(candidate) ? candidate :
|
|
13942
|
+
isAbsolute5(candidate) ? candidate : join11(folder, candidate),
|
|
13503
13943
|
"utf8"
|
|
13504
13944
|
)).trim();
|
|
13505
13945
|
if (headName.startsWith("refs/heads/")) {
|
|
@@ -13682,7 +14122,7 @@ async function gitDirectory(folder, timeoutMs, signal) {
|
|
|
13682
14122
|
),
|
|
13683
14123
|
"Could not resolve the worktree Git directory"
|
|
13684
14124
|
);
|
|
13685
|
-
return
|
|
14125
|
+
return realpath7(result.stdout.trim());
|
|
13686
14126
|
}
|
|
13687
14127
|
async function origin(folder, timeoutMs, signal) {
|
|
13688
14128
|
const result = requireSuccess3(
|
|
@@ -13692,8 +14132,8 @@ async function origin(folder, timeoutMs, signal) {
|
|
|
13692
14132
|
return normalizeGitOrigin(result.stdout.trim()).canonicalOrigin;
|
|
13693
14133
|
}
|
|
13694
14134
|
async function validateWorktree2(input, timeoutMs, signal) {
|
|
13695
|
-
const folder = await
|
|
13696
|
-
if (!(await
|
|
14135
|
+
const folder = await realpath7(input.folder);
|
|
14136
|
+
if (!(await stat9(folder)).isDirectory())
|
|
13697
14137
|
throw new Error("Worktree is missing");
|
|
13698
14138
|
const observedGitDirectory = await gitDirectory(folder, timeoutMs, signal);
|
|
13699
14139
|
if (observedGitDirectory !== input.gitDirectory) {
|
|
@@ -13739,7 +14179,7 @@ async function worktreePushStatus(folder, branch, changes, timeoutMs, signal) {
|
|
|
13739
14179
|
async function inspectWorktreeItem(folderValue2, rootFolder, baseBranch, primary, timeoutMs, signal) {
|
|
13740
14180
|
const checkedAt = (/* @__PURE__ */ new Date()).toISOString();
|
|
13741
14181
|
try {
|
|
13742
|
-
const folder = await
|
|
14182
|
+
const folder = await realpath7(folderValue2);
|
|
13743
14183
|
const [gitDir, branchResult, headResult, statusResult, rebasing] = await Promise.all([
|
|
13744
14184
|
gitDirectory(folder, timeoutMs, signal),
|
|
13745
14185
|
git3(
|
|
@@ -13839,7 +14279,7 @@ async function inspectWorktreeItem(folderValue2, rootFolder, baseBranch, primary
|
|
|
13839
14279
|
}
|
|
13840
14280
|
}
|
|
13841
14281
|
async function discoverWorktrees(rootFolderValue, baseOverrides, knownDefaultBranch, timeoutMs, signal) {
|
|
13842
|
-
const rootFolder = await
|
|
14282
|
+
const rootFolder = await realpath7(rootFolderValue);
|
|
13843
14283
|
const list = requireSuccess3(
|
|
13844
14284
|
await git3(
|
|
13845
14285
|
rootFolder,
|
|
@@ -13934,7 +14374,7 @@ function parseNumstat(value) {
|
|
|
13934
14374
|
}
|
|
13935
14375
|
async function untrackedLines(folder, path) {
|
|
13936
14376
|
try {
|
|
13937
|
-
const file = await
|
|
14377
|
+
const file = await stat9(`${folder}/${path}`);
|
|
13938
14378
|
if (!file.isFile() || file.size > 1024 * 1024) return null;
|
|
13939
14379
|
const contents = await readFile7(`${folder}/${path}`);
|
|
13940
14380
|
if (contents.includes(0)) return null;
|
|
@@ -14145,7 +14585,7 @@ async function comparisonSides(input, folder, timeoutMs, signal) {
|
|
|
14145
14585
|
if (!input.path) return { before: null, after: null };
|
|
14146
14586
|
const path = input.path;
|
|
14147
14587
|
const previousPath = input.previousPath ?? path;
|
|
14148
|
-
const currentPath =
|
|
14588
|
+
const currentPath = join11(folder, path);
|
|
14149
14589
|
if (input.scope === "UNTRACKED") {
|
|
14150
14590
|
return { before: null, after: { kind: "FILE", path: currentPath } };
|
|
14151
14591
|
}
|
|
@@ -14228,9 +14668,9 @@ async function availableSide(side, folder, timeoutMs, signal) {
|
|
|
14228
14668
|
return gitObjectExists(folder, side.specification, timeoutMs, signal);
|
|
14229
14669
|
}
|
|
14230
14670
|
try {
|
|
14231
|
-
const resolved = await
|
|
14671
|
+
const resolved = await realpath7(side.path);
|
|
14232
14672
|
const difference = relative5(folder, resolved);
|
|
14233
|
-
return difference !== ".." && !difference.startsWith("../") && (await
|
|
14673
|
+
return difference !== ".." && !difference.startsWith("../") && (await stat9(resolved)).isFile();
|
|
14234
14674
|
} catch {
|
|
14235
14675
|
return false;
|
|
14236
14676
|
}
|
|
@@ -14301,7 +14741,7 @@ async function inspectRequestedDiff(input, folder, timeoutMs, signal) {
|
|
|
14301
14741
|
let patch;
|
|
14302
14742
|
if (input.scope === "UNTRACKED") {
|
|
14303
14743
|
const bounded = await readBoundedFile(
|
|
14304
|
-
|
|
14744
|
+
join11(folder, input.path),
|
|
14305
14745
|
MAX_DIFF_BYTES
|
|
14306
14746
|
);
|
|
14307
14747
|
const contents = bounded.contents;
|
|
@@ -14405,7 +14845,7 @@ function imageContentType(path) {
|
|
|
14405
14845
|
}
|
|
14406
14846
|
async function writeGitObject(folder, specification, destination, timeoutMs, signal) {
|
|
14407
14847
|
await new Promise((resolvePromise, rejectPromise) => {
|
|
14408
|
-
const child =
|
|
14848
|
+
const child = spawn6(
|
|
14409
14849
|
"git",
|
|
14410
14850
|
["-C", folder, "cat-file", "blob", specification],
|
|
14411
14851
|
{ stdio: ["ignore", "pipe", "pipe"] }
|
|
@@ -14471,7 +14911,7 @@ var downloadWorktreeDiffAsset = async (payload, timeoutMs, signal, _onLog, conte
|
|
|
14471
14911
|
let temporaryDirectory = null;
|
|
14472
14912
|
try {
|
|
14473
14913
|
if (selected.kind === "FILE") {
|
|
14474
|
-
uploadPath = await
|
|
14914
|
+
uploadPath = await realpath7(selected.path);
|
|
14475
14915
|
const difference = relative5(folder, uploadPath);
|
|
14476
14916
|
if (difference === ".." || difference.startsWith("../")) {
|
|
14477
14917
|
throw new Error("Diff image resolves outside the worktree");
|
|
@@ -14489,8 +14929,8 @@ var downloadWorktreeDiffAsset = async (payload, timeoutMs, signal, _onLog, conte
|
|
|
14489
14929
|
if (!/^\d+$/.test(size) || Number(size) > 20 * 1024 * 1024) {
|
|
14490
14930
|
throw new Error("Diff image exceeds the 20 MiB limit");
|
|
14491
14931
|
}
|
|
14492
|
-
temporaryDirectory = await
|
|
14493
|
-
uploadPath =
|
|
14932
|
+
temporaryDirectory = await mkdtemp6(join11(tmpdir6(), "ade-diff-image-"));
|
|
14933
|
+
uploadPath = join11(temporaryDirectory, basename4(input.path));
|
|
14494
14934
|
await writeGitObject(
|
|
14495
14935
|
folder,
|
|
14496
14936
|
selected.specification,
|
|
@@ -14499,7 +14939,7 @@ var downloadWorktreeDiffAsset = async (payload, timeoutMs, signal, _onLog, conte
|
|
|
14499
14939
|
signal
|
|
14500
14940
|
);
|
|
14501
14941
|
}
|
|
14502
|
-
const information = await
|
|
14942
|
+
const information = await stat9(uploadPath);
|
|
14503
14943
|
if (!information.isFile() || information.size > 20 * 1024 * 1024) {
|
|
14504
14944
|
throw new Error("Diff image exceeds the 20 MiB limit");
|
|
14505
14945
|
}
|
|
@@ -14512,7 +14952,7 @@ var downloadWorktreeDiffAsset = async (payload, timeoutMs, signal, _onLog, conte
|
|
|
14512
14952
|
return successfulProcess7;
|
|
14513
14953
|
} finally {
|
|
14514
14954
|
if (temporaryDirectory) {
|
|
14515
|
-
await
|
|
14955
|
+
await rm9(temporaryDirectory, { recursive: true, force: true });
|
|
14516
14956
|
}
|
|
14517
14957
|
}
|
|
14518
14958
|
};
|
|
@@ -14689,8 +15129,8 @@ async function chooseNewBranch(folder, candidates, allowedCurrentBranch, timeout
|
|
|
14689
15129
|
throw new Error("Every generated ticket branch name is already taken");
|
|
14690
15130
|
}
|
|
14691
15131
|
async function validateBranchRoot(input, timeoutMs, signal) {
|
|
14692
|
-
const rootFolder = await
|
|
14693
|
-
if (!(await
|
|
15132
|
+
const rootFolder = await realpath7(input.rootFolder);
|
|
15133
|
+
if (!(await stat9(rootFolder)).isDirectory()) {
|
|
14694
15134
|
throw new Error("Base repository is missing");
|
|
14695
15135
|
}
|
|
14696
15136
|
if (await origin(rootFolder, timeoutMs, signal) !== input.expectedOrigin) {
|
|
@@ -14753,13 +15193,13 @@ var branchWorktree = async (payload, timeoutMs, signal) => {
|
|
|
14753
15193
|
timeoutMs,
|
|
14754
15194
|
signal
|
|
14755
15195
|
) : input.candidates[0];
|
|
14756
|
-
const targetFolder = input.action === "CREATE" ?
|
|
15196
|
+
const targetFolder = input.action === "CREATE" ? join11(
|
|
14757
15197
|
dirname6(rootFolder),
|
|
14758
15198
|
`${basename4(rootFolder)}-${branch.replaceAll("/", "-")}`
|
|
14759
15199
|
) : changeFolder;
|
|
14760
15200
|
if (input.action === "CREATE") {
|
|
14761
15201
|
try {
|
|
14762
|
-
await
|
|
15202
|
+
await stat9(targetFolder);
|
|
14763
15203
|
throw new Error(`Worktree folder already exists: ${targetFolder}`);
|
|
14764
15204
|
} catch (error) {
|
|
14765
15205
|
if (!(error instanceof Error) || !("code" in error) || error.code !== "ENOENT") {
|
|
@@ -14993,12 +15433,12 @@ var checkoutMovedWorktree = async (payload, timeoutMs, signal) => {
|
|
|
14993
15433
|
`Branch ${input.branch} is already checked out in ${occupiedFolder}`
|
|
14994
15434
|
);
|
|
14995
15435
|
}
|
|
14996
|
-
targetFolder =
|
|
15436
|
+
targetFolder = join11(
|
|
14997
15437
|
dirname6(rootFolder),
|
|
14998
15438
|
`${basename4(rootFolder)}-${input.branch.replaceAll("/", "-")}`
|
|
14999
15439
|
);
|
|
15000
15440
|
try {
|
|
15001
|
-
await
|
|
15441
|
+
await stat9(targetFolder);
|
|
15002
15442
|
throw new Error(`Worktree folder already exists: ${targetFolder}`);
|
|
15003
15443
|
} catch (error) {
|
|
15004
15444
|
if (!(error instanceof Error) || !("code" in error) || error.code !== "ENOENT") {
|
|
@@ -15044,7 +15484,7 @@ var checkoutMovedWorktree = async (payload, timeoutMs, signal) => {
|
|
|
15044
15484
|
const targetBranch = await currentBranch(targetFolder, timeoutMs, signal);
|
|
15045
15485
|
const targetChanges = await statusState(targetFolder, timeoutMs, signal);
|
|
15046
15486
|
if (occupiedFolder) {
|
|
15047
|
-
const occupied = await
|
|
15487
|
+
const occupied = await realpath7(occupiedFolder);
|
|
15048
15488
|
if (occupied !== targetFolder) {
|
|
15049
15489
|
throw new Error(
|
|
15050
15490
|
`Branch ${input.branch} is checked out in another destination worktree`
|
|
@@ -15158,8 +15598,8 @@ var checkoutMovedWorktree = async (payload, timeoutMs, signal) => {
|
|
|
15158
15598
|
};
|
|
15159
15599
|
var deleteWorktree = async (payload, timeoutMs, signal) => {
|
|
15160
15600
|
const input = worktreeDeleteJobPayload(payload);
|
|
15161
|
-
const rootFolder = await
|
|
15162
|
-
if (!(await
|
|
15601
|
+
const rootFolder = await realpath7(input.rootFolder);
|
|
15602
|
+
if (!(await stat9(rootFolder)).isDirectory()) {
|
|
15163
15603
|
throw new Error("Base repository is missing");
|
|
15164
15604
|
}
|
|
15165
15605
|
if (await origin(rootFolder, timeoutMs, signal) !== input.expectedOrigin) {
|
|
@@ -15401,7 +15841,7 @@ var operateWorktree = async (payload, timeoutMs, signal) => {
|
|
|
15401
15841
|
|
|
15402
15842
|
// src/handlers/index.ts
|
|
15403
15843
|
var handlers = {
|
|
15404
|
-
|
|
15844
|
+
[COMMAND_RUN_JOB_KIND]: runCommand,
|
|
15405
15845
|
[CCUSAGE_REPORT_JOB_KIND]: runCcusage,
|
|
15406
15846
|
[BUILD_DATA_SCAN_JOB_KIND]: scanBuildData,
|
|
15407
15847
|
[BUILD_DATA_SIZE_JOB_KIND]: sizeBuildData,
|
|
@@ -15489,7 +15929,9 @@ var JobExecutor = class {
|
|
|
15489
15929
|
this.running.set(job.id, { controller, task });
|
|
15490
15930
|
}
|
|
15491
15931
|
cancel(jobId) {
|
|
15492
|
-
this.running.get(jobId)
|
|
15932
|
+
const running = this.running.get(jobId);
|
|
15933
|
+
running?.controller.abort();
|
|
15934
|
+
return Boolean(running);
|
|
15493
15935
|
}
|
|
15494
15936
|
async cancelAll() {
|
|
15495
15937
|
this.stopping = true;
|
|
@@ -15524,10 +15966,11 @@ var JobExecutor = class {
|
|
|
15524
15966
|
{
|
|
15525
15967
|
reportWorktreeActivity: (input) => this.client.reportWorktreeActivity(input),
|
|
15526
15968
|
reportBuildProgress: (input) => this.client.reportBuildProgress(input),
|
|
15527
|
-
|
|
15969
|
+
appendBuildLogChunks: (buildId, chunks) => this.client.appendBuildLogChunks(buildId, chunks),
|
|
15528
15970
|
uploadBuildArtifact: (input) => this.client.uploadBuildArtifact(input),
|
|
15529
15971
|
claimSigningSecretTransfer: (transferId) => this.client.claimSigningSecretTransfer(transferId),
|
|
15530
|
-
claimWorkflowJobSecrets: () => this.client.claimWorkflowJobSecrets(claimed.id)
|
|
15972
|
+
claimWorkflowJobSecrets: () => this.client.claimWorkflowJobSecrets(claimed.id),
|
|
15973
|
+
appendCommandOutput: (attemptId, chunks) => this.client.appendCommandOutput(claimed.id, attemptId, chunks)
|
|
15531
15974
|
}
|
|
15532
15975
|
);
|
|
15533
15976
|
const codebaseId = claimed.payload && typeof claimed.payload === "object" && !Array.isArray(claimed.payload) && typeof claimed.payload.codebaseId === "string" ? String(claimed.payload.codebaseId) : null;
|
|
@@ -15703,8 +16146,8 @@ var CodebaseMonitor = class {
|
|
|
15703
16146
|
|
|
15704
16147
|
// src/runs/run-manager.ts
|
|
15705
16148
|
import { execFile as execFile4 } from "node:child_process";
|
|
15706
|
-
import { mkdir as mkdir6, rm as
|
|
15707
|
-
import { dirname as dirname8, join as
|
|
16149
|
+
import { mkdir as mkdir6, rm as rm13 } from "node:fs/promises";
|
|
16150
|
+
import { dirname as dirname8, join as join15 } from "node:path";
|
|
15708
16151
|
import { promisify as promisify4 } from "node:util";
|
|
15709
16152
|
|
|
15710
16153
|
// src/runs/journal.ts
|
|
@@ -15714,10 +16157,10 @@ import {
|
|
|
15714
16157
|
mkdir as mkdir5,
|
|
15715
16158
|
readFile as readFile8,
|
|
15716
16159
|
rename as rename4,
|
|
15717
|
-
rm as
|
|
15718
|
-
writeFile as
|
|
16160
|
+
rm as rm10,
|
|
16161
|
+
writeFile as writeFile7
|
|
15719
16162
|
} from "node:fs/promises";
|
|
15720
|
-
import { dirname as dirname7, join as
|
|
16163
|
+
import { dirname as dirname7, join as join12 } from "node:path";
|
|
15721
16164
|
var RunJournal = class {
|
|
15722
16165
|
constructor(runId, attemptId) {
|
|
15723
16166
|
this.runId = runId;
|
|
@@ -15736,13 +16179,13 @@ var RunJournal = class {
|
|
|
15736
16179
|
this.attemptId = attemptId;
|
|
15737
16180
|
}
|
|
15738
16181
|
get directory() {
|
|
15739
|
-
return
|
|
16182
|
+
return join12(dirname7(configPath()), "runs", this.runId);
|
|
15740
16183
|
}
|
|
15741
16184
|
get eventsPath() {
|
|
15742
|
-
return
|
|
16185
|
+
return join12(this.directory, "events.jsonl");
|
|
15743
16186
|
}
|
|
15744
16187
|
get statePath() {
|
|
15745
|
-
return
|
|
16188
|
+
return join12(this.directory, "state.json");
|
|
15746
16189
|
}
|
|
15747
16190
|
async load() {
|
|
15748
16191
|
if (this.loaded) return;
|
|
@@ -15843,10 +16286,10 @@ var RunJournal = class {
|
|
|
15843
16286
|
const operation = this.saving.then(async () => {
|
|
15844
16287
|
const temporary = `${this.statePath}.${process.pid}.${randomUUID4()}.tmp`;
|
|
15845
16288
|
try {
|
|
15846
|
-
await
|
|
16289
|
+
await writeFile7(temporary, contents, { mode: 384 });
|
|
15847
16290
|
await rename4(temporary, this.statePath);
|
|
15848
16291
|
} catch (error) {
|
|
15849
|
-
await
|
|
16292
|
+
await rm10(temporary, { force: true }).catch(() => void 0);
|
|
15850
16293
|
throw error;
|
|
15851
16294
|
}
|
|
15852
16295
|
});
|
|
@@ -25020,7 +25463,7 @@ function Yy(e) {
|
|
|
25020
25463
|
var l = {};
|
|
25021
25464
|
lt(l, { xid: () => u9, void: () => I9, uuidv7: () => n9, uuidv6: () => r9, uuidv4: () => t9, uuid: () => e9, url: () => o9, uppercase: () => Fl, unknown: () => Ke, union: () => $e, undefined: () => C9, ulid: () => l9, uint64: () => A9, uint32: () => w9, tuple: () => L9, trim: () => Wl, treeifyError: () => Yd, transform: () => jv, toUpperCase: () => Zl, toLowerCase: () => Kl, toJSONSchema: () => Js, templateLiteral: () => q9, symbol: () => O9, superRefine: () => ER, success: () => B9, stringbool: () => W9, stringFormat: () => x9, string: () => k, strictObject: () => N9, startsWith: () => Hl, size: () => $l, setErrorMap: () => J9, set: () => $9, safeParseAsync: () => gv, safeParse: () => mv, registry: () => hl, regexes: () => wo, regex: () => jl, refine: () => SR, record: () => je, readonly: () => hR, property: () => iv, promise: () => G9, prettifyError: () => Xd, preprocess: () => Km, prefault: () => lR, positive: () => tv, pipe: () => Fm, partialRecord: () => M9, parseAsync: () => fv, parse: () => dv, overwrite: () => Vn, optional: () => Ve, object: () => G, number: () => Ce, nullish: () => F9, nullable: () => zm, null: () => Bm, normalize: () => Vl, nonpositive: () => nv, nonoptional: () => uR, nonnegative: () => ov, never: () => Hm, negative: () => rv, nativeEnum: () => j9, nanoid: () => s9, nan: () => H9, multipleOf: () => wi, minSize: () => Ti, minLength: () => Ao, mime: () => Gl, maxSize: () => Ws, maxLength: () => Ks, map: () => U9, lte: () => Ur, lt: () => qn, lowercase: () => zl, looseObject: () => Bt, locales: () => Gs, literal: () => Z, length: () => Zs, lazy: () => bR, ksuid: () => p9, keyof: () => D9, jwt: () => b9, json: () => K9, iso: () => Ys, ipv6: () => f9, ipv4: () => d9, intersection: () => ru, int64: () => k9, int32: () => E9, int: () => hv, instanceof: () => V9, includes: () => Bl, guid: () => QZ, gte: () => ar, gt: () => Gn, globalRegistry: () => sr, getErrorMap: () => Y9, function: () => Dm, formatError: () => js, float64: () => S9, float32: () => v9, flattenError: () => $s, file: () => z9, enum: () => Jt, endsWith: () => ql, emoji: () => i9, email: () => XZ, e164: () => y9, discriminatedUnion: () => Vm, date: () => P9, custom: () => Hv, cuid2: () => c9, cuid: () => a9, core: () => Qr, config: () => ut, coerce: () => qv, clone: () => Ft, cidrv6: () => g9, cidrv4: () => m9, check: () => vR, catch: () => fR, boolean: () => ht, bigint: () => T9, base64url: () => _9, base64: () => h9, array: () => he, any: () => R9, _default: () => aR, _ZodString: () => _v, ZodXID: () => Tv, ZodVoid: () => JC, ZodUnknown: () => KC, ZodUnion: () => Mv, ZodUndefined: () => GC, ZodUUID: () => Wn, ZodURL: () => bv, ZodULID: () => wv, ZodType: () => de, ZodTuple: () => eR, ZodTransform: () => $v, ZodTemplateLiteral: () => _R, ZodSymbol: () => qC, ZodSuccess: () => pR, ZodStringFormat: () => Ge, ZodString: () => Xl, ZodSet: () => rR, ZodRecord: () => Uv, ZodRealError: () => Xs, ZodReadonly: () => gR, ZodPromise: () => xR, ZodPrefault: () => cR, ZodPipe: () => Bv, ZodOptional: () => zv, ZodObject: () => Gm, ZodNumberFormat: () => Qs, ZodNumber: () => Ql, ZodNullable: () => iR, ZodNull: () => VC, ZodNonOptional: () => Fv, ZodNever: () => ZC, ZodNanoID: () => vv, ZodNaN: () => mR, ZodMap: () => tR, ZodLiteral: () => nR, ZodLazy: () => yR, ZodKSUID: () => kv, ZodJWT: () => Nv, ZodIssueCode: () => Z9, ZodIntersection: () => QC, ZodISOTime: () => Um, ZodISODuration: () => $m, ZodISODateTime: () => Lm, ZodISODate: () => Mm, ZodIPv6: () => Ov, ZodIPv4: () => Av, ZodGUID: () => jm, ZodFile: () => oR, ZodError: () => JZ, ZodEnum: () => Yl, ZodEmoji: () => xv, ZodEmail: () => yv, ZodE164: () => Dv, ZodDiscriminatedUnion: () => XC, ZodDefault: () => sR, ZodDate: () => qm, ZodCustomStringFormat: () => HC, ZodCustom: () => Wm, ZodCatch: () => dR, ZodCUID2: () => Ev, ZodCUID: () => Sv, ZodCIDRv6: () => Rv, ZodCIDRv4: () => Cv, ZodBoolean: () => eu, ZodBigIntFormat: () => Lv, ZodBigInt: () => tu, ZodBase64URL: () => Pv, ZodBase64: () => Iv, ZodArray: () => YC, ZodAny: () => WC, TimePrecision: () => lm, NEVER: () => Kd, $output: () => sm, $input: () => am, $brand: () => Zd });
|
|
25022
25465
|
var Qr = {};
|
|
25023
|
-
lt(Qr, { version: () => tx, util: () => M, treeifyError: () => Yd, toJSONSchema: () => Js, toDotPath: () => yC, safeParseAsync: () => Eo, safeParse: () => So, registry: () => hl, regexes: () => wo, prettifyError: () => Xd, parseAsync: () => xi, parse: () => bi, locales: () => Gs, isValidJWT: () => MC, isValidBase64URL: () => LC, isValidBase64: () => ax, globalRegistry: () => sr, globalConfig: () => tl, function: () => Dm, formatError: () => js, flattenError: () => $s, config: () => ut, clone: () => Ft, _xid: () => Ol, _void: () => Tm, _uuidv7: () => vl, _uuidv6: () => xl, _uuidv4: () => bl, _uuid: () => yl, _url: () => Sl, _uppercase: () => Fl, _unknown: () => Ei, _union: () => OZ, _undefined: () => vm, _ulid: () => Al, _uint64: () => bm, _uint32: () => gm, _tuple: () => sv, _trim: () => Wl, _transform: () => UZ, _toUpperCase: () => Zl, _toLowerCase: () => Kl, _templateLiteral: () => VZ, _symbol: () => xm, _success: () => BZ, _stringbool: () => Im, _stringFormat: () => Pm, _string: () => cm, _startsWith: () => Hl, _size: () => $l, _set: () => DZ, _safeParseAsync: () => rf, _safeParse: () => tf, _regex: () => jl, _refine: () => Rm, _record: () => IZ, _readonly: () => GZ, _property: () => iv, _promise: () => KZ, _positive: () => tv, _pipe: () => qZ, _parseAsync: () => ef, _parse: () => Qd, _overwrite: () => Vn, _optional: () => $Z, _number: () => um, _nullable: () => jZ, _null: () => Sm, _normalize: () => Vl, _nonpositive: () => nv, _nonoptional: () => FZ, _nonnegative: () => ov, _never: () => wm, _negative: () => rv, _nativeEnum: () => LZ, _nanoid: () => wl, _nan: () => Am, _multipleOf: () => wi, _minSize: () => Ti, _minLength: () => Ao, _min: () => ar, _mime: () => Gl, _maxSize: () => Ws, _maxLength: () => Ks, _max: () => Ur, _map: () => PZ, _lte: () => Ur, _lt: () => qn, _lowercase: () => zl, _literal: () => MZ, _length: () => Zs, _lazy: () => WZ, _ksuid: () => Cl, _jwt: () => Ul, _isoTime: () => Zx, _isoDuration: () => Jx, _isoDateTime: () => Wx, _isoDate: () => Kx, _ipv6: () => Il, _ipv4: () => Rl, _intersection: () => RZ, _int64: () => ym, _int32: () => mm, _int: () => pm, _includes: () => Bl, _guid: () => Vs, _gte: () => ar, _gt: () => Gn, _float64: () => fm, _float32: () => dm, _file: () => Om, _enum: () => NZ, _endsWith: () => ql, _emoji: () => El, _email: () => _l, _e164: () => Ml, _discriminatedUnion: () => CZ, _default: () => zZ, _date: () => km, _custom: () => Cm, _cuid2: () => kl, _cuid: () => Tl, _coercedString: () => Vx, _coercedNumber: () => Yx, _coercedDate: () => ev, _coercedBoolean: () => Xx, _coercedBigint: () => Qx, _cidrv6: () => Dl, _cidrv4: () => Pl, _catch: () => HZ, _boolean: () => hm, _bigint: () => _m, _base64url: () => Ll, _base64: () => Nl, _array: () => Jl, _any: () => Em, TimePrecision: () => lm, NEVER: () => Kd, JSONSchemaGenerator: () => Nm, JSONSchema: () => zC, Doc: () => af, $output: () => sm, $input: () => am, $constructor: () => S, $brand: () => Zd, $ZodXID: () => bf, $ZodVoid: () => Uf, $ZodUnknown: () => Si, $ZodUnion: () => fl, $ZodUndefined: () => Df, $ZodUUID: () => pf, $ZodURL: () => ff, $ZodULID: () => yf, $ZodType: () => ie, $ZodTuple: () => ko, $ZodTransform: () => Hs, $ZodTemplateLiteral: () =>
|
|
25466
|
+
lt(Qr, { version: () => tx, util: () => M, treeifyError: () => Yd, toJSONSchema: () => Js, toDotPath: () => yC, safeParseAsync: () => Eo, safeParse: () => So, registry: () => hl, regexes: () => wo, prettifyError: () => Xd, parseAsync: () => xi, parse: () => bi, locales: () => Gs, isValidJWT: () => MC, isValidBase64URL: () => LC, isValidBase64: () => ax, globalRegistry: () => sr, globalConfig: () => tl, function: () => Dm, formatError: () => js, flattenError: () => $s, config: () => ut, clone: () => Ft, _xid: () => Ol, _void: () => Tm, _uuidv7: () => vl, _uuidv6: () => xl, _uuidv4: () => bl, _uuid: () => yl, _url: () => Sl, _uppercase: () => Fl, _unknown: () => Ei, _union: () => OZ, _undefined: () => vm, _ulid: () => Al, _uint64: () => bm, _uint32: () => gm, _tuple: () => sv, _trim: () => Wl, _transform: () => UZ, _toUpperCase: () => Zl, _toLowerCase: () => Kl, _templateLiteral: () => VZ, _symbol: () => xm, _success: () => BZ, _stringbool: () => Im, _stringFormat: () => Pm, _string: () => cm, _startsWith: () => Hl, _size: () => $l, _set: () => DZ, _safeParseAsync: () => rf, _safeParse: () => tf, _regex: () => jl, _refine: () => Rm, _record: () => IZ, _readonly: () => GZ, _property: () => iv, _promise: () => KZ, _positive: () => tv, _pipe: () => qZ, _parseAsync: () => ef, _parse: () => Qd, _overwrite: () => Vn, _optional: () => $Z, _number: () => um, _nullable: () => jZ, _null: () => Sm, _normalize: () => Vl, _nonpositive: () => nv, _nonoptional: () => FZ, _nonnegative: () => ov, _never: () => wm, _negative: () => rv, _nativeEnum: () => LZ, _nanoid: () => wl, _nan: () => Am, _multipleOf: () => wi, _minSize: () => Ti, _minLength: () => Ao, _min: () => ar, _mime: () => Gl, _maxSize: () => Ws, _maxLength: () => Ks, _max: () => Ur, _map: () => PZ, _lte: () => Ur, _lt: () => qn, _lowercase: () => zl, _literal: () => MZ, _length: () => Zs, _lazy: () => WZ, _ksuid: () => Cl, _jwt: () => Ul, _isoTime: () => Zx, _isoDuration: () => Jx, _isoDateTime: () => Wx, _isoDate: () => Kx, _ipv6: () => Il, _ipv4: () => Rl, _intersection: () => RZ, _int64: () => ym, _int32: () => mm, _int: () => pm, _includes: () => Bl, _guid: () => Vs, _gte: () => ar, _gt: () => Gn, _float64: () => fm, _float32: () => dm, _file: () => Om, _enum: () => NZ, _endsWith: () => ql, _emoji: () => El, _email: () => _l, _e164: () => Ml, _discriminatedUnion: () => CZ, _default: () => zZ, _date: () => km, _custom: () => Cm, _cuid2: () => kl, _cuid: () => Tl, _coercedString: () => Vx, _coercedNumber: () => Yx, _coercedDate: () => ev, _coercedBoolean: () => Xx, _coercedBigint: () => Qx, _cidrv6: () => Dl, _cidrv4: () => Pl, _catch: () => HZ, _boolean: () => hm, _bigint: () => _m, _base64url: () => Ll, _base64: () => Nl, _array: () => Jl, _any: () => Em, TimePrecision: () => lm, NEVER: () => Kd, JSONSchemaGenerator: () => Nm, JSONSchema: () => zC, Doc: () => af, $output: () => sm, $input: () => am, $constructor: () => S, $brand: () => Zd, $ZodXID: () => bf, $ZodVoid: () => Uf, $ZodUnknown: () => Si, $ZodUnion: () => fl, $ZodUndefined: () => Df, $ZodUUID: () => pf, $ZodURL: () => ff, $ZodULID: () => yf, $ZodType: () => ie, $ZodTuple: () => ko, $ZodTransform: () => Hs, $ZodTemplateLiteral: () => rm11, $ZodSymbol: () => Pf, $ZodSuccess: () => Xf, $ZodStringFormat: () => Ue, $ZodString: () => To, $ZodSet: () => Hf, $ZodRegistry: () => gl, $ZodRecord: () => Ff, $ZodRealError: () => Us, $ZodReadonly: () => tm, $ZodPromise: () => nm, $ZodPrefault: () => Jf, $ZodPipe: () => qs, $ZodOptional: () => Wf, $ZodObject: () => dl, $ZodNumberFormat: () => Rf, $ZodNumber: () => ul, $ZodNullable: () => Kf, $ZodNull: () => Nf, $ZodNonOptional: () => Yf, $ZodNever: () => Mf, $ZodNanoID: () => gf, $ZodNaN: () => em, $ZodMap: () => Bf, $ZodLiteral: () => Gf, $ZodLazy: () => om, $ZodKSUID: () => xf, $ZodJWT: () => Of, $ZodIntersection: () => zf, $ZodISOTime: () => ix, $ZodISODuration: () => sx, $ZodISODateTime: () => nx, $ZodISODate: () => ox, $ZodIPv6: () => Sf, $ZodIPv4: () => vf, $ZodGUID: () => uf, $ZodFunction: () => av, $ZodFile: () => Vf, $ZodError: () => ll, $ZodEnum: () => qf, $ZodEmoji: () => mf, $ZodEmail: () => df, $ZodE164: () => Af, $ZodDiscriminatedUnion: () => jf, $ZodDefault: () => Zf, $ZodDate: () => $f, $ZodCustomStringFormat: () => Cf, $ZodCustom: () => im, $ZodCheckUpperCase: () => Kb, $ZodCheckStringFormat: () => zs, $ZodCheckStartsWith: () => Jb, $ZodCheckSizeEquals: () => Bb, $ZodCheckRegex: () => Vb, $ZodCheckProperty: () => Xb, $ZodCheckOverwrite: () => ex, $ZodCheckNumberFormat: () => $b, $ZodCheckMultipleOf: () => Ub, $ZodCheckMinSize: () => Fb, $ZodCheckMinLength: () => qb, $ZodCheckMimeType: () => Qb, $ZodCheckMaxSize: () => zb, $ZodCheckMaxLength: () => Hb, $ZodCheckLowerCase: () => Wb, $ZodCheckLessThan: () => of, $ZodCheckLengthEquals: () => Gb, $ZodCheckIncludes: () => Zb, $ZodCheckGreaterThan: () => sf, $ZodCheckEndsWith: () => Yb, $ZodCheckBigIntFormat: () => jb, $ZodCheck: () => Xe, $ZodCatch: () => Qf, $ZodCUID2: () => _f, $ZodCUID: () => hf, $ZodCIDRv6: () => wf, $ZodCIDRv4: () => Ef, $ZodBoolean: () => Fs, $ZodBigIntFormat: () => If, $ZodBigInt: () => pl, $ZodBase64URL: () => kf, $ZodBase64: () => Tf, $ZodAsyncError: () => Bn, $ZodArray: () => Bs, $ZodAny: () => Lf });
|
|
25024
25467
|
var Kd = Object.freeze({ status: "aborted" });
|
|
25025
25468
|
function S(e, t, r) {
|
|
25026
25469
|
function n(a, c) {
|
|
@@ -26568,7 +27011,7 @@ var tm = S("$ZodReadonly", (e, t) => {
|
|
|
26568
27011
|
function DC(e) {
|
|
26569
27012
|
return e.value = Object.freeze(e.value), e;
|
|
26570
27013
|
}
|
|
26571
|
-
var
|
|
27014
|
+
var rm11 = S("$ZodTemplateLiteral", (e, t) => {
|
|
26572
27015
|
ie.init(e, t);
|
|
26573
27016
|
let r = [];
|
|
26574
27017
|
for (let n of t.parts) if (n instanceof ie) {
|
|
@@ -30375,7 +30818,7 @@ function hR(e) {
|
|
|
30375
30818
|
return new gR({ type: "readonly", innerType: e });
|
|
30376
30819
|
}
|
|
30377
30820
|
var _R = S("ZodTemplateLiteral", (e, t) => {
|
|
30378
|
-
|
|
30821
|
+
rm11.init(e, t), de.init(e, t);
|
|
30379
30822
|
});
|
|
30380
30823
|
function q9(e, t) {
|
|
30381
30824
|
return new _R({ type: "template_literal", parts: e, ...M.normalizeParams(t) });
|
|
@@ -41994,11 +42437,11 @@ var ClaudeAdapter = class {
|
|
|
41994
42437
|
// src/runs/codex-adapter.ts
|
|
41995
42438
|
import {
|
|
41996
42439
|
execFile as execFile3,
|
|
41997
|
-
spawn as
|
|
42440
|
+
spawn as spawn7
|
|
41998
42441
|
} from "node:child_process";
|
|
41999
|
-
import { mkdtemp as
|
|
42000
|
-
import { tmpdir as
|
|
42001
|
-
import { join as
|
|
42442
|
+
import { mkdtemp as mkdtemp7, rm as rm12, writeFile as writeFile8 } from "node:fs/promises";
|
|
42443
|
+
import { tmpdir as tmpdir7 } from "node:os";
|
|
42444
|
+
import { join as join14 } from "node:path";
|
|
42002
42445
|
import { createInterface } from "node:readline";
|
|
42003
42446
|
import { promisify as promisify3 } from "node:util";
|
|
42004
42447
|
var SUPPORTED_CODEX_APP_SERVER_MINORS = ["0.144", "0.145"];
|
|
@@ -42056,7 +42499,7 @@ var CodexAppServer = class {
|
|
|
42056
42499
|
async start() {
|
|
42057
42500
|
const modelCatalogPath = await this.createBundledModelCatalog();
|
|
42058
42501
|
const modelCatalogDirectory = this.modelCatalogDirectory;
|
|
42059
|
-
const child =
|
|
42502
|
+
const child = spawn7("codex", codexAppServerArgs(modelCatalogPath), {
|
|
42060
42503
|
stdio: ["pipe", "pipe", "pipe"],
|
|
42061
42504
|
env: process.env
|
|
42062
42505
|
});
|
|
@@ -42125,7 +42568,7 @@ var CodexAppServer = class {
|
|
|
42125
42568
|
}
|
|
42126
42569
|
}
|
|
42127
42570
|
async createBundledModelCatalog() {
|
|
42128
|
-
const directory = await
|
|
42571
|
+
const directory = await mkdtemp7(join14(tmpdir7(), "aide-codex-models-"));
|
|
42129
42572
|
try {
|
|
42130
42573
|
const { stdout } = await execFileAsync2(
|
|
42131
42574
|
"codex",
|
|
@@ -42135,12 +42578,12 @@ var CodexAppServer = class {
|
|
|
42135
42578
|
maxBuffer: 16 * 1024 * 1024
|
|
42136
42579
|
}
|
|
42137
42580
|
);
|
|
42138
|
-
const catalogPath =
|
|
42139
|
-
await
|
|
42581
|
+
const catalogPath = join14(directory, "models.json");
|
|
42582
|
+
await writeFile8(catalogPath, stdout, "utf8");
|
|
42140
42583
|
this.modelCatalogDirectory = directory;
|
|
42141
42584
|
return catalogPath;
|
|
42142
42585
|
} catch (error) {
|
|
42143
|
-
await
|
|
42586
|
+
await rm12(directory, { recursive: true, force: true }).catch(
|
|
42144
42587
|
() => void 0
|
|
42145
42588
|
);
|
|
42146
42589
|
throw error;
|
|
@@ -42151,7 +42594,7 @@ var CodexAppServer = class {
|
|
|
42151
42594
|
if (this.modelCatalogDirectory === directory) {
|
|
42152
42595
|
this.modelCatalogDirectory = void 0;
|
|
42153
42596
|
}
|
|
42154
|
-
await
|
|
42597
|
+
await rm12(directory, { recursive: true, force: true }).catch(
|
|
42155
42598
|
() => void 0
|
|
42156
42599
|
);
|
|
42157
42600
|
}
|
|
@@ -48829,7 +49272,7 @@ var RunManager = class {
|
|
|
48829
49272
|
5
|
|
48830
49273
|
);
|
|
48831
49274
|
await this.completeCommand(command3.id, "SUCCEEDED");
|
|
48832
|
-
await
|
|
49275
|
+
await rm13(join15(dirname8(configPath()), "runs", run.id, "attachments"), {
|
|
48833
49276
|
recursive: true,
|
|
48834
49277
|
force: true
|
|
48835
49278
|
}).catch(() => void 0);
|
|
@@ -49010,7 +49453,7 @@ var RunManager = class {
|
|
|
49010
49453
|
this.active.delete(run.id);
|
|
49011
49454
|
this.interruptionRequests.delete(run.id);
|
|
49012
49455
|
this.executingCommands.delete(command3.id);
|
|
49013
|
-
await
|
|
49456
|
+
await rm13(join15(dirname8(configPath()), "runs", run.id, "attachments"), {
|
|
49014
49457
|
recursive: true,
|
|
49015
49458
|
force: true
|
|
49016
49459
|
}).catch(() => void 0);
|
|
@@ -49238,11 +49681,11 @@ var RunManager = class {
|
|
|
49238
49681
|
}
|
|
49239
49682
|
async stageAttachments(runId, attachments) {
|
|
49240
49683
|
if (!attachments.length) return [];
|
|
49241
|
-
const directory =
|
|
49684
|
+
const directory = join15(dirname8(configPath()), "runs", runId, "attachments");
|
|
49242
49685
|
await mkdir6(directory, { recursive: true, mode: 448 });
|
|
49243
49686
|
return Promise.all(
|
|
49244
49687
|
attachments.map(async (attachment) => {
|
|
49245
|
-
const path =
|
|
49688
|
+
const path = join15(
|
|
49246
49689
|
directory,
|
|
49247
49690
|
`${attachment.id}-${safeFilename(attachment.filename)}`
|
|
49248
49691
|
);
|
|
@@ -49358,6 +49801,10 @@ var RunManager = class {
|
|
|
49358
49801
|
}
|
|
49359
49802
|
};
|
|
49360
49803
|
|
|
49804
|
+
// ../agent-contract/src/disk-space.ts
|
|
49805
|
+
var DISK_SPACE_POLL_INTERVAL_SECONDS = 60;
|
|
49806
|
+
var DISK_SPACE_STALE_AFTER_SECONDS = DISK_SPACE_POLL_INTERVAL_SECONDS * 2;
|
|
49807
|
+
|
|
49361
49808
|
// src/agent-runtime.ts
|
|
49362
49809
|
function configuredIntervalMs(value, fallbackSeconds, minSeconds, maxSeconds) {
|
|
49363
49810
|
return (Number.isInteger(value) && value >= minSeconds && value <= maxSeconds ? value : fallbackSeconds) * 1e3;
|
|
@@ -49380,6 +49827,9 @@ async function runAgent(config, signal) {
|
|
|
49380
49827
|
let heartbeatTimer;
|
|
49381
49828
|
let jobReconciliationTimer;
|
|
49382
49829
|
let codebaseTimer;
|
|
49830
|
+
let diskSpaceTimer;
|
|
49831
|
+
let diskSpaceRunning = false;
|
|
49832
|
+
let diskSpaceIntervalMs = DISK_SPACE_POLL_INTERVAL_SECONDS * 1e3;
|
|
49383
49833
|
let startupRecoveryPending = true;
|
|
49384
49834
|
const interruptedJobs = /* @__PURE__ */ new Set();
|
|
49385
49835
|
const reconcileJobs = async (recoverInterrupted) => {
|
|
@@ -49399,6 +49849,12 @@ async function runAgent(config, signal) {
|
|
|
49399
49849
|
executor.cancel(job.id);
|
|
49400
49850
|
return;
|
|
49401
49851
|
}
|
|
49852
|
+
if (job.status === "CANCELLING") {
|
|
49853
|
+
if (!executor.cancel(job.id)) {
|
|
49854
|
+
await client2.completeJob(job.id, "CANCELLED");
|
|
49855
|
+
}
|
|
49856
|
+
return;
|
|
49857
|
+
}
|
|
49402
49858
|
if (job.status !== "RUNNING" || !recoverInterrupted && !interruptedJobs.has(job.id)) {
|
|
49403
49859
|
executor.execute(job);
|
|
49404
49860
|
return;
|
|
@@ -49527,11 +49983,48 @@ async function runAgent(config, signal) {
|
|
|
49527
49983
|
codebaseTimer = void 0;
|
|
49528
49984
|
void reconcileCodebases();
|
|
49529
49985
|
};
|
|
49986
|
+
const scheduleDiskSpacePoll = () => {
|
|
49987
|
+
if (diskSpaceTimer) clearTimeout(diskSpaceTimer);
|
|
49988
|
+
if (!signal.aborted) {
|
|
49989
|
+
diskSpaceTimer = setTimeout(
|
|
49990
|
+
() => void runDiskSpacePoll(),
|
|
49991
|
+
diskSpaceIntervalMs
|
|
49992
|
+
);
|
|
49993
|
+
}
|
|
49994
|
+
};
|
|
49995
|
+
const runDiskSpacePoll = async () => {
|
|
49996
|
+
if (diskSpaceRunning || signal.aborted) return;
|
|
49997
|
+
diskSpaceRunning = true;
|
|
49998
|
+
if (diskSpaceTimer) clearTimeout(diskSpaceTimer);
|
|
49999
|
+
diskSpaceTimer = void 0;
|
|
50000
|
+
try {
|
|
50001
|
+
const configuration = await client2.diskSpaceConfiguration();
|
|
50002
|
+
diskSpaceIntervalMs = Math.max(
|
|
50003
|
+
1e3,
|
|
50004
|
+
configuration.pollIntervalSeconds * 1e3
|
|
50005
|
+
);
|
|
50006
|
+
if (configuration.enabled) {
|
|
50007
|
+
const report = await collectAgentDiskSpace(configuration, signal);
|
|
50008
|
+
await client2.reportDiskSpace(report);
|
|
50009
|
+
}
|
|
50010
|
+
} catch (error) {
|
|
50011
|
+
if (!signal.aborted) {
|
|
50012
|
+
console.error(
|
|
50013
|
+
"Disk space poll failed:",
|
|
50014
|
+
error instanceof Error ? error.message : error
|
|
50015
|
+
);
|
|
50016
|
+
}
|
|
50017
|
+
} finally {
|
|
50018
|
+
diskSpaceRunning = false;
|
|
50019
|
+
scheduleDiskSpacePoll();
|
|
50020
|
+
}
|
|
50021
|
+
};
|
|
49530
50022
|
await refreshCadence();
|
|
49531
50023
|
await heartbeat();
|
|
49532
50024
|
await runJobReconciliation();
|
|
49533
50025
|
await runManager.start();
|
|
49534
50026
|
void reconcileCodebases();
|
|
50027
|
+
void runDiskSpacePoll();
|
|
49535
50028
|
const subscriptionClient = createAgentSubscriptionClient(config);
|
|
49536
50029
|
const unsubscribe = subscribeToAgentEvents(
|
|
49537
50030
|
subscriptionClient,
|
|
@@ -49544,11 +50037,14 @@ async function runAgent(config, signal) {
|
|
|
49544
50037
|
requestCodebaseReconcile();
|
|
49545
50038
|
} else if (event.type === "RUN_COMMAND_AVAILABLE") {
|
|
49546
50039
|
runManager.execute(event.runCommand);
|
|
50040
|
+
} else if (event.type === "DISK_SPACE_POLL_REQUESTED") {
|
|
50041
|
+
void runDiskSpacePoll();
|
|
49547
50042
|
} else {
|
|
49548
50043
|
void refreshCadence().then(() => {
|
|
49549
50044
|
scheduleHeartbeat();
|
|
49550
50045
|
scheduleJobReconciliation();
|
|
49551
50046
|
requestCodebaseReconcile();
|
|
50047
|
+
void runDiskSpacePoll();
|
|
49552
50048
|
});
|
|
49553
50049
|
}
|
|
49554
50050
|
}
|
|
@@ -49560,6 +50056,7 @@ async function runAgent(config, signal) {
|
|
|
49560
50056
|
if (heartbeatTimer) clearTimeout(heartbeatTimer);
|
|
49561
50057
|
if (jobReconciliationTimer) clearTimeout(jobReconciliationTimer);
|
|
49562
50058
|
if (codebaseTimer) clearTimeout(codebaseTimer);
|
|
50059
|
+
if (diskSpaceTimer) clearTimeout(diskSpaceTimer);
|
|
49563
50060
|
unsubscribe();
|
|
49564
50061
|
await subscriptionClient.dispose();
|
|
49565
50062
|
await executor.cancelAll();
|
|
@@ -49699,7 +50196,6 @@ function redactedRequestHeaders(headers) {
|
|
|
49699
50196
|
}
|
|
49700
50197
|
|
|
49701
50198
|
// src/index.ts
|
|
49702
|
-
var execFileAsync4 = promisify5(execFile5);
|
|
49703
50199
|
function flags(args) {
|
|
49704
50200
|
const result = {};
|
|
49705
50201
|
const headerValues = [];
|
|
@@ -49802,22 +50298,6 @@ async function doctor() {
|
|
|
49802
50298
|
detail: error instanceof Error ? error.message : String(error)
|
|
49803
50299
|
});
|
|
49804
50300
|
}
|
|
49805
|
-
try {
|
|
49806
|
-
const { stdout, stderr } = await execFileAsync4("cloudflared", [
|
|
49807
|
-
"--version"
|
|
49808
|
-
]);
|
|
49809
|
-
checks.push({
|
|
49810
|
-
check: "cloudflared",
|
|
49811
|
-
ok: true,
|
|
49812
|
-
detail: (stdout || stderr).trim()
|
|
49813
|
-
});
|
|
49814
|
-
} catch (error) {
|
|
49815
|
-
checks.push({
|
|
49816
|
-
check: "cloudflared",
|
|
49817
|
-
ok: false,
|
|
49818
|
-
detail: error instanceof Error ? error.message : String(error)
|
|
49819
|
-
});
|
|
49820
|
-
}
|
|
49821
50301
|
for (const check of checks)
|
|
49822
50302
|
console.log(
|
|
49823
50303
|
`${check.ok ? "PASS" : "FAIL"} ${check.check}: ${check.detail}`
|
|
@@ -49835,21 +50315,26 @@ async function main() {
|
|
|
49835
50315
|
if (command3 === "doctor") return doctor();
|
|
49836
50316
|
if (command3 === "run" || command3 === "dev") {
|
|
49837
50317
|
const controller = new AbortController();
|
|
49838
|
-
|
|
49839
|
-
|
|
49840
|
-
|
|
49841
|
-
|
|
49842
|
-
|
|
49843
|
-
|
|
49844
|
-
{
|
|
49845
|
-
|
|
49846
|
-
|
|
49847
|
-
|
|
49848
|
-
|
|
49849
|
-
|
|
49850
|
-
|
|
50318
|
+
const stop2 = () => controller.abort();
|
|
50319
|
+
const shutdownSignals = ["SIGINT", "SIGTERM", "SIGHUP"];
|
|
50320
|
+
for (const signal of shutdownSignals) process.once(signal, stop2);
|
|
50321
|
+
try {
|
|
50322
|
+
if (command3 === "dev") {
|
|
50323
|
+
const options = flags(args).values;
|
|
50324
|
+
const server = options.server ?? process.env.CONTROL_AGENT_DEV_SERVER ?? `http://127.0.0.1:${process.env.PORT ?? "3000"}`;
|
|
50325
|
+
return await runDevelopmentAgent(
|
|
50326
|
+
{
|
|
50327
|
+
server,
|
|
50328
|
+
websocketServer: options["websocket-server"] ?? process.env.CONTROL_AGENT_DEV_WEBSOCKET_SERVER ?? process.env.NEXT_PUBLIC_AGENT_WS_URL,
|
|
50329
|
+
name: options.name
|
|
50330
|
+
},
|
|
50331
|
+
controller.signal
|
|
50332
|
+
);
|
|
50333
|
+
}
|
|
50334
|
+
return await runAgent(await loadConfig(), controller.signal);
|
|
50335
|
+
} finally {
|
|
50336
|
+
for (const signal of shutdownSignals) process.off(signal, stop2);
|
|
49851
50337
|
}
|
|
49852
|
-
return runAgent(await loadConfig(), controller.signal);
|
|
49853
50338
|
}
|
|
49854
50339
|
throw new Error(`Unknown command: ${command3}`);
|
|
49855
50340
|
}
|