@myagentroam/agent 0.10.45 → 0.10.47

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.
@@ -5,7 +5,10 @@ import { isOpenAiResponsesRecoverableStreamError } from './openai-responses.js';
5
5
  /** Retry only classified recoverable failures within the attempt budget; never retry cancellation. */
6
6
  export async function recoverModelStream(error, retryState, signal) {
7
7
  if (signal.aborted ||
8
- !(isRetryableModelRequestError(error) ||
8
+ !((error instanceof MarAgentError &&
9
+ error.code === 'MAR_AGENT_MODEL_OUTPUT_INCOMPLETE' &&
10
+ error.retryable) ||
11
+ isRetryableModelRequestError(error) ||
9
12
  isOpenAiResponsesRecoverableStreamError(error) ||
10
13
  isAnthropicRecoverableStreamError(error)) ||
11
14
  retryState.attempts >= modelRetryMaxAttempts(retryState))
@@ -261,7 +261,6 @@ export class ExecutionLoop {
261
261
  }
262
262
  else
263
263
  pendingTools.splice(0, pendingTools.length);
264
- modelRetryState.attempts = 0;
265
264
  }
266
265
  catch (error) {
267
266
  this.planOutputPrefixes.clear();
@@ -351,6 +350,7 @@ export class ExecutionLoop {
351
350
  content: modelOutputContinuationMessage
352
351
  };
353
352
  this.finalAnswer = '';
353
+ modelRetryState.attempts = 0;
354
354
  continue;
355
355
  }
356
356
  maxOutputContinuationUsed = false;
@@ -369,19 +369,27 @@ export class ExecutionLoop {
369
369
  }
370
370
  if (input.mailbox.hasPending() && (await input.mailbox.append())) {
371
371
  this.finalAnswer = '';
372
+ modelRetryState.attempts = 0;
372
373
  continue;
373
374
  }
374
375
  if (stop === 'completed' && !sawTool) {
375
- input.mailbox.close();
376
376
  const compactSummary = mode === 'compact' ? this.finalAnswer.trim() : '';
377
377
  if (mode === 'compact' && !compactSummary)
378
378
  throw new MarAgentError('MAR_AGENT_COMPACT_FAILED', 'Compaction returned an empty handoff.');
379
- if (mode !== 'compact' && !this.finalAnswer.trim())
380
- throw new MarAgentError(input.sourceType === 'subagent'
379
+ if (mode !== 'compact' && !this.finalAnswer.trim()) {
380
+ const error = new MarAgentError(input.sourceType === 'subagent'
381
381
  ? 'MAR_AGENT_SUBAGENT_FAILED'
382
382
  : 'MAR_AGENT_MODEL_OUTPUT_INCOMPLETE', input.sourceType === 'subagent'
383
383
  ? 'Subagent completed without a final summary.'
384
- : 'Model completed without an answer or tool request.');
384
+ : 'Model completed without an answer or tool request.', { retryable: input.sourceType !== 'subagent' });
385
+ this.planOutputPrefixes.clear();
386
+ if (await recoverModelStream(error, modelRetryState, input.recoverySignal())) {
387
+ this.finalAnswer = '';
388
+ continue;
389
+ }
390
+ throw error;
391
+ }
392
+ input.mailbox.close();
385
393
  return {
386
394
  finalAnswer: this.finalAnswer,
387
395
  ...(latestUsage === undefined ? {} : { usage: latestUsage })
@@ -389,6 +397,7 @@ export class ExecutionLoop {
389
397
  }
390
398
  if (!sawTool && stop !== 'pause')
391
399
  throw new MarAgentError('MAR_AGENT_MODEL_OUTPUT_INCOMPLETE', 'Model did not complete or request a tool.');
400
+ modelRetryState.attempts = 0;
392
401
  }
393
402
  }
394
403
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@myagentroam/agent",
3
- "version": "0.10.45",
3
+ "version": "0.10.47",
4
4
  "description": "Embeddable MAR coding agent SDK and CLI.",
5
5
  "license": "Apache-2.0",
6
6
  "type": "module",