@probelabs/probe 0.6.0-rc166 → 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 +291 -3
- 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 +1291 -161
- package/build/agent/mcp/built-in-server.js +464 -0
- package/cjs/agent/ProbeAgent.cjs +8979 -6698
- package/cjs/index.cjs +9030 -6749
- package/package.json +2 -1
- package/src/agent/ProbeAgent.js +291 -3
- 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/README.md
CHANGED
|
@@ -352,6 +352,45 @@ const agent = new ProbeAgent({
|
|
|
352
352
|
|
|
353
353
|
**Note:** MCP tools are automatically initialized when needed (lazy initialization), so you don't need to call `agent.initialize()` when using the SDK.
|
|
354
354
|
|
|
355
|
+
## Claude Code Integration
|
|
356
|
+
|
|
357
|
+
ProbeAgent now supports Claude Code's `claude` command for zero-configuration usage in Claude Code environments. See the [Claude Code Integration Guide](./docs/CLAUDE_CODE_INTEGRATION.md) for full details.
|
|
358
|
+
|
|
359
|
+
### Quick Start
|
|
360
|
+
|
|
361
|
+
```javascript
|
|
362
|
+
import { ProbeAgent } from '@probelabs/probe';
|
|
363
|
+
|
|
364
|
+
// Works automatically if claude command is installed!
|
|
365
|
+
const agent = new ProbeAgent({
|
|
366
|
+
allowedFolders: ['/path/to/your/code']
|
|
367
|
+
});
|
|
368
|
+
|
|
369
|
+
await agent.initialize();
|
|
370
|
+
const response = await agent.answer('Explain how this codebase works');
|
|
371
|
+
```
|
|
372
|
+
|
|
373
|
+
### Auto-Fallback
|
|
374
|
+
|
|
375
|
+
ProbeAgent automatically detects and uses Claude Code when:
|
|
376
|
+
- No API keys are configured (no ANTHROPIC_API_KEY, OPENAI_API_KEY, etc.)
|
|
377
|
+
- The `claude` command is available on your system
|
|
378
|
+
|
|
379
|
+
Priority order:
|
|
380
|
+
1. Explicit `provider: 'claude-code'`
|
|
381
|
+
2. API keys (Anthropic, OpenAI, Google, AWS)
|
|
382
|
+
3. Claude command (auto-detected)
|
|
383
|
+
|
|
384
|
+
### Features
|
|
385
|
+
|
|
386
|
+
- **Zero Configuration**: No API keys needed in Claude Code environments
|
|
387
|
+
- **Black-box Operation**: Claude Code handles its own agentic loop
|
|
388
|
+
- **Tool Event Extraction**: Visibility into internal tool usage
|
|
389
|
+
- **Built-in MCP Server**: Provides Probe's semantic search tools
|
|
390
|
+
- **Auto-fallback**: Seamlessly switches based on environment
|
|
391
|
+
|
|
392
|
+
For complete documentation, examples, and troubleshooting, see [docs/CLAUDE_CODE_INTEGRATION.md](./docs/CLAUDE_CODE_INTEGRATION.md).
|
|
393
|
+
|
|
355
394
|
## API Reference
|
|
356
395
|
|
|
357
396
|
### Search
|
|
@@ -221,6 +221,9 @@ export class ProbeAgent {
|
|
|
221
221
|
this.fallbackConfig = options.fallback || null;
|
|
222
222
|
this.fallbackManager = null; // Will be initialized in initializeModel
|
|
223
223
|
|
|
224
|
+
// Engine support - minimal interface for multi-engine compatibility
|
|
225
|
+
this.engine = null; // Will be set in initializeModel or getEngine
|
|
226
|
+
|
|
224
227
|
// Initialize the AI model
|
|
225
228
|
this.initializeModel();
|
|
226
229
|
|
|
@@ -301,6 +304,31 @@ export class ProbeAgent {
|
|
|
301
304
|
* This method initializes MCP and merges MCP tools into the tool list, and loads history from storage
|
|
302
305
|
*/
|
|
303
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
|
+
|
|
304
332
|
// Load history from storage adapter
|
|
305
333
|
try {
|
|
306
334
|
const history = await this.storageAdapter.loadHistory(this.sessionId);
|
|
@@ -452,6 +480,21 @@ export class ProbeAgent {
|
|
|
452
480
|
}
|
|
453
481
|
}
|
|
454
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
|
+
|
|
455
498
|
/**
|
|
456
499
|
* Initialize the AI model based on available API keys and forced provider setting
|
|
457
500
|
*/
|
|
@@ -465,6 +508,19 @@ export class ProbeAgent {
|
|
|
465
508
|
return;
|
|
466
509
|
}
|
|
467
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
|
+
|
|
468
524
|
// Get API keys from environment variables
|
|
469
525
|
// Support both ANTHROPIC_API_KEY and ANTHROPIC_AUTH_TOKEN (used by Z.AI)
|
|
470
526
|
const anthropicApiKey = process.env.ANTHROPIC_API_KEY || process.env.ANTHROPIC_AUTH_TOKEN;
|
|
@@ -534,7 +590,12 @@ export class ProbeAgent {
|
|
|
534
590
|
this.initializeBedrockModel(awsAccessKeyId, awsSecretAccessKey, awsRegion, awsSessionToken, awsApiKey, awsBedrockBaseUrl, modelName);
|
|
535
591
|
this.initializeFallbackManager('bedrock', modelName);
|
|
536
592
|
} else {
|
|
537
|
-
|
|
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
|
|
538
599
|
}
|
|
539
600
|
}
|
|
540
601
|
|
|
@@ -609,6 +670,60 @@ export class ProbeAgent {
|
|
|
609
670
|
* @private
|
|
610
671
|
*/
|
|
611
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
|
+
|
|
612
727
|
// Initialize retry manager if not already created
|
|
613
728
|
if (!this.retryManager) {
|
|
614
729
|
this.retryManager = new RetryManager({
|
|
@@ -752,6 +867,56 @@ export class ProbeAgent {
|
|
|
752
867
|
}
|
|
753
868
|
}
|
|
754
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
|
+
|
|
755
920
|
/**
|
|
756
921
|
* Process assistant response content and detect/load image references
|
|
757
922
|
* @param {string} content - The assistant's response content
|
|
@@ -1138,6 +1303,56 @@ export class ProbeAgent {
|
|
|
1138
1303
|
}
|
|
1139
1304
|
}
|
|
1140
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
|
+
|
|
1141
1356
|
/**
|
|
1142
1357
|
* Get the system message with instructions for the AI (XML Tool Format)
|
|
1143
1358
|
*/
|
|
@@ -1532,6 +1747,79 @@ When troubleshooting:
|
|
|
1532
1747
|
const baseMaxIterations = this.maxIterations || MAX_TOOL_ITERATIONS;
|
|
1533
1748
|
const maxIterations = options.schema ? baseMaxIterations + 4 : baseMaxIterations;
|
|
1534
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
|
+
|
|
1535
1823
|
if (this.debug) {
|
|
1536
1824
|
console.log(`[DEBUG] Starting agentic flow for question: ${message.substring(0, 100)}...`);
|
|
1537
1825
|
if (options.schema) {
|
|
@@ -1539,7 +1827,7 @@ When troubleshooting:
|
|
|
1539
1827
|
}
|
|
1540
1828
|
}
|
|
1541
1829
|
|
|
1542
|
-
// Tool iteration loop
|
|
1830
|
+
// Tool iteration loop (only for non-Claude Code engines)
|
|
1543
1831
|
while (currentIteration < maxIterations && !completionAttempted) {
|
|
1544
1832
|
currentIteration++;
|
|
1545
1833
|
if (this.cancelled) throw new Error('Request was cancelled by the user');
|
|
@@ -1612,7 +1900,7 @@ When troubleshooting:
|
|
|
1612
1900
|
const messagesForAI = this.prepareMessagesWithImages(currentMessages);
|
|
1613
1901
|
|
|
1614
1902
|
const result = await this.streamTextWithRetryAndFallback({
|
|
1615
|
-
model: this.provider(this.model),
|
|
1903
|
+
model: this.provider ? this.provider(this.model) : this.model,
|
|
1616
1904
|
messages: messagesForAI,
|
|
1617
1905
|
maxTokens: maxResponseTokens,
|
|
1618
1906
|
temperature: 0.3,
|