clodds 1.6.1 → 1.6.3

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.
@@ -16336,9 +16336,14 @@ async function createAgentManager(config, feeds, db, sessionManager, sendMessage
16336
16336
  'claude-3-opus-20240229': 200000,
16337
16337
  };
16338
16338
  const modelContextWindow = MODEL_CONTEXT_WINDOWS[modelId] || 200000;
16339
+ // Estimate fixed overhead: tool definitions + system prompt (these don't change during conversation)
16340
+ const toolsTokenEstimate = (0, context_1.estimateTokens)(JSON.stringify(tools), modelId);
16341
+ const systemTokenEstimate = (0, context_1.estimateTokens)(finalSystemPrompt, modelId);
16342
+ // Reserve enough for tools + system prompt + response buffer
16343
+ const reserveForFixed = toolsTokenEstimate + systemTokenEstimate + 4096;
16339
16344
  const contextConfig = {
16340
16345
  maxTokens: modelContextWindow,
16341
- reserveTokens: 4096,
16346
+ reserveTokens: reserveForFixed,
16342
16347
  compactThreshold: 0.85,
16343
16348
  minMessagesAfterCompact: 6,
16344
16349
  summarizer,
@@ -16349,14 +16354,14 @@ async function createAgentManager(config, feeds, db, sessionManager, sendMessage
16349
16354
  similarity: memory?.cosineSimilarity,
16350
16355
  };
16351
16356
  const contextManager = (0, context_1.createContextManager)(contextConfig, memory);
16352
- const effectiveMaxTokens = (contextConfig.maxTokens ?? 128000) - (contextConfig.reserveTokens ?? 4096);
16357
+ const effectiveMaxTokens = (contextConfig.maxTokens ?? 128000) - reserveForFixed;
16353
16358
  const estimateSubmitTokens = () => {
16354
16359
  const system = (0, context_1.estimateTokens)(finalSystemPrompt, modelId);
16355
16360
  const msgs = messages.reduce((sum, m) => {
16356
16361
  const content = typeof m.content === 'string' ? m.content : JSON.stringify(m.content);
16357
16362
  return sum + (0, context_1.estimateTokens)(content, modelId) + 4;
16358
16363
  }, 0);
16359
- return system + msgs;
16364
+ return system + msgs + toolsTokenEstimate;
16360
16365
  };
16361
16366
  // Add all messages to context manager for tracking
16362
16367
  for (const msg of messages) {
@@ -16366,10 +16371,9 @@ async function createAgentManager(config, feeds, db, sessionManager, sendMessage
16366
16371
  content,
16367
16372
  });
16368
16373
  }
16369
- // Add system prompt tokens
16370
- const systemTokens = (0, context_1.estimateTokens)(finalSystemPrompt, modelId);
16371
16374
  // Check if we need to compact before first API call
16372
- const guard = contextManager.checkGuard(systemTokens);
16375
+ // (tools + system prompt are already accounted for in reserveTokens)
16376
+ const guard = contextManager.checkGuard();
16373
16377
  if (guard.shouldCompact) {
16374
16378
  logger_1.logger.info({ percentUsed: guard.percentUsed }, 'Context approaching limit, compacting');
16375
16379
  // Trigger compaction:before hook
@@ -16411,6 +16415,11 @@ async function createAgentManager(config, feeds, db, sessionManager, sendMessage
16411
16415
  }
16412
16416
  const initialEstimate = estimateSubmitTokens();
16413
16417
  logger_1.logger.info({ tokens: initialEstimate, max: effectiveMaxTokens }, 'Token estimate before submit');
16418
+ // Safety: if still over limit after compaction, return a friendly error
16419
+ if (initialEstimate > effectiveMaxTokens * 1.1) {
16420
+ logger_1.logger.warn({ tokens: initialEstimate, max: effectiveMaxTokens }, 'Context exceeds limit even after compaction');
16421
+ return 'This conversation has gotten too long for me to process. Please start a new conversation and I\'ll be happy to help!';
16422
+ }
16414
16423
  let response = await createMessage({
16415
16424
  model: modelId,
16416
16425
  max_tokens: 1024,
@@ -16515,7 +16524,7 @@ async function createAgentManager(config, feeds, db, sessionManager, sendMessage
16515
16524
  content,
16516
16525
  });
16517
16526
  }
16518
- const loopGuard = contextManager.checkGuard(0);
16527
+ const loopGuard = contextManager.checkGuard();
16519
16528
  if (loopGuard.shouldCompact) {
16520
16529
  logger_1.logger.info({ percentUsed: loopGuard.percentUsed }, 'Compacting context during tool loop');
16521
16530
  const loopCompactResult = await contextManager.compact();
@@ -16533,6 +16542,11 @@ async function createAgentManager(config, feeds, db, sessionManager, sendMessage
16533
16542
  }
16534
16543
  const loopEstimate = estimateSubmitTokens();
16535
16544
  logger_1.logger.info({ tokens: loopEstimate, max: effectiveMaxTokens }, 'Token estimate before submit (tool loop)');
16545
+ // Safety: bail if over limit during tool loop
16546
+ if (loopEstimate > effectiveMaxTokens * 1.1) {
16547
+ logger_1.logger.warn({ tokens: loopEstimate, max: effectiveMaxTokens }, 'Context exceeds limit during tool loop');
16548
+ break;
16549
+ }
16536
16550
  response = await createMessage({
16537
16551
  model: modelId,
16538
16552
  max_tokens: 1024,