@strayl/agent 0.1.9 → 0.1.11
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/agent.js +36 -12
- package/package.json +1 -1
package/dist/agent.js
CHANGED
|
@@ -7201,6 +7201,9 @@ var LLMClient = class {
|
|
|
7201
7201
|
}
|
|
7202
7202
|
}
|
|
7203
7203
|
}
|
|
7204
|
+
if (choice.finish_reason) {
|
|
7205
|
+
console.error(`[LLM] finish_reason: ${choice.finish_reason}, partialToolCalls: ${partialToolCalls.size}`);
|
|
7206
|
+
}
|
|
7204
7207
|
if (choice.finish_reason === "tool_calls" || choice.finish_reason === "stop") {
|
|
7205
7208
|
if (!emittedToolCalls) {
|
|
7206
7209
|
emittedToolCalls = true;
|
|
@@ -7220,10 +7223,11 @@ var LLMClient = class {
|
|
|
7220
7223
|
};
|
|
7221
7224
|
}
|
|
7222
7225
|
}
|
|
7223
|
-
if (!emittedToolCalls) {
|
|
7226
|
+
if (!emittedToolCalls && partialToolCalls.size > 0) {
|
|
7227
|
+
console.error(`[LLM] Fallback tool call emit: ${partialToolCalls.size} partial calls`);
|
|
7224
7228
|
for (const [, partial] of partialToolCalls) {
|
|
7225
|
-
if (partial.id && partial.name
|
|
7226
|
-
yield { type: "tool_call_complete", id: partial.id, name: partial.name, arguments: partial.arguments };
|
|
7229
|
+
if (partial.id && partial.name) {
|
|
7230
|
+
yield { type: "tool_call_complete", id: partial.id, name: partial.name, arguments: partial.arguments || "{}" };
|
|
7227
7231
|
}
|
|
7228
7232
|
}
|
|
7229
7233
|
}
|
|
@@ -7431,7 +7435,11 @@ var ContextManager = class {
|
|
|
7431
7435
|
}
|
|
7432
7436
|
maybeTriggerPreSummarization(client, emitter) {
|
|
7433
7437
|
if (!this.shouldPreSummarize() || this.pendingSummary) return;
|
|
7434
|
-
this.pendingSummary = this.createSummary(client).catch(() =>
|
|
7438
|
+
this.pendingSummary = this.createSummary(client).catch((err) => {
|
|
7439
|
+
const msg = err instanceof Error ? err.message : String(err);
|
|
7440
|
+
emitter.emit({ type: "error", message: `Pre-summarization failed: ${msg}`, recoverable: true });
|
|
7441
|
+
return "";
|
|
7442
|
+
});
|
|
7435
7443
|
}
|
|
7436
7444
|
async applyPendingSummary(emitter) {
|
|
7437
7445
|
if (!this.pendingSummary) return false;
|
|
@@ -7454,7 +7462,10 @@ var ContextManager = class {
|
|
|
7454
7462
|
if (summary) {
|
|
7455
7463
|
this.replaceSummarizedMessages(summary, emitter);
|
|
7456
7464
|
}
|
|
7457
|
-
} catch {
|
|
7465
|
+
} catch (err) {
|
|
7466
|
+
const msg = err instanceof Error ? err.message : String(err);
|
|
7467
|
+
emitter.emit({ type: "error", message: `Summarization failed, falling back to trim: ${msg}`, recoverable: true });
|
|
7468
|
+
this.applyTrim();
|
|
7458
7469
|
}
|
|
7459
7470
|
}
|
|
7460
7471
|
async createSummary(client) {
|
|
@@ -12998,9 +13009,9 @@ var requestEnvVarTool = {
|
|
|
12998
13009
|
// src/tools/external/database.ts
|
|
12999
13010
|
async function dbFetch(path16, init, ctx) {
|
|
13000
13011
|
const env = ctx.env;
|
|
13001
|
-
if (env.STRAYL_LLM_DIRECT === "1") {
|
|
13012
|
+
if (env.STRAYL_LLM_DIRECT === "1" && env.STRAYL_AUTH_TOKEN) {
|
|
13002
13013
|
const dbApiUrl = env.DB_API_URL ?? "https://db.strayl.dev";
|
|
13003
|
-
const authToken = env.STRAYL_AUTH_TOKEN
|
|
13014
|
+
const authToken = env.STRAYL_AUTH_TOKEN;
|
|
13004
13015
|
const username2 = env.STRAYL_USERNAME ?? "";
|
|
13005
13016
|
const projectSlug2 = env.STRAYL_PROJECT_SLUG ?? "";
|
|
13006
13017
|
const url2 = `${dbApiUrl}/databases/${username2}/${projectSlug2}${path16}`;
|
|
@@ -13394,15 +13405,16 @@ function createPlanModeMiddleware(getMode) {
|
|
|
13394
13405
|
name: "planModeFilter",
|
|
13395
13406
|
filterTools: (tools) => {
|
|
13396
13407
|
const mode2 = getMode();
|
|
13408
|
+
const getName2 = (t) => t.type === "function" ? t.function.name : "";
|
|
13397
13409
|
if (mode2 === "plan") {
|
|
13398
|
-
return tools.filter((t) => !PLAN_MODE_BLOCKED.has(t
|
|
13410
|
+
return tools.filter((t) => !PLAN_MODE_BLOCKED.has(getName2(t)));
|
|
13399
13411
|
}
|
|
13400
13412
|
if (mode2 === "implement") {
|
|
13401
13413
|
return tools.filter(
|
|
13402
|
-
(t) => !IMPL_MODE_BLOCKED.has(t
|
|
13414
|
+
(t) => !IMPL_MODE_BLOCKED.has(getName2(t)) && getName2(t) !== "enterPlanMode"
|
|
13403
13415
|
);
|
|
13404
13416
|
}
|
|
13405
|
-
return tools.filter((t) => !IMPL_MODE_BLOCKED.has(t
|
|
13417
|
+
return tools.filter((t) => !IMPL_MODE_BLOCKED.has(getName2(t)));
|
|
13406
13418
|
},
|
|
13407
13419
|
wrapToolCall: async (call, next) => {
|
|
13408
13420
|
const mode2 = getMode();
|
|
@@ -13536,6 +13548,8 @@ async function runAgent(config) {
|
|
|
13536
13548
|
});
|
|
13537
13549
|
let iteration = 0;
|
|
13538
13550
|
const maxIterations = config.maxIterations ?? 200;
|
|
13551
|
+
let consecutiveLLMErrors = 0;
|
|
13552
|
+
const MAX_CONSECUTIVE_LLM_ERRORS = 5;
|
|
13539
13553
|
if (config.restoreCheckpoint) {
|
|
13540
13554
|
const cp = config.restoreCheckpoint;
|
|
13541
13555
|
context.restoreMessages(cp.messages);
|
|
@@ -13675,7 +13689,12 @@ ${IMPLEMENTATION_MODE_PROMPT2}`);
|
|
|
13675
13689
|
}
|
|
13676
13690
|
} catch (e) {
|
|
13677
13691
|
const msg = e instanceof Error ? e.message : String(e);
|
|
13678
|
-
|
|
13692
|
+
consecutiveLLMErrors++;
|
|
13693
|
+
if (consecutiveLLMErrors >= MAX_CONSECUTIVE_LLM_ERRORS) {
|
|
13694
|
+
emitter.emit({ type: "error", message: `LLM failed ${consecutiveLLMErrors} times in a row: ${msg}`, recoverable: false });
|
|
13695
|
+
break;
|
|
13696
|
+
}
|
|
13697
|
+
emitter.emit({ type: "error", message: `LLM error (${consecutiveLLMErrors}/${MAX_CONSECUTIVE_LLM_ERRORS}): ${msg}`, recoverable: true });
|
|
13679
13698
|
context.addAssistant(`[Error communicating with model: ${msg}]`);
|
|
13680
13699
|
continue;
|
|
13681
13700
|
}
|
|
@@ -13687,6 +13706,7 @@ ${IMPLEMENTATION_MODE_PROMPT2}`);
|
|
|
13687
13706
|
emitter.emit({ type: "session-end", usage: context.totalUsage(), exit_reason: "cancelled" });
|
|
13688
13707
|
return;
|
|
13689
13708
|
}
|
|
13709
|
+
consecutiveLLMErrors = 0;
|
|
13690
13710
|
context.addAssistant(assistantText, completedToolCalls.length > 0 ? completedToolCalls : void 0);
|
|
13691
13711
|
{
|
|
13692
13712
|
const used = context.estimateTokens();
|
|
@@ -13702,7 +13722,11 @@ ${IMPLEMENTATION_MODE_PROMPT2}`);
|
|
|
13702
13722
|
context_left_percent: leftPercent
|
|
13703
13723
|
});
|
|
13704
13724
|
}
|
|
13705
|
-
if (completedToolCalls.length === 0)
|
|
13725
|
+
if (completedToolCalls.length === 0) {
|
|
13726
|
+
console.error(`[Agent] Iteration ${iteration}: No tool calls. assistantText: ${assistantText.length} chars. Breaking.`);
|
|
13727
|
+
break;
|
|
13728
|
+
}
|
|
13729
|
+
console.error(`[Agent] Iteration ${iteration}: ${completedToolCalls.length} tool call(s): ${completedToolCalls.map((tc) => tc.function.name).join(", ")}`);
|
|
13706
13730
|
for (const tc of completedToolCalls) {
|
|
13707
13731
|
if (stdin.isCancelled()) {
|
|
13708
13732
|
context.addToolResult(tc.id, tc.function.name, JSON.stringify({ error: "Cancelled by user." }));
|