Add Ollama and LiteLLM backend support (v0.2.0)
All checks were successful
Build App / build-macos (push) Successful in 2m25s
Build App / build-windows (push) Successful in 3m27s
Build App / build-linux (push) Successful in 4m31s
Build App / sync-to-github (push) Successful in 9s

Add two new auth modes for projects alongside Anthropic and Bedrock:
- Ollama: connect to local or remote Ollama servers via ANTHROPIC_BASE_URL
- LiteLLM: connect through a LiteLLM proxy gateway to 100+ model providers

Both modes inject ANTHROPIC_BASE_URL and ANTHROPIC_AUTH_TOKEN env vars into
the container, with optional model override via ANTHROPIC_MODEL. LiteLLM
API keys are stored securely in the OS keychain. Config changes trigger
automatic container recreation via fingerprinting.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-03-11 13:05:52 -07:00
parent 2dce2993cc
commit 93deab68a7
10 changed files with 337 additions and 7 deletions

View File

@@ -34,6 +34,11 @@ fn store_secrets_for_project(project: &Project) -> Result<(), String> {
secure::store_project_secret(&project.id, "aws-bearer-token", v)?;
}
}
if let Some(ref litellm) = project.litellm_config {
if let Some(ref v) = litellm.api_key {
secure::store_project_secret(&project.id, "litellm-api-key", v)?;
}
}
Ok(())
}
@@ -51,6 +56,10 @@ fn load_secrets_for_project(project: &mut Project) {
bedrock.aws_bearer_token = secure::get_project_secret(&project.id, "aws-bearer-token")
.unwrap_or(None);
}
if let Some(ref mut litellm) = project.litellm_config {
litellm.api_key = secure::get_project_secret(&project.id, "litellm-api-key")
.unwrap_or(None);
}
}
/// Resolve enabled MCP servers and filter to Docker-only ones.
@@ -180,6 +189,22 @@ pub async fn start_project_container(
}
}
if project.auth_mode == AuthMode::Ollama {
let ollama = project.ollama_config.as_ref()
.ok_or_else(|| "Ollama auth mode selected but no Ollama configuration found.".to_string())?;
if ollama.base_url.is_empty() {
return Err("Ollama base URL is required.".to_string());
}
}
if project.auth_mode == AuthMode::LiteLlm {
let litellm = project.litellm_config.as_ref()
.ok_or_else(|| "LiteLLM auth mode selected but no LiteLLM configuration found.".to_string())?;
if litellm.base_url.is_empty() {
return Err("LiteLLM base URL is required.".to_string());
}
}
// Update status to starting
state.projects_store.update_status(&project_id, ProjectStatus::Starting)?;