topchester-ai 0.66.0 → 0.68.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/bin.mjs +1 -1
- package/dist/{cli-BS67FTk8.mjs → cli-CRhzHqMB.mjs} +240 -20
- package/dist/cli-CRhzHqMB.mjs.map +1 -0
- package/dist/cli.mjs +1 -1
- package/package.json +1 -1
- package/dist/cli-BS67FTk8.mjs.map +0 -1
package/dist/bin.mjs
CHANGED
|
@@ -9,8 +9,9 @@ import { createOpenAICompatible } from "@ai-sdk/openai-compatible";
|
|
|
9
9
|
import { generateText, stepCountIs, streamText, tool } from "ai";
|
|
10
10
|
import { ZodError, z } from "zod";
|
|
11
11
|
import { execFile, spawn } from "node:child_process";
|
|
12
|
-
import { accessSync, constants, existsSync, mkdirSync, readFileSync, statSync, writeFileSync } from "node:fs";
|
|
12
|
+
import { accessSync, constants, createReadStream, existsSync, mkdirSync, readFileSync, statSync, writeFileSync } from "node:fs";
|
|
13
13
|
import { createHash, randomUUID } from "node:crypto";
|
|
14
|
+
import { TextDecoder as TextDecoder$1 } from "node:util";
|
|
14
15
|
import { parseDocument } from "yaml";
|
|
15
16
|
import { fileURLToPath } from "node:url";
|
|
16
17
|
import pino from "pino";
|
|
@@ -420,6 +421,7 @@ function toAiSdkToolSet(definitions) {
|
|
|
420
421
|
//#region src/agent/tools/process-runner.ts
|
|
421
422
|
const DEFAULT_MAX_OUTPUT_BYTES$1 = 4e4;
|
|
422
423
|
const DEFAULT_MAX_OUTPUT_LINES = 1e3;
|
|
424
|
+
const TERMINAL_BENCH_MAX_OUTPUT_BYTES = 2e4;
|
|
423
425
|
async function runProcess(options) {
|
|
424
426
|
const startedAt = Date.now();
|
|
425
427
|
const pathEnv = options.pathEnv ?? process.env.PATH ?? "";
|
|
@@ -785,6 +787,8 @@ async function runBashCommand(workspaceRoot, args, options = {}) {
|
|
|
785
787
|
pathEnv: options.pathEnv,
|
|
786
788
|
timeoutMs: args.timeout_ms,
|
|
787
789
|
abortSignal: options.abortSignal,
|
|
790
|
+
outputLimitBytes: options.benchmarkProfile === "terminal-bench" ? TERMINAL_BENCH_MAX_OUTPUT_BYTES : void 0,
|
|
791
|
+
outputLimitLines: options.benchmarkProfile === "terminal-bench" ? 500 : void 0,
|
|
788
792
|
env: { NO_COLOR: "1" },
|
|
789
793
|
missingExecutableLabel: "bash"
|
|
790
794
|
});
|
|
@@ -3584,7 +3588,10 @@ const inspectCommandTool = defineTool({
|
|
|
3584
3588
|
description: "Run a narrowly validated read-only command for repository orientation.",
|
|
3585
3589
|
prompt: "inspect_command: run a safe read-only discovery command inside the workspace for quick repo orientation; prefer read_file, list_files, grep, and find_file for exact file tasks, and do not use it for builds, tests, installs, network, shell scripts, edits, or user-requested specific commands such as node --version, which node, or pnpm --version. To use it, reply with only JSON: {\"tool\":\"inspect_command\",\"args\":{\"command\":\"pwd && rg --files docs/plans | head -20\",\"workdir\":\".\",\"timeout_ms\":10000}}",
|
|
3586
3590
|
argsSchema: inspectCommandArgsSchema,
|
|
3587
|
-
execute: (context, args) => inspectWorkspaceCommand(context.workspaceRoot, args, {
|
|
3591
|
+
execute: (context, args) => inspectWorkspaceCommand(context.workspaceRoot, args, {
|
|
3592
|
+
pathEnv: context.pathEnv,
|
|
3593
|
+
benchmarkProfile: context.benchmarkProfile
|
|
3594
|
+
})
|
|
3588
3595
|
});
|
|
3589
3596
|
async function inspectWorkspaceCommand(workspaceRoot, args, options = {}) {
|
|
3590
3597
|
const startedAt = Date.now();
|
|
@@ -3596,7 +3603,8 @@ async function inspectWorkspaceCommand(workspaceRoot, args, options = {}) {
|
|
|
3596
3603
|
const result = await executePlan(decision.plan, {
|
|
3597
3604
|
cwd,
|
|
3598
3605
|
pathEnv: options.pathEnv ?? process.env.PATH ?? "",
|
|
3599
|
-
deadlineAt
|
|
3606
|
+
deadlineAt,
|
|
3607
|
+
benchmarkProfile: options.benchmarkProfile
|
|
3600
3608
|
});
|
|
3601
3609
|
const durationMs = Date.now() - startedAt;
|
|
3602
3610
|
return {
|
|
@@ -3634,14 +3642,16 @@ async function executePlan(plan, context) {
|
|
|
3634
3642
|
timedOut: true,
|
|
3635
3643
|
truncated
|
|
3636
3644
|
};
|
|
3645
|
+
const outputLimits = getOutputLimits(context.benchmarkProfile);
|
|
3637
3646
|
const result = await executePipeline(entry.pipeline, {
|
|
3638
3647
|
...context,
|
|
3639
3648
|
timeoutMs: remainingMs
|
|
3640
3649
|
});
|
|
3641
|
-
|
|
3642
|
-
|
|
3650
|
+
const nextStdout = appendBoundedOutput(stdout, result.stdout, outputLimits);
|
|
3651
|
+
stdout = nextStdout.output;
|
|
3652
|
+
const nextStderr = appendBoundedOutput(stderr, result.stderr, outputLimits);
|
|
3643
3653
|
stderr = nextStderr.output;
|
|
3644
|
-
truncated = truncated || result.truncated || nextStderr.truncated;
|
|
3654
|
+
truncated = truncated || result.truncated || nextStdout.truncated || nextStderr.truncated;
|
|
3645
3655
|
timedOut = timedOut || result.timedOut;
|
|
3646
3656
|
lastExitCode = result.exitCode;
|
|
3647
3657
|
if (result.missingExecutable || result.timedOut) return {
|
|
@@ -3681,7 +3691,8 @@ async function executePipeline(pipeline, context) {
|
|
|
3681
3691
|
timeoutMs: remainingMs
|
|
3682
3692
|
});
|
|
3683
3693
|
input = result.stdout;
|
|
3684
|
-
const
|
|
3694
|
+
const outputLimits = getOutputLimits(context.benchmarkProfile);
|
|
3695
|
+
const nextStderr = appendBoundedOutput(stderr, result.stderr, outputLimits);
|
|
3685
3696
|
stderr = nextStderr.output;
|
|
3686
3697
|
exitCode = result.exitCode;
|
|
3687
3698
|
timedOut = timedOut || result.timedOut;
|
|
@@ -3718,6 +3729,8 @@ async function executeSimpleCommand(command, input, context) {
|
|
|
3718
3729
|
cwd: context.cwd,
|
|
3719
3730
|
pathEnv: context.pathEnv,
|
|
3720
3731
|
timeoutMs: context.timeoutMs,
|
|
3732
|
+
outputLimitBytes: context.benchmarkProfile === "terminal-bench" ? TERMINAL_BENCH_MAX_OUTPUT_BYTES : void 0,
|
|
3733
|
+
outputLimitLines: context.benchmarkProfile === "terminal-bench" ? 500 : void 0,
|
|
3721
3734
|
missingExecutableLabel: "inspect_command"
|
|
3722
3735
|
});
|
|
3723
3736
|
return {
|
|
@@ -3740,6 +3753,13 @@ function shouldExecuteEntry(entry, previousExitCode) {
|
|
|
3740
3753
|
function getRemainingTimeoutMs(deadlineAt) {
|
|
3741
3754
|
return deadlineAt - Date.now();
|
|
3742
3755
|
}
|
|
3756
|
+
function getOutputLimits(benchmarkProfile) {
|
|
3757
|
+
if (benchmarkProfile !== "terminal-bench") return {};
|
|
3758
|
+
return {
|
|
3759
|
+
maxBytes: TERMINAL_BENCH_MAX_OUTPUT_BYTES,
|
|
3760
|
+
maxLines: 500
|
|
3761
|
+
};
|
|
3762
|
+
}
|
|
3743
3763
|
function formatInspectCommandContent(result) {
|
|
3744
3764
|
const sections = [];
|
|
3745
3765
|
sections.push(result.stdout.trimEnd() || "(no output)");
|
|
@@ -4107,16 +4127,30 @@ const planTodoTool = defineTool({
|
|
|
4107
4127
|
};
|
|
4108
4128
|
}
|
|
4109
4129
|
});
|
|
4130
|
+
//#endregion
|
|
4131
|
+
//#region src/agent/tools/read-file.ts
|
|
4132
|
+
const DEFAULT_MAX_UTF8_READ_BYTES = 512 * 1024;
|
|
4133
|
+
const TERMINAL_BENCH_MAX_UTF8_READ_BYTES = 64 * 1024;
|
|
4134
|
+
const SAMPLE_BYTES = 256;
|
|
4110
4135
|
const readFileTool = defineTool({
|
|
4111
4136
|
name: "read_file",
|
|
4112
4137
|
description: "Read a UTF-8 file inside the workspace.",
|
|
4113
|
-
prompt: "read_file: read a UTF-8 file inside the workspace. To use it, reply with only JSON: {\"tool\":\"read_file\",\"args\":{\"path\":\"package.json\"}}",
|
|
4114
|
-
argsSchema: z.object({
|
|
4138
|
+
prompt: "read_file: read a UTF-8 file inside the workspace. For large files, use offset and limit to read a focused byte range. To use it, reply with only JSON: {\"tool\":\"read_file\",\"args\":{\"path\":\"package.json\"}}",
|
|
4139
|
+
argsSchema: z.object({
|
|
4140
|
+
path: z.string(),
|
|
4141
|
+
offset: z.number().int().min(0).optional(),
|
|
4142
|
+
limit: z.number().int().min(1).max(DEFAULT_MAX_UTF8_READ_BYTES).optional()
|
|
4143
|
+
}),
|
|
4115
4144
|
parallelSafe: true,
|
|
4116
4145
|
mutatesWorkspace: false,
|
|
4117
4146
|
resourceKeys: (args) => [`file:${args.path}`],
|
|
4118
4147
|
execute: async (context, args) => {
|
|
4119
|
-
const result = await readWorkspaceFile(context.workspaceRoot, args.path
|
|
4148
|
+
const result = await readWorkspaceFile(context.workspaceRoot, args.path, {
|
|
4149
|
+
offset: args.offset,
|
|
4150
|
+
limit: args.limit,
|
|
4151
|
+
benchmarkProfile: context.benchmarkProfile,
|
|
4152
|
+
cache: context.readFileCache
|
|
4153
|
+
});
|
|
4120
4154
|
const projectInstructions = await resolveToolProjectInstructions(context, {
|
|
4121
4155
|
targetPath: args.path,
|
|
4122
4156
|
skipWhenTargetIsInstructionFile: true
|
|
@@ -4128,19 +4162,181 @@ const readFileTool = defineTool({
|
|
|
4128
4162
|
};
|
|
4129
4163
|
}
|
|
4130
4164
|
});
|
|
4131
|
-
async function readWorkspaceFile(workspaceRoot, path) {
|
|
4165
|
+
async function readWorkspaceFile(workspaceRoot, path, options = {}) {
|
|
4132
4166
|
const resolvedWorkspace = resolve(workspaceRoot);
|
|
4133
4167
|
const resolvedPath = isAbsolute(path) ? resolve(path) : resolve(resolvedWorkspace, path);
|
|
4134
4168
|
const relativePath = relative(resolvedWorkspace, resolvedPath);
|
|
4169
|
+
const maxReadBytes = getReadFileMaxBytes(options.benchmarkProfile);
|
|
4135
4170
|
if (relativePath.startsWith("..") || isAbsolute(relativePath)) throw new Error(`read_file can only read files inside the workspace: ${path}`);
|
|
4136
|
-
const
|
|
4171
|
+
const fileStat = await stat(resolvedPath);
|
|
4172
|
+
if (!fileStat.isFile()) throw new Error(`read_file can only read regular files: ${path}`);
|
|
4173
|
+
const offset = options.offset ?? 0;
|
|
4174
|
+
const requestedLimit = options.limit;
|
|
4175
|
+
const hasExplicitRange = options.offset !== void 0 || requestedLimit !== void 0;
|
|
4176
|
+
if (offset > fileStat.size) throw new Error(`read_file offset ${offset} is beyond end of file ${relativePath || "."} (${fileStat.size} bytes).`);
|
|
4177
|
+
if (!hasExplicitRange && fileStat.size > maxReadBytes) {
|
|
4178
|
+
const [sample, hash] = await Promise.all([readFileSample(resolvedPath, SAMPLE_BYTES), hashFile$2(resolvedPath)]);
|
|
4179
|
+
return {
|
|
4180
|
+
tool: "read_file",
|
|
4181
|
+
path: relativePath || ".",
|
|
4182
|
+
content: formatSkippedReadSummary({
|
|
4183
|
+
reason: "too_large",
|
|
4184
|
+
relativePath: relativePath || ".",
|
|
4185
|
+
bytes: fileStat.size,
|
|
4186
|
+
maxReadBytes,
|
|
4187
|
+
sample
|
|
4188
|
+
}),
|
|
4189
|
+
hash,
|
|
4190
|
+
skipped: "too_large",
|
|
4191
|
+
bytes: fileStat.size,
|
|
4192
|
+
warning: `Skipped reading ${relativePath || "."}: file is ${fileStat.size} bytes, above the ${maxReadBytes} byte read_file limit.`
|
|
4193
|
+
};
|
|
4194
|
+
}
|
|
4195
|
+
const hashPromise = hashFile$2(resolvedPath);
|
|
4196
|
+
const bytes = hasExplicitRange ? await readFileRange(resolvedPath, offset, Math.min(requestedLimit ?? maxReadBytes, maxReadBytes)) : await readFile(resolvedPath);
|
|
4197
|
+
const hash = await hashPromise;
|
|
4198
|
+
const length = bytes.length;
|
|
4199
|
+
const truncated = hasExplicitRange ? offset + length < fileStat.size : false;
|
|
4200
|
+
const cacheKey = makeReadFileCacheKey(relativePath || ".", hash, fileStat.size, offset, length);
|
|
4201
|
+
if (options.cache?.seen.has(cacheKey)) return {
|
|
4202
|
+
tool: "read_file",
|
|
4203
|
+
path: relativePath || ".",
|
|
4204
|
+
content: formatDedupedReadSummary({
|
|
4205
|
+
relativePath: relativePath || ".",
|
|
4206
|
+
bytes: fileStat.size,
|
|
4207
|
+
hash,
|
|
4208
|
+
offset,
|
|
4209
|
+
length
|
|
4210
|
+
}),
|
|
4211
|
+
hash,
|
|
4212
|
+
bytes: fileStat.size,
|
|
4213
|
+
offset,
|
|
4214
|
+
length,
|
|
4215
|
+
deduped: true,
|
|
4216
|
+
truncated,
|
|
4217
|
+
warning: `Skipped repeated read of unchanged ${relativePath || "."} bytes ${offset}-${offset + length}.`
|
|
4218
|
+
};
|
|
4219
|
+
if (looksBinary$1(bytes) || !isValidUtf8(bytes)) {
|
|
4220
|
+
const sample = bytes.subarray(0, SAMPLE_BYTES);
|
|
4221
|
+
return {
|
|
4222
|
+
tool: "read_file",
|
|
4223
|
+
path: relativePath || ".",
|
|
4224
|
+
content: formatSkippedReadSummary({
|
|
4225
|
+
reason: "binary",
|
|
4226
|
+
relativePath: relativePath || ".",
|
|
4227
|
+
bytes: fileStat.size,
|
|
4228
|
+
maxReadBytes,
|
|
4229
|
+
sample
|
|
4230
|
+
}),
|
|
4231
|
+
hash,
|
|
4232
|
+
skipped: "binary",
|
|
4233
|
+
bytes: fileStat.size,
|
|
4234
|
+
warning: `Skipped reading ${relativePath || "."}: file appears to be binary or non-UTF-8.`
|
|
4235
|
+
};
|
|
4236
|
+
}
|
|
4137
4237
|
const content = bytes.toString("utf8");
|
|
4138
|
-
|
|
4238
|
+
options.cache?.seen.set(cacheKey, {
|
|
4239
|
+
hash,
|
|
4240
|
+
bytes: fileStat.size,
|
|
4241
|
+
offset,
|
|
4242
|
+
length
|
|
4243
|
+
});
|
|
4244
|
+
const result = {
|
|
4139
4245
|
tool: "read_file",
|
|
4140
4246
|
path: relativePath || ".",
|
|
4141
|
-
content
|
|
4142
|
-
|
|
4247
|
+
content: formatReadFileContent({
|
|
4248
|
+
content,
|
|
4249
|
+
relativePath: relativePath || ".",
|
|
4250
|
+
bytes: fileStat.size,
|
|
4251
|
+
offset,
|
|
4252
|
+
length,
|
|
4253
|
+
truncated,
|
|
4254
|
+
ranged: hasExplicitRange
|
|
4255
|
+
}),
|
|
4256
|
+
hash
|
|
4143
4257
|
};
|
|
4258
|
+
if (hasExplicitRange) {
|
|
4259
|
+
result.bytes = fileStat.size;
|
|
4260
|
+
result.offset = offset;
|
|
4261
|
+
result.length = length;
|
|
4262
|
+
result.truncated = truncated;
|
|
4263
|
+
}
|
|
4264
|
+
return result;
|
|
4265
|
+
}
|
|
4266
|
+
function createReadFileCache() {
|
|
4267
|
+
return { seen: /* @__PURE__ */ new Map() };
|
|
4268
|
+
}
|
|
4269
|
+
function looksBinary$1(bytes) {
|
|
4270
|
+
return bytes.subarray(0, Math.min(bytes.length, SAMPLE_BYTES)).includes(0);
|
|
4271
|
+
}
|
|
4272
|
+
function isValidUtf8(bytes) {
|
|
4273
|
+
try {
|
|
4274
|
+
new TextDecoder$1("utf-8", { fatal: true }).decode(bytes);
|
|
4275
|
+
return true;
|
|
4276
|
+
} catch {
|
|
4277
|
+
return false;
|
|
4278
|
+
}
|
|
4279
|
+
}
|
|
4280
|
+
function formatSkippedReadSummary(options) {
|
|
4281
|
+
const reason = options.reason === "binary" ? "read_file did not return file contents because this file appears to be binary or non-UTF-8." : `read_file did not return file contents because this file is ${options.bytes} bytes, above the ${options.maxReadBytes} byte limit.`;
|
|
4282
|
+
const sampleHex = options.sample.length > 0 ? options.sample.toString("hex").match(/.{1,2}/g)?.join(" ") : "";
|
|
4283
|
+
return [
|
|
4284
|
+
reason,
|
|
4285
|
+
`path: ${options.relativePath}`,
|
|
4286
|
+
`bytes: ${options.bytes}`,
|
|
4287
|
+
sampleHex ? `first_${options.sample.length}_bytes_hex: ${sampleHex}` : "first_bytes_hex: <empty>",
|
|
4288
|
+
"Use read_file with offset and limit for a focused byte range, or shell inspection tools such as `file`, `xxd`, `readelf`, `objdump`, `strings`, or a focused parser instead of reading the whole file into context."
|
|
4289
|
+
].join("\n");
|
|
4290
|
+
}
|
|
4291
|
+
function formatReadFileContent(options) {
|
|
4292
|
+
if (!options.ranged) return options.content;
|
|
4293
|
+
return [`read_file range: ${options.relativePath} bytes ${options.offset}-${options.offset + options.length} of ${options.bytes}${options.truncated ? " (truncated)" : ""}`, options.content].join("\n");
|
|
4294
|
+
}
|
|
4295
|
+
function formatDedupedReadSummary(options) {
|
|
4296
|
+
return [
|
|
4297
|
+
"read_file did not return file contents because this exact unchanged file range was already shown in this session.",
|
|
4298
|
+
`path: ${options.relativePath}`,
|
|
4299
|
+
`bytes: ${options.bytes}`,
|
|
4300
|
+
`hash: ${options.hash}`,
|
|
4301
|
+
`range: ${options.offset}-${options.offset + options.length}`,
|
|
4302
|
+
"Use a different offset/limit if you need another part of the file."
|
|
4303
|
+
].join("\n");
|
|
4304
|
+
}
|
|
4305
|
+
async function readFileSample(path, maxBytes) {
|
|
4306
|
+
const handle = await open(path, "r");
|
|
4307
|
+
try {
|
|
4308
|
+
const sample = Buffer.alloc(maxBytes);
|
|
4309
|
+
const { bytesRead } = await handle.read(sample, 0, maxBytes, 0);
|
|
4310
|
+
return sample.subarray(0, bytesRead);
|
|
4311
|
+
} finally {
|
|
4312
|
+
await handle.close();
|
|
4313
|
+
}
|
|
4314
|
+
}
|
|
4315
|
+
async function readFileRange(path, offset, maxBytes) {
|
|
4316
|
+
const handle = await open(path, "r");
|
|
4317
|
+
try {
|
|
4318
|
+
const sample = Buffer.alloc(maxBytes);
|
|
4319
|
+
const { bytesRead } = await handle.read(sample, 0, maxBytes, offset);
|
|
4320
|
+
return sample.subarray(0, bytesRead);
|
|
4321
|
+
} finally {
|
|
4322
|
+
await handle.close();
|
|
4323
|
+
}
|
|
4324
|
+
}
|
|
4325
|
+
async function hashFile$2(path) {
|
|
4326
|
+
const hash = createHash("sha256");
|
|
4327
|
+
await new Promise((resolvePromise, reject) => {
|
|
4328
|
+
const stream = createReadStream(path);
|
|
4329
|
+
stream.on("data", (chunk) => hash.update(chunk));
|
|
4330
|
+
stream.on("error", reject);
|
|
4331
|
+
stream.on("end", resolvePromise);
|
|
4332
|
+
});
|
|
4333
|
+
return `sha256:${hash.digest("hex")}`;
|
|
4334
|
+
}
|
|
4335
|
+
function getReadFileMaxBytes(benchmarkProfile) {
|
|
4336
|
+
return benchmarkProfile === "terminal-bench" ? TERMINAL_BENCH_MAX_UTF8_READ_BYTES : DEFAULT_MAX_UTF8_READ_BYTES;
|
|
4337
|
+
}
|
|
4338
|
+
function makeReadFileCacheKey(path, hash, bytes, offset, length) {
|
|
4339
|
+
return `${path}\0${hash}\0${bytes}\0${offset}\0${length}`;
|
|
4144
4340
|
}
|
|
4145
4341
|
//#endregion
|
|
4146
4342
|
//#region src/agent/tools/command-policy.ts
|
|
@@ -4583,18 +4779,29 @@ const runValidatorTool = defineTool({
|
|
|
4583
4779
|
timeout_ms: z.number().int().min(100).max(6e5).optional().default(12e4)
|
|
4584
4780
|
}),
|
|
4585
4781
|
requiresExclusiveWorkspace: true,
|
|
4586
|
-
execute: async (context, args) => runValidatorCommand(context.workspaceRoot, args,
|
|
4782
|
+
execute: async (context, args) => runValidatorCommand(context.workspaceRoot, args, {
|
|
4783
|
+
pathEnv: context.pathEnv,
|
|
4784
|
+
abortSignal: context.abortSignal,
|
|
4785
|
+
benchmarkProfile: context.benchmarkProfile
|
|
4786
|
+
})
|
|
4587
4787
|
});
|
|
4588
|
-
async function runValidatorCommand(workspaceRoot, args,
|
|
4788
|
+
async function runValidatorCommand(workspaceRoot, args, pathEnvOrOptions, legacyAbortSignal) {
|
|
4789
|
+
const options = typeof pathEnvOrOptions === "string" ? {
|
|
4790
|
+
pathEnv: pathEnvOrOptions,
|
|
4791
|
+
abortSignal: legacyAbortSignal,
|
|
4792
|
+
benchmarkProfile: void 0
|
|
4793
|
+
} : pathEnvOrOptions ?? {};
|
|
4589
4794
|
const decision = await validateValidatorCommand(args, { workspaceRoot });
|
|
4590
4795
|
if (!decision.allowed) throw new Error(decision.reason);
|
|
4591
4796
|
const result = await runProcess({
|
|
4592
4797
|
executable: decision.plan.executable,
|
|
4593
4798
|
args: decision.plan.args,
|
|
4594
4799
|
cwd: decision.plan.cwd,
|
|
4595
|
-
pathEnv,
|
|
4800
|
+
pathEnv: options.pathEnv,
|
|
4596
4801
|
timeoutMs: args.timeout_ms,
|
|
4597
|
-
abortSignal,
|
|
4802
|
+
abortSignal: options.abortSignal,
|
|
4803
|
+
outputLimitBytes: options.benchmarkProfile === "terminal-bench" ? TERMINAL_BENCH_MAX_OUTPUT_BYTES : void 0,
|
|
4804
|
+
outputLimitLines: options.benchmarkProfile === "terminal-bench" ? 500 : void 0,
|
|
4598
4805
|
env: {
|
|
4599
4806
|
CI: "1",
|
|
4600
4807
|
NO_COLOR: "1"
|
|
@@ -12065,6 +12272,7 @@ async function executeToolCall(workspaceRoot, call, options = {}) {
|
|
|
12065
12272
|
projectInstructions: options.projectInstructions,
|
|
12066
12273
|
currentUserMessage: options.currentUserMessage,
|
|
12067
12274
|
benchmarkProfile: options.benchmarkProfile,
|
|
12275
|
+
readFileCache: options.readFileCache,
|
|
12068
12276
|
eventSink: options.eventSink,
|
|
12069
12277
|
abortSignal: options.abortSignal,
|
|
12070
12278
|
toolCallId: options.toolCallId
|
|
@@ -13319,6 +13527,7 @@ var TopchesterAgentRuntime = class TopchesterAgentRuntime {
|
|
|
13319
13527
|
const requireFinishTask = isFinishTaskRequiredByEnv() && isToolAllowed(permissions, "finish_task");
|
|
13320
13528
|
const projectInstructionToolState = { shownSourceKeys: /* @__PURE__ */ new Set() };
|
|
13321
13529
|
const persistedProjectInstructionKeys = /* @__PURE__ */ new Set();
|
|
13530
|
+
const readFileCache = createReadFileCache();
|
|
13322
13531
|
try {
|
|
13323
13532
|
for (let toolCalls = 0; toolCalls <= maxToolCallsPerTurn; toolCalls += 1) {
|
|
13324
13533
|
const startedAt = Date.now();
|
|
@@ -13504,6 +13713,7 @@ var TopchesterAgentRuntime = class TopchesterAgentRuntime {
|
|
|
13504
13713
|
projectInstructions: projectInstructionToolState,
|
|
13505
13714
|
currentUserMessage: message,
|
|
13506
13715
|
benchmarkProfile: options.benchmarkProfile,
|
|
13716
|
+
readFileCache,
|
|
13507
13717
|
abortSignal,
|
|
13508
13718
|
toolCallId: entry.toolCallId,
|
|
13509
13719
|
toolCatalog,
|
|
@@ -13575,6 +13785,7 @@ var TopchesterAgentRuntime = class TopchesterAgentRuntime {
|
|
|
13575
13785
|
projectInstructions: projectInstructionToolState,
|
|
13576
13786
|
currentUserMessage: message,
|
|
13577
13787
|
benchmarkProfile: options.benchmarkProfile,
|
|
13788
|
+
readFileCache,
|
|
13578
13789
|
abortSignal,
|
|
13579
13790
|
toolCallId: entry.toolCallId,
|
|
13580
13791
|
toolCatalog
|
|
@@ -13653,6 +13864,7 @@ var TopchesterAgentRuntime = class TopchesterAgentRuntime {
|
|
|
13653
13864
|
projectInstructions: projectInstructionToolState,
|
|
13654
13865
|
currentUserMessage: message,
|
|
13655
13866
|
benchmarkProfile: options.benchmarkProfile,
|
|
13867
|
+
readFileCache,
|
|
13656
13868
|
abortSignal,
|
|
13657
13869
|
toolCallId: toolCall.id,
|
|
13658
13870
|
toolCatalog,
|
|
@@ -14087,6 +14299,14 @@ function getToolCallDisplayDiff(result) {
|
|
|
14087
14299
|
function readMaxToolCallsPerTurn() {
|
|
14088
14300
|
const raw = process.env[MAX_TOOL_CALLS_PER_TURN_ENV]?.trim();
|
|
14089
14301
|
if (!raw) return DEFAULT_MAX_TOOL_CALLS_PER_TURN;
|
|
14302
|
+
if ([
|
|
14303
|
+
"0",
|
|
14304
|
+
"off",
|
|
14305
|
+
"false",
|
|
14306
|
+
"none",
|
|
14307
|
+
"unlimited",
|
|
14308
|
+
"disabled"
|
|
14309
|
+
].includes(raw.toLowerCase())) return Number.POSITIVE_INFINITY;
|
|
14090
14310
|
const parsed = Number(raw);
|
|
14091
14311
|
if (!Number.isInteger(parsed) || parsed <= 0) return DEFAULT_MAX_TOOL_CALLS_PER_TURN;
|
|
14092
14312
|
return parsed;
|
|
@@ -16554,4 +16774,4 @@ function formatDryRunSyncStatus(status) {
|
|
|
16554
16774
|
//#endregion
|
|
16555
16775
|
export { runTopchesterCli as t };
|
|
16556
16776
|
|
|
16557
|
-
//# sourceMappingURL=cli-
|
|
16777
|
+
//# sourceMappingURL=cli-CRhzHqMB.mjs.map
|