diff --git a/apps/client/src/widgets/llm_chat/llm_chat_panel.ts b/apps/client/src/widgets/llm_chat/llm_chat_panel.ts index 57a95fd5b..fc6a28f26 100644 --- a/apps/client/src/widgets/llm_chat/llm_chat_panel.ts +++ b/apps/client/src/widgets/llm_chat/llm_chat_panel.ts @@ -69,7 +69,6 @@ export default class LlmChatPanel extends BasicWidget { totalTokens?: number; }; } = { - model: 'default', temperature: 0.7, toolExecutions: [] }; @@ -332,7 +331,7 @@ export default class LlmChatPanel extends BasicWidget { sources: this.sources || [], // Add metadata metadata: { - model: this.metadata?.model || 'default', + model: this.metadata?.model || undefined, provider: this.metadata?.provider || undefined, temperature: this.metadata?.temperature || 0.7, lastUpdated: new Date().toISOString(), diff --git a/apps/server/src/services/llm/chat/rest_chat_service.ts b/apps/server/src/services/llm/chat/rest_chat_service.ts index 432cc6e08..eb57276bd 100644 --- a/apps/server/src/services/llm/chat/rest_chat_service.ts +++ b/apps/server/src/services/llm/chat/rest_chat_service.ts @@ -267,7 +267,8 @@ class RestChatService { systemPrompt: session?.messages.find(m => m.role === 'system')?.content, temperature: session?.metadata.temperature, maxTokens: session?.metadata.maxTokens, - model: session?.metadata.model, + // Get the user's preferred model if session model is 'default' or not set + model: await this.getPreferredModel(session?.metadata.model), // Set stream based on request type, but ensure it's explicitly a boolean value // GET requests or format=stream parameter indicates streaming should be used stream: !!(req.method === 'GET' || req.query.format === 'stream' || req.query.stream === 'true'), @@ -702,6 +703,59 @@ class RestChatService { // Create from Chat Note return await this.createSessionFromChatNote(noteId); } + + /** + * Get the user's preferred model + */ + async getPreferredModel(sessionModel?: string): Promise { + // If the session already has a valid model (not 'default'), use it + if (sessionModel && sessionModel !== 'default') { + return sessionModel; + } + + try { + // Get provider precedence list (same logic as model selection stage) + const providerPrecedence = await options.getOption('aiProviderPrecedence'); + let defaultProvider = 'openai'; + let defaultModelName = 'gpt-3.5-turbo'; + + if (providerPrecedence) { + // Parse provider precedence list + let providers: string[] = []; + if (providerPrecedence.includes(',')) { + providers = providerPrecedence.split(',').map(p => p.trim()); + } else if (providerPrecedence.startsWith('[') && providerPrecedence.endsWith(']')) { + providers = JSON.parse(providerPrecedence); + } else { + providers = [providerPrecedence]; + } + + // Get first available provider + if (providers.length > 0) { + const firstProvider = providers[0]; + defaultProvider = firstProvider; + + // Get provider-specific default model + if (firstProvider === 'openai') { + const model = await options.getOption('openaiDefaultModel'); + if (model) defaultModelName = model; + } else if (firstProvider === 'anthropic') { + const model = await options.getOption('anthropicDefaultModel'); + if (model) defaultModelName = model; + } else if (firstProvider === 'ollama') { + const model = await options.getOption('ollamaDefaultModel'); + if (model) defaultModelName = model; + } + } + } + + log.info(`Selected user's preferred model: ${defaultModelName} from provider: ${defaultProvider}`); + return defaultModelName; + } catch (error) { + log.error(`Error getting user's preferred model: ${error}`); + return 'gpt-3.5-turbo'; // Fallback + } + } } // Create singleton instance