Architecture: How should the LLM provider layer be designed for Vitto?

Documentation for Sessions

🏗️ Architecture: How should the LLM provider layer be designed for Vitto?

Date: 2026-02-07
Time: 18:11:03 UTC
Session: gspace1-98.4
Agent: backend
Confidence: 92%
Status: ✅ Documented


📋 Decision Context

Question:

How should the LLM provider layer be designed for Vitto?

Task: Vitto LLM provider abstraction


🎯 Decision Made

Chosen:

Provider-agnostic LLM abstraction with BaseLLMProvider abstract class, concrete providers for Claude/OpenAI/Gemini, and ProviderFactory with env-driven selection and fallback chains

Options Considered:

  1. Direct Anthropic SDK only
  2. Provider-agnostic abstraction layer
  3. LangChain integration
  4. Custom SDK wrapper per provider

💭 Reasoning

Adopted from gmodules1's battle-tested BaseLLMProvider pattern. Unified interface (sendMessage/streamMessage) with each provider translating to/from native format (Anthropic tool_use blocks, OpenAI function_calling, Google functionCall). Tool definitions are provider-agnostic — ToolRegistry stores unified format, provider adapts at call time. Env-driven via VITTO_LLM_PROVIDER with automatic fallback to next healthy provider.


📁 Files Involved


🔗 Related


Auto-generated by MCP Smart Consolidation