open-agents-ai 0.187.472 → 0.187.473

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -520540,6 +520540,8 @@ TASK: ${task}` : task;
520540
520540
  let sameToolFailStreak = 0;
520541
520541
  let sameToolFailName = null;
520542
520542
  const recentToolResults = /* @__PURE__ */ new Map();
520543
+ const dedupHitCount = /* @__PURE__ */ new Map();
520544
+ const DEDUP_ESCALATION_THRESHOLD = 3;
520543
520545
  const toolCallBudget = /* @__PURE__ */ new Map();
520544
520546
  const loopTier = this.options.modelTier ?? "large";
520545
520547
  const toolBudgets = loopTier === "small" ? { web_search: 6, web_fetch: 4, list_directory: 12, find_files: 10, grep_search: 12 } : loopTier === "medium" ? { web_search: 10, web_fetch: 8, list_directory: 18, find_files: 14, grep_search: 18 } : { web_search: 20, web_fetch: 15, list_directory: 30, find_files: 20, grep_search: 30 };
@@ -521417,9 +521419,31 @@ ${cachedEntry2.result.slice(0, 500)}` : `[BLOCKED — the observer confirmed thi
521417
521419
  turn,
521418
521420
  timestamp: (/* @__PURE__ */ new Date()).toISOString()
521419
521421
  });
521422
+ const hits = (dedupHitCount.get(toolFingerprint) ?? 0) + 1;
521423
+ dedupHitCount.set(toolFingerprint, hits);
521424
+ if (hits >= DEDUP_ESCALATION_THRESHOLD) {
521425
+ const argPreview = JSON.stringify(tc.arguments ?? {}).slice(0, 200);
521426
+ const blockMsg = `[FORCED PROGRESS BLOCK — you have called ${tc.name}(${argPreview}) ${hits} times with identical arguments and received the cached result each time. The data is not changing. You are stuck in a read-only loop instead of advancing the plan.
521427
+
521428
+ REQUIRED before this tool will run again with these arguments:
521429
+ • file_write or file_edit, OR
521430
+ • todo_write that advances the plan, OR
521431
+ • task_complete (if all phases are done).
521432
+
521433
+ If you genuinely need this same data again, call a DIFFERENT tool first (one of the three above). Until then, refer to your conversation history — the result of this exact call is already there.]`;
521434
+ this.emit({
521435
+ type: "tool_result",
521436
+ toolName: tc.name,
521437
+ success: false,
521438
+ content: blockMsg.slice(0, 120),
521439
+ turn,
521440
+ timestamp: (/* @__PURE__ */ new Date()).toISOString()
521441
+ });
521442
+ return { tc, output: blockMsg };
521443
+ }
521420
521444
  const header = cachedEntry.compacted ? `[RE-SERVED FROM CACHE — the original result was compacted from context. Here is the data again. No need to call this tool again.]
521421
521445
 
521422
- ` : `[DUPLICATE CALL — you already called ${tc.name} with these exact arguments. The result is identical. Do NOT call this again. Use the data you already have to make progress.]
521446
+ ` : `[DUPLICATE CALL #${hits} — you already called ${tc.name} with these exact arguments. The result is identical. Do NOT call this again. Use the data you already have to make progress. One more identical call will trigger a hard progress block.]
521423
521447
 
521424
521448
  `;
521425
521449
  const truncatedCache = cachedEntry.result.length > 500 ? cachedEntry.result.slice(0, 500) + `
@@ -521821,12 +521845,18 @@ ${cachedEntry2.result.slice(0, 500)}` : `[BLOCKED — the observer confirmed thi
521821
521845
  }
521822
521846
  if (isReadLike && result.success) {
521823
521847
  recentToolResults.set(toolFingerprint, { result: (result.output ?? "").slice(0, 2e3), compacted: false });
521824
- if (recentToolResults.size > 50) {
521848
+ if (recentToolResults.size > 500) {
521825
521849
  const firstKey = recentToolResults.keys().next().value;
521826
- if (firstKey !== void 0)
521850
+ if (firstKey !== void 0) {
521827
521851
  recentToolResults.delete(firstKey);
521852
+ dedupHitCount.delete(firstKey);
521853
+ }
521828
521854
  }
521829
521855
  }
521856
+ const isMutating = ["file_write", "file_edit", "batch_edit", "file_patch"].includes(tc.name) || tc.name === "shell" && !this._isShellCommandReadOnly(tc.arguments?.["command"] ?? tc.arguments?.["cmd"] ?? "");
521857
+ if (isMutating && result.success && dedupHitCount.size > 0) {
521858
+ dedupHitCount.clear();
521859
+ }
521830
521860
  if (result.success) {
521831
521861
  this._recentFailures = this._recentFailures.filter((f2) => f2.fingerprint !== toolFingerprint);
521832
521862
  }
@@ -1,12 +1,12 @@
1
1
  {
2
2
  "name": "open-agents-ai",
3
- "version": "0.187.472",
3
+ "version": "0.187.473",
4
4
  "lockfileVersion": 3,
5
5
  "requires": true,
6
6
  "packages": {
7
7
  "": {
8
8
  "name": "open-agents-ai",
9
- "version": "0.187.472",
9
+ "version": "0.187.473",
10
10
  "hasInstallScript": true,
11
11
  "license": "CC-BY-NC-4.0",
12
12
  "dependencies": {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "open-agents-ai",
3
- "version": "0.187.472",
3
+ "version": "0.187.473",
4
4
  "description": "AI coding agent powered by open-source models (Ollama/vLLM) — interactive TUI with agentic tool-calling loop",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",