@probelabs/probe 0.6.0-rc165 → 0.6.0-rc167
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/README.md +39 -0
- package/build/agent/ProbeAgent.js +316 -7
- package/build/agent/engines/enhanced-claude-code.js +595 -0
- package/build/agent/engines/enhanced-vercel.js +83 -0
- package/build/agent/engines/vercel.js +62 -0
- package/build/agent/index.js +1335 -166
- package/build/agent/mcp/built-in-server.js +464 -0
- package/build/agent/tools.js +25 -0
- package/cjs/agent/ProbeAgent.cjs +9023 -6703
- package/cjs/index.cjs +9074 -6754
- package/package.json +2 -1
- package/src/agent/ProbeAgent.js +316 -7
- package/src/agent/engines/enhanced-claude-code.js +595 -0
- package/src/agent/engines/enhanced-vercel.js +83 -0
- package/src/agent/engines/vercel.js +62 -0
- package/src/agent/mcp/built-in-server.js +464 -0
- package/src/agent/tools.js +25 -0
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@probelabs/probe",
|
|
3
|
-
"version": "0.6.0-
|
|
3
|
+
"version": "0.6.0-rc167",
|
|
4
4
|
"description": "Node.js wrapper for the probe code search tool",
|
|
5
5
|
"main": "src/index.js",
|
|
6
6
|
"module": "src/index.js",
|
|
@@ -77,6 +77,7 @@
|
|
|
77
77
|
"@ai-sdk/anthropic": "^2.0.8",
|
|
78
78
|
"@ai-sdk/google": "^2.0.14",
|
|
79
79
|
"@ai-sdk/openai": "^2.0.10",
|
|
80
|
+
"@anthropic-ai/claude-agent-sdk": "^0.1.46",
|
|
80
81
|
"@modelcontextprotocol/sdk": "^1.0.0",
|
|
81
82
|
"@probelabs/maid": "^0.0.21",
|
|
82
83
|
"adm-zip": "^0.5.16",
|
package/src/agent/ProbeAgent.js
CHANGED
|
@@ -27,6 +27,7 @@ import {
|
|
|
27
27
|
bashToolDefinition,
|
|
28
28
|
listFilesToolDefinition,
|
|
29
29
|
searchFilesToolDefinition,
|
|
30
|
+
readImageToolDefinition,
|
|
30
31
|
attemptCompletionToolDefinition,
|
|
31
32
|
implementToolDefinition,
|
|
32
33
|
editToolDefinition,
|
|
@@ -220,6 +221,9 @@ export class ProbeAgent {
|
|
|
220
221
|
this.fallbackConfig = options.fallback || null;
|
|
221
222
|
this.fallbackManager = null; // Will be initialized in initializeModel
|
|
222
223
|
|
|
224
|
+
// Engine support - minimal interface for multi-engine compatibility
|
|
225
|
+
this.engine = null; // Will be set in initializeModel or getEngine
|
|
226
|
+
|
|
223
227
|
// Initialize the AI model
|
|
224
228
|
this.initializeModel();
|
|
225
229
|
|
|
@@ -300,6 +304,31 @@ export class ProbeAgent {
|
|
|
300
304
|
* This method initializes MCP and merges MCP tools into the tool list, and loads history from storage
|
|
301
305
|
*/
|
|
302
306
|
async initialize() {
|
|
307
|
+
// Check if we need to auto-detect claude-code provider
|
|
308
|
+
// This happens when no API keys are set and no provider is specified
|
|
309
|
+
if (!this.provider && !this.clientApiProvider && this.apiType !== 'claude-code') {
|
|
310
|
+
// Check if initializeModel marked as uninitialized (no API keys)
|
|
311
|
+
if (this.apiType === 'uninitialized') {
|
|
312
|
+
const claudeAvailable = await this.isClaudeCommandAvailable();
|
|
313
|
+
if (claudeAvailable) {
|
|
314
|
+
if (this.debug) {
|
|
315
|
+
console.log('[DEBUG] No API keys found, but claude command detected');
|
|
316
|
+
console.log('[DEBUG] Auto-switching to claude-code provider');
|
|
317
|
+
}
|
|
318
|
+
// Set provider to claude-code
|
|
319
|
+
this.clientApiProvider = 'claude-code';
|
|
320
|
+
this.provider = null;
|
|
321
|
+
this.model = this.clientApiModel || 'claude-3-5-sonnet-20241022';
|
|
322
|
+
this.apiType = 'claude-code';
|
|
323
|
+
} else {
|
|
324
|
+
// Neither API keys nor claude command available
|
|
325
|
+
throw new Error('No API key provided and claude command not found. Please either:\n' +
|
|
326
|
+
'1. Set an API key: ANTHROPIC_API_KEY, OPENAI_API_KEY, GOOGLE_GENERATIVE_AI_API_KEY, or AWS credentials\n' +
|
|
327
|
+
'2. Install claude command from https://docs.claude.com/en/docs/claude-code');
|
|
328
|
+
}
|
|
329
|
+
}
|
|
330
|
+
}
|
|
331
|
+
|
|
303
332
|
// Load history from storage adapter
|
|
304
333
|
try {
|
|
305
334
|
const history = await this.storageAdapter.loadHistory(this.sessionId);
|
|
@@ -399,6 +428,23 @@ export class ProbeAgent {
|
|
|
399
428
|
delegate: wrappedTools.delegateToolInstance,
|
|
400
429
|
listFiles: listFilesToolInstance,
|
|
401
430
|
searchFiles: searchFilesToolInstance,
|
|
431
|
+
readImage: {
|
|
432
|
+
execute: async (params) => {
|
|
433
|
+
const imagePath = params.path;
|
|
434
|
+
if (!imagePath) {
|
|
435
|
+
throw new Error('Image path is required');
|
|
436
|
+
}
|
|
437
|
+
|
|
438
|
+
// Load the image using the existing loadImageIfValid method
|
|
439
|
+
const loaded = await this.loadImageIfValid(imagePath);
|
|
440
|
+
|
|
441
|
+
if (!loaded) {
|
|
442
|
+
throw new Error(`Failed to load image: ${imagePath}. The file may not exist, be too large, have an unsupported format, or be outside allowed directories.`);
|
|
443
|
+
}
|
|
444
|
+
|
|
445
|
+
return `Image loaded successfully: ${imagePath}. The image is now available for analysis in the conversation.`;
|
|
446
|
+
}
|
|
447
|
+
}
|
|
402
448
|
};
|
|
403
449
|
|
|
404
450
|
// Add bash tool if enabled
|
|
@@ -434,6 +480,21 @@ export class ProbeAgent {
|
|
|
434
480
|
}
|
|
435
481
|
}
|
|
436
482
|
|
|
483
|
+
/**
|
|
484
|
+
* Check if claude command is available on the system
|
|
485
|
+
* @returns {Promise<boolean>} True if claude command is available
|
|
486
|
+
* @private
|
|
487
|
+
*/
|
|
488
|
+
async isClaudeCommandAvailable() {
|
|
489
|
+
try {
|
|
490
|
+
const { execSync } = await import('child_process');
|
|
491
|
+
execSync('claude --version', { stdio: 'ignore' });
|
|
492
|
+
return true;
|
|
493
|
+
} catch (error) {
|
|
494
|
+
return false;
|
|
495
|
+
}
|
|
496
|
+
}
|
|
497
|
+
|
|
437
498
|
/**
|
|
438
499
|
* Initialize the AI model based on available API keys and forced provider setting
|
|
439
500
|
*/
|
|
@@ -447,6 +508,19 @@ export class ProbeAgent {
|
|
|
447
508
|
return;
|
|
448
509
|
}
|
|
449
510
|
|
|
511
|
+
// Skip API key requirement for Claude Code (uses built-in access in Claude Code)
|
|
512
|
+
if (this.clientApiProvider === 'claude-code' || process.env.USE_CLAUDE_CODE === 'true') {
|
|
513
|
+
// Claude Code engine will be initialized lazily in getEngine()
|
|
514
|
+
// Set minimal defaults for compatibility
|
|
515
|
+
this.provider = null;
|
|
516
|
+
this.model = modelName || 'claude-3-5-sonnet-20241022';
|
|
517
|
+
this.apiType = 'claude-code';
|
|
518
|
+
if (this.debug) {
|
|
519
|
+
console.log('[DEBUG] Claude Code engine selected - will use built-in access if available');
|
|
520
|
+
}
|
|
521
|
+
return;
|
|
522
|
+
}
|
|
523
|
+
|
|
450
524
|
// Get API keys from environment variables
|
|
451
525
|
// Support both ANTHROPIC_API_KEY and ANTHROPIC_AUTH_TOKEN (used by Z.AI)
|
|
452
526
|
const anthropicApiKey = process.env.ANTHROPIC_API_KEY || process.env.ANTHROPIC_AUTH_TOKEN;
|
|
@@ -516,7 +590,12 @@ export class ProbeAgent {
|
|
|
516
590
|
this.initializeBedrockModel(awsAccessKeyId, awsSecretAccessKey, awsRegion, awsSessionToken, awsApiKey, awsBedrockBaseUrl, modelName);
|
|
517
591
|
this.initializeFallbackManager('bedrock', modelName);
|
|
518
592
|
} else {
|
|
519
|
-
|
|
593
|
+
// No API keys found - mark for potential claude-code auto-detection in initialize()
|
|
594
|
+
this.apiType = 'uninitialized';
|
|
595
|
+
if (this.debug) {
|
|
596
|
+
console.log('[DEBUG] No API keys found - will check for claude command in initialize()');
|
|
597
|
+
}
|
|
598
|
+
// Don't throw error yet - will be checked in initialize() method
|
|
520
599
|
}
|
|
521
600
|
}
|
|
522
601
|
|
|
@@ -591,6 +670,60 @@ export class ProbeAgent {
|
|
|
591
670
|
* @private
|
|
592
671
|
*/
|
|
593
672
|
async streamTextWithRetryAndFallback(options) {
|
|
673
|
+
// Check if we should use Claude Code engine
|
|
674
|
+
if (this.clientApiProvider === 'claude-code' || process.env.USE_CLAUDE_CODE === 'true') {
|
|
675
|
+
try {
|
|
676
|
+
const engine = await this.getEngine();
|
|
677
|
+
if (engine && engine.query) {
|
|
678
|
+
// Convert Vercel AI SDK format to engine format
|
|
679
|
+
// Extract the ORIGINAL user message as the main prompt (skip any warning messages)
|
|
680
|
+
// Look for user messages that are NOT the warning message
|
|
681
|
+
const userMessages = options.messages.filter(m =>
|
|
682
|
+
m.role === 'user' &&
|
|
683
|
+
!m.content.includes('WARNING: You have reached the maximum tool iterations limit')
|
|
684
|
+
);
|
|
685
|
+
const lastUserMessage = userMessages[userMessages.length - 1];
|
|
686
|
+
const prompt = lastUserMessage ? lastUserMessage.content : '';
|
|
687
|
+
|
|
688
|
+
// Pass system message and other options
|
|
689
|
+
const engineOptions = {
|
|
690
|
+
maxTokens: options.maxTokens,
|
|
691
|
+
temperature: options.temperature,
|
|
692
|
+
messages: options.messages,
|
|
693
|
+
systemPrompt: options.messages.find(m => m.role === 'system')?.content
|
|
694
|
+
};
|
|
695
|
+
|
|
696
|
+
// Get the engine's query result (async generator)
|
|
697
|
+
const engineStream = engine.query(prompt, engineOptions);
|
|
698
|
+
|
|
699
|
+
// Create a text stream that extracts text from engine messages
|
|
700
|
+
async function* createTextStream() {
|
|
701
|
+
for await (const message of engineStream) {
|
|
702
|
+
if (message.type === 'text' && message.content) {
|
|
703
|
+
yield message.content;
|
|
704
|
+
} else if (typeof message === 'string') {
|
|
705
|
+
// If engine returns plain strings, pass them through
|
|
706
|
+
yield message;
|
|
707
|
+
}
|
|
708
|
+
// Ignore other message types for the text stream
|
|
709
|
+
}
|
|
710
|
+
}
|
|
711
|
+
|
|
712
|
+
// Wrap the engine result to match streamText interface
|
|
713
|
+
return {
|
|
714
|
+
textStream: createTextStream(),
|
|
715
|
+
usage: Promise.resolve({}), // Engine should handle its own usage tracking
|
|
716
|
+
// Add other streamText-compatible properties as needed
|
|
717
|
+
};
|
|
718
|
+
}
|
|
719
|
+
} catch (error) {
|
|
720
|
+
if (this.debug) {
|
|
721
|
+
console.log(`[DEBUG] Failed to use Claude Code engine, falling back to Vercel:`, error.message);
|
|
722
|
+
}
|
|
723
|
+
// Fall through to use Vercel engine as fallback
|
|
724
|
+
}
|
|
725
|
+
}
|
|
726
|
+
|
|
594
727
|
// Initialize retry manager if not already created
|
|
595
728
|
if (!this.retryManager) {
|
|
596
729
|
this.retryManager = new RetryManager({
|
|
@@ -734,6 +867,56 @@ export class ProbeAgent {
|
|
|
734
867
|
}
|
|
735
868
|
}
|
|
736
869
|
|
|
870
|
+
/**
|
|
871
|
+
* Get or create the AI engine based on configuration
|
|
872
|
+
* @returns {Promise<Object>} Engine interface
|
|
873
|
+
* @private
|
|
874
|
+
*/
|
|
875
|
+
async getEngine() {
|
|
876
|
+
// If engine already created, return it
|
|
877
|
+
if (this.engine) {
|
|
878
|
+
return this.engine;
|
|
879
|
+
}
|
|
880
|
+
|
|
881
|
+
// Try Claude Code engine if requested
|
|
882
|
+
if (this.clientApiProvider === 'claude-code' || process.env.USE_CLAUDE_CODE === 'true') {
|
|
883
|
+
try {
|
|
884
|
+
const { createEnhancedClaudeCLIEngine } = await import('./engines/enhanced-claude-code.js');
|
|
885
|
+
|
|
886
|
+
// For Claude Code, use a cleaner system prompt without XML formatting
|
|
887
|
+
// since it has native MCP support for tools
|
|
888
|
+
const systemPrompt = this.customPrompt || this.getClaudeNativeSystemPrompt();
|
|
889
|
+
|
|
890
|
+
this.engine = await createEnhancedClaudeCLIEngine({
|
|
891
|
+
agent: this, // Pass reference to ProbeAgent for tool access
|
|
892
|
+
systemPrompt: systemPrompt,
|
|
893
|
+
customPrompt: this.customPrompt,
|
|
894
|
+
sessionId: this.options?.sessionId,
|
|
895
|
+
debug: this.debug,
|
|
896
|
+
allowedTools: this.allowedTools // Pass tool filtering configuration
|
|
897
|
+
});
|
|
898
|
+
if (this.debug) {
|
|
899
|
+
console.log('[DEBUG] Using Claude Code engine with Probe tools');
|
|
900
|
+
if (this.customPrompt) {
|
|
901
|
+
console.log('[DEBUG] Using custom prompt/persona');
|
|
902
|
+
}
|
|
903
|
+
}
|
|
904
|
+
return this.engine;
|
|
905
|
+
} catch (error) {
|
|
906
|
+
console.warn('[WARNING] Failed to load Claude Code engine:', error.message);
|
|
907
|
+
console.warn('[WARNING] Falling back to Vercel AI SDK');
|
|
908
|
+
this.clientApiProvider = null;
|
|
909
|
+
}
|
|
910
|
+
}
|
|
911
|
+
// Default to enhanced Vercel AI SDK (wraps existing logic)
|
|
912
|
+
const { createEnhancedVercelEngine } = await import('./engines/enhanced-vercel.js');
|
|
913
|
+
this.engine = createEnhancedVercelEngine(this);
|
|
914
|
+
if (this.debug) {
|
|
915
|
+
console.log('[DEBUG] Using Vercel AI SDK engine');
|
|
916
|
+
}
|
|
917
|
+
return this.engine;
|
|
918
|
+
}
|
|
919
|
+
|
|
737
920
|
/**
|
|
738
921
|
* Process assistant response content and detect/load image references
|
|
739
922
|
* @param {string} content - The assistant's response content
|
|
@@ -1120,6 +1303,56 @@ export class ProbeAgent {
|
|
|
1120
1303
|
}
|
|
1121
1304
|
}
|
|
1122
1305
|
|
|
1306
|
+
/**
|
|
1307
|
+
* Get system prompt for Claude native engines (CLI/SDK) without XML formatting
|
|
1308
|
+
* These engines have native MCP support and don't need XML instructions
|
|
1309
|
+
*/
|
|
1310
|
+
getClaudeNativeSystemPrompt() {
|
|
1311
|
+
let systemPrompt = '';
|
|
1312
|
+
|
|
1313
|
+
// Add persona/role if configured
|
|
1314
|
+
if (this.predefinedPrompt) {
|
|
1315
|
+
const personaPrompt = getPromptByType(this.predefinedPrompt);
|
|
1316
|
+
if (personaPrompt?.system) {
|
|
1317
|
+
systemPrompt += personaPrompt.system + '\n\n';
|
|
1318
|
+
}
|
|
1319
|
+
}
|
|
1320
|
+
|
|
1321
|
+
// Add high-level instructions about when to use tools
|
|
1322
|
+
systemPrompt += `You have access to powerful code search and analysis tools through MCP:
|
|
1323
|
+
- search: Find code patterns using semantic search
|
|
1324
|
+
- extract: Extract specific code sections with context
|
|
1325
|
+
- query: Use AST patterns for structural code matching
|
|
1326
|
+
- listFiles: Browse directory contents
|
|
1327
|
+
- searchFiles: Find files by name patterns`;
|
|
1328
|
+
|
|
1329
|
+
if (this.enableBash) {
|
|
1330
|
+
systemPrompt += `\n- bash: Execute bash commands for system operations`;
|
|
1331
|
+
}
|
|
1332
|
+
|
|
1333
|
+
systemPrompt += `\n
|
|
1334
|
+
When exploring code:
|
|
1335
|
+
1. Start with search to find relevant code patterns
|
|
1336
|
+
2. Use extract to get detailed context when needed
|
|
1337
|
+
3. Prefer focused, specific searches over broad queries
|
|
1338
|
+
4. Combine multiple tools to build complete understanding`;
|
|
1339
|
+
|
|
1340
|
+
// Add workspace context
|
|
1341
|
+
if (this.allowedFolders && this.allowedFolders.length > 0) {
|
|
1342
|
+
systemPrompt += `\n\nWorkspace: ${this.allowedFolders.join(', ')}`;
|
|
1343
|
+
}
|
|
1344
|
+
|
|
1345
|
+
// Add repository structure if available
|
|
1346
|
+
if (this.fileList) {
|
|
1347
|
+
systemPrompt += `\n\n# Repository Structure\n`;
|
|
1348
|
+
systemPrompt += `You are working with a repository located at: ${this.allowedFolders[0]}\n\n`;
|
|
1349
|
+
systemPrompt += `Here's an overview of the repository structure (showing up to 100 most relevant files):\n\n`;
|
|
1350
|
+
systemPrompt += '```\n' + this.fileList + '\n```\n';
|
|
1351
|
+
}
|
|
1352
|
+
|
|
1353
|
+
return systemPrompt;
|
|
1354
|
+
}
|
|
1355
|
+
|
|
1123
1356
|
/**
|
|
1124
1357
|
* Get the system message with instructions for the AI (XML Tool Format)
|
|
1125
1358
|
*/
|
|
@@ -1172,6 +1405,9 @@ export class ProbeAgent {
|
|
|
1172
1405
|
if (isToolAllowed('searchFiles')) {
|
|
1173
1406
|
toolDefinitions += `${searchFilesToolDefinition}\n`;
|
|
1174
1407
|
}
|
|
1408
|
+
if (isToolAllowed('readImage')) {
|
|
1409
|
+
toolDefinitions += `${readImageToolDefinition}\n`;
|
|
1410
|
+
}
|
|
1175
1411
|
|
|
1176
1412
|
// Edit tools (require both allowEdit flag AND allowedTools permission)
|
|
1177
1413
|
if (this.allowEdit && isToolAllowed('implement')) {
|
|
@@ -1262,6 +1498,7 @@ Available Tools:
|
|
|
1262
1498
|
- extract: Extract specific code blocks or lines from files.
|
|
1263
1499
|
- listFiles: List files and directories in a specified location.
|
|
1264
1500
|
- searchFiles: Find files matching a glob pattern with recursive search capability.
|
|
1501
|
+
- readImage: Read and load an image file for AI analysis.
|
|
1265
1502
|
${this.allowEdit ? '- implement: Implement a feature or fix a bug using aider.\n- edit: Edit files using exact string replacement.\n- create: Create new files with specified content.\n' : ''}${this.enableDelegate ? '- delegate: Delegate big distinct tasks to specialized probe subagents.\n' : ''}${this.enableBash ? '- bash: Execute bash commands for system operations.\n' : ''}
|
|
1266
1503
|
- attempt_completion: Finalize the task and provide the result to the user.
|
|
1267
1504
|
- attempt_complete: Quick completion using previous response (shorthand).
|
|
@@ -1510,6 +1747,79 @@ When troubleshooting:
|
|
|
1510
1747
|
const baseMaxIterations = this.maxIterations || MAX_TOOL_ITERATIONS;
|
|
1511
1748
|
const maxIterations = options.schema ? baseMaxIterations + 4 : baseMaxIterations;
|
|
1512
1749
|
|
|
1750
|
+
// Check if we're using Claude Code engine which handles its own agentic loop
|
|
1751
|
+
const isClaudeCode = this.clientApiProvider === 'claude-code' || process.env.USE_CLAUDE_CODE === 'true';
|
|
1752
|
+
|
|
1753
|
+
if (isClaudeCode) {
|
|
1754
|
+
// For Claude Code, bypass the tool loop entirely - it handles its own internal dialogue
|
|
1755
|
+
if (this.debug) {
|
|
1756
|
+
console.log(`[DEBUG] Using Claude Code engine - bypassing tool loop (black box mode)`);
|
|
1757
|
+
console.log(`[DEBUG] Sending question directly to Claude Code: ${message.substring(0, 100)}...`);
|
|
1758
|
+
}
|
|
1759
|
+
|
|
1760
|
+
// Send the message directly to Claude Code and collect the response
|
|
1761
|
+
try {
|
|
1762
|
+
const engine = await this.getEngine();
|
|
1763
|
+
if (engine && engine.query) {
|
|
1764
|
+
let assistantResponseContent = '';
|
|
1765
|
+
let toolBatch = null;
|
|
1766
|
+
|
|
1767
|
+
// Query Claude Code directly with the message and schema
|
|
1768
|
+
for await (const chunk of engine.query(message, options)) {
|
|
1769
|
+
if (chunk.type === 'text' && chunk.content) {
|
|
1770
|
+
assistantResponseContent += chunk.content;
|
|
1771
|
+
if (options.onStream) {
|
|
1772
|
+
options.onStream(chunk.content);
|
|
1773
|
+
}
|
|
1774
|
+
} else if (chunk.type === 'toolBatch' && chunk.tools) {
|
|
1775
|
+
// Store tool batch for processing after response
|
|
1776
|
+
toolBatch = chunk.tools;
|
|
1777
|
+
if (this.debug) {
|
|
1778
|
+
console.log(`[DEBUG] Received batch of ${chunk.tools.length} tool events from Claude Code`);
|
|
1779
|
+
}
|
|
1780
|
+
} else if (chunk.type === 'error') {
|
|
1781
|
+
throw chunk.error;
|
|
1782
|
+
}
|
|
1783
|
+
}
|
|
1784
|
+
|
|
1785
|
+
// Emit tool events after response is complete (batch mode)
|
|
1786
|
+
if (toolBatch && toolBatch.length > 0 && this.events) {
|
|
1787
|
+
if (this.debug) {
|
|
1788
|
+
console.log(`[DEBUG] Emitting ${toolBatch.length} tool events from Claude Code batch`);
|
|
1789
|
+
}
|
|
1790
|
+
for (const toolEvent of toolBatch) {
|
|
1791
|
+
this.events.emit('toolCall', toolEvent);
|
|
1792
|
+
}
|
|
1793
|
+
}
|
|
1794
|
+
|
|
1795
|
+
// Update history with the exchange
|
|
1796
|
+
this.history.push(userMessage);
|
|
1797
|
+
this.history.push({
|
|
1798
|
+
role: 'assistant',
|
|
1799
|
+
content: assistantResponseContent
|
|
1800
|
+
});
|
|
1801
|
+
|
|
1802
|
+
// Store conversation history
|
|
1803
|
+
// TODO: storeConversationHistory is not yet implemented for Claude Code
|
|
1804
|
+
// await this.storeConversationHistory(this.history, oldHistoryLength);
|
|
1805
|
+
|
|
1806
|
+
// Emit completion hook
|
|
1807
|
+
await this.hooks.emit(HOOK_TYPES.COMPLETION, {
|
|
1808
|
+
sessionId: this.sessionId,
|
|
1809
|
+
prompt: message,
|
|
1810
|
+
response: assistantResponseContent
|
|
1811
|
+
});
|
|
1812
|
+
|
|
1813
|
+
return assistantResponseContent;
|
|
1814
|
+
}
|
|
1815
|
+
} catch (error) {
|
|
1816
|
+
if (this.debug) {
|
|
1817
|
+
console.error('[DEBUG] Claude Code error:', error);
|
|
1818
|
+
}
|
|
1819
|
+
throw error;
|
|
1820
|
+
}
|
|
1821
|
+
}
|
|
1822
|
+
|
|
1513
1823
|
if (this.debug) {
|
|
1514
1824
|
console.log(`[DEBUG] Starting agentic flow for question: ${message.substring(0, 100)}...`);
|
|
1515
1825
|
if (options.schema) {
|
|
@@ -1517,7 +1827,7 @@ When troubleshooting:
|
|
|
1517
1827
|
}
|
|
1518
1828
|
}
|
|
1519
1829
|
|
|
1520
|
-
// Tool iteration loop
|
|
1830
|
+
// Tool iteration loop (only for non-Claude Code engines)
|
|
1521
1831
|
while (currentIteration < maxIterations && !completionAttempted) {
|
|
1522
1832
|
currentIteration++;
|
|
1523
1833
|
if (this.cancelled) throw new Error('Request was cancelled by the user');
|
|
@@ -1590,7 +1900,7 @@ When troubleshooting:
|
|
|
1590
1900
|
const messagesForAI = this.prepareMessagesWithImages(currentMessages);
|
|
1591
1901
|
|
|
1592
1902
|
const result = await this.streamTextWithRetryAndFallback({
|
|
1593
|
-
model: this.provider(this.model),
|
|
1903
|
+
model: this.provider ? this.provider(this.model) : this.model,
|
|
1594
1904
|
messages: messagesForAI,
|
|
1595
1905
|
maxTokens: maxResponseTokens,
|
|
1596
1906
|
temperature: 0.3,
|
|
@@ -1700,10 +2010,8 @@ When troubleshooting:
|
|
|
1700
2010
|
console.log(`[DEBUG] Assistant response (${assistantResponseContent.length} chars): ${assistantPreview}`);
|
|
1701
2011
|
}
|
|
1702
2012
|
|
|
1703
|
-
//
|
|
1704
|
-
|
|
1705
|
-
await this.processImageReferences(assistantResponseContent);
|
|
1706
|
-
}
|
|
2013
|
+
// Images in assistant responses are not automatically processed
|
|
2014
|
+
// AI can use the readImage tool to explicitly request reading an image
|
|
1707
2015
|
|
|
1708
2016
|
// Parse tool call from response with valid tools list
|
|
1709
2017
|
// Build validTools based on allowedTools configuration (same pattern as getSystemMessage)
|
|
@@ -1713,6 +2021,7 @@ When troubleshooting:
|
|
|
1713
2021
|
if (this.allowedTools.isEnabled('extract')) validTools.push('extract');
|
|
1714
2022
|
if (this.allowedTools.isEnabled('listFiles')) validTools.push('listFiles');
|
|
1715
2023
|
if (this.allowedTools.isEnabled('searchFiles')) validTools.push('searchFiles');
|
|
2024
|
+
if (this.allowedTools.isEnabled('readImage')) validTools.push('readImage');
|
|
1716
2025
|
if (this.allowedTools.isEnabled('attempt_completion')) validTools.push('attempt_completion');
|
|
1717
2026
|
|
|
1718
2027
|
// Edit tools (require both allowEdit flag AND allowedTools permission)
|