centicodehelp 0.2.0__tar.gz

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.
Files changed (39) hide show
  1. centicodehelp-0.2.0/PKG-INFO +79 -0
  2. centicodehelp-0.2.0/README.md +64 -0
  3. centicodehelp-0.2.0/pyproject.toml +28 -0
  4. centicodehelp-0.2.0/setup.cfg +4 -0
  5. centicodehelp-0.2.0/src/centicodehelp/__init__.py +3 -0
  6. centicodehelp-0.2.0/src/centicodehelp/ai/llm_client.py +150 -0
  7. centicodehelp-0.2.0/src/centicodehelp/ai/prompts.py +63 -0
  8. centicodehelp-0.2.0/src/centicodehelp/ai/providers.py +195 -0
  9. centicodehelp-0.2.0/src/centicodehelp/ai/reviewer.py +139 -0
  10. centicodehelp-0.2.0/src/centicodehelp/analysis/binary_analyzer.py +124 -0
  11. centicodehelp-0.2.0/src/centicodehelp/analysis/detector.py +80 -0
  12. centicodehelp-0.2.0/src/centicodehelp/analysis/parser.py +41 -0
  13. centicodehelp-0.2.0/src/centicodehelp/analysis/static_analyzer.py +194 -0
  14. centicodehelp-0.2.0/src/centicodehelp/cli/banner.py +60 -0
  15. centicodehelp-0.2.0/src/centicodehelp/cli/commands/ai.py +128 -0
  16. centicodehelp-0.2.0/src/centicodehelp/cli/commands/analyze.py +389 -0
  17. centicodehelp-0.2.0/src/centicodehelp/cli/commands/check.py +91 -0
  18. centicodehelp-0.2.0/src/centicodehelp/cli/commands/config.py +67 -0
  19. centicodehelp-0.2.0/src/centicodehelp/cli/commands/fix.py +170 -0
  20. centicodehelp-0.2.0/src/centicodehelp/cli/commands/providers.py +81 -0
  21. centicodehelp-0.2.0/src/centicodehelp/cli/commands/scan.py +129 -0
  22. centicodehelp-0.2.0/src/centicodehelp/cli/commands/setup.py +93 -0
  23. centicodehelp-0.2.0/src/centicodehelp/cli/commands/update.py +51 -0
  24. centicodehelp-0.2.0/src/centicodehelp/cli/main.py +141 -0
  25. centicodehelp-0.2.0/src/centicodehelp/cli/theme.py +50 -0
  26. centicodehelp-0.2.0/src/centicodehelp/core/config.py +58 -0
  27. centicodehelp-0.2.0/src/centicodehelp/core/models.py +31 -0
  28. centicodehelp-0.2.0/src/centicodehelp/fixer/applier.py +23 -0
  29. centicodehelp-0.2.0/src/centicodehelp/fixer/patcher.py +42 -0
  30. centicodehelp-0.2.0/src/centicodehelp.egg-info/PKG-INFO +79 -0
  31. centicodehelp-0.2.0/src/centicodehelp.egg-info/SOURCES.txt +37 -0
  32. centicodehelp-0.2.0/src/centicodehelp.egg-info/dependency_links.txt +1 -0
  33. centicodehelp-0.2.0/src/centicodehelp.egg-info/entry_points.txt +4 -0
  34. centicodehelp-0.2.0/src/centicodehelp.egg-info/requires.txt +8 -0
  35. centicodehelp-0.2.0/src/centicodehelp.egg-info/top_level.txt +1 -0
  36. centicodehelp-0.2.0/tests/test_centicodehelp.py +52 -0
  37. centicodehelp-0.2.0/tests/test_centitool.py +52 -0
  38. centicodehelp-0.2.0/tests/test_mcp.py +67 -0
  39. centicodehelp-0.2.0/tests/test_mcp_handshake.py +32 -0
@@ -0,0 +1,79 @@
1
+ Metadata-Version: 2.4
2
+ Name: centicodehelp
3
+ Version: 0.2.0
4
+ Summary: Dein Code. Besser. Sauber. Cross-platform static and AI-assisted code & binary analysis and auto-fixing tool
5
+ Requires-Python: >=3.12
6
+ Description-Content-Type: text/markdown
7
+ Requires-Dist: click>=8.1.0
8
+ Requires-Dist: rich>=13.0.0
9
+ Requires-Dist: litellm>=1.40.0
10
+ Requires-Dist: tree-sitter>=0.23.0
11
+ Requires-Dist: tree-sitter-python>=0.23.0
12
+ Requires-Dist: pyyaml>=6.0.0
13
+ Requires-Dist: pydantic>=2.0.0
14
+ Requires-Dist: fastmcp>=0.1.0
15
+
16
+ # CentiCodeHelp – Mach deinen Code besser.
17
+
18
+ > **Dein Code. Besser. Sauber.**
19
+ > Automatische Sicherheitsanalyse, Qualitätsprüfung und KI-gestützte Code-Reparatur.
20
+ > *Version v0.2.0 • centi09.de*
21
+
22
+ ---
23
+
24
+ ## ⚡ Schnellstart
25
+
26
+ CentiCodeHelp bietet kinderleichte Befehle:
27
+
28
+ - **Hauptbefehl**: `centicodehelp`
29
+ - **Kurz-Aliase**: `cch` und `ct`
30
+
31
+ ```bash
32
+ # 1. Schnelle statische Analyse (ohne KI)
33
+ cch scan
34
+
35
+ # 2. Vollautomatische Reparatur mit KI & automatischem .bak-Backup
36
+ cch fix samples/vulnerable_code.py
37
+
38
+ # 3. Schnellcheck einer einzelnen Datei
39
+ cch check samples/vulnerable_code.py
40
+
41
+ # 4. Reine KI-Analyse
42
+ cch ai samples/vulnerable_code.py
43
+
44
+ # 5. Interaktiver Einrichtungs-Assistent
45
+ cch setup
46
+ ```
47
+
48
+ ---
49
+
50
+ ## 📂 Neue Projekt- und Workspace-Struktur
51
+
52
+ ```
53
+ C:\CentiTools\
54
+ ├── centicodehelp\ # Code-Analyse, KI-Audit, Auto-Fixing und CLI
55
+ ├── config\ # Gemeinsame Konfigurationen (centicodehelp.yaml)
56
+ └── samples\ # Gemeinsame Testdateien (Python, JS, Java, C++)
57
+ ```
58
+
59
+ ---
60
+
61
+ ## 🤖 MCP-Server & Antigravity-Integration
62
+
63
+ CentiCodeHelp beinhaltet einen nativen FastMCP-Server unter:
64
+ `C:\CentiTools\centicodehelp\centicodehelp_mcp.py`
65
+
66
+ ### Verfügbare Tools:
67
+ - `centicodehelp_scan(pfad: str)`: Statische Analyse, liefert JSON-Findings.
68
+ - `centicodehelp_fix(pfad: str, provider: str, model: str)`: Automatische Reparatur mit Backup.
69
+ - `centicodehelp_providers()`: Listet alle KI-Anbieter & Modelle auf.
70
+ *(Aliase `centitool_scan`, `centitool_fix`, `centitool_providers` bleiben abwärtskompatibel erhalten).*
71
+
72
+ ---
73
+
74
+ ## 🔧 Installation
75
+
76
+ ```bash
77
+ cd C:\CentiTools\centicodehelp
78
+ pip install -e .
79
+ ```
@@ -0,0 +1,64 @@
1
+ # CentiCodeHelp – Mach deinen Code besser.
2
+
3
+ > **Dein Code. Besser. Sauber.**
4
+ > Automatische Sicherheitsanalyse, Qualitätsprüfung und KI-gestützte Code-Reparatur.
5
+ > *Version v0.2.0 • centi09.de*
6
+
7
+ ---
8
+
9
+ ## ⚡ Schnellstart
10
+
11
+ CentiCodeHelp bietet kinderleichte Befehle:
12
+
13
+ - **Hauptbefehl**: `centicodehelp`
14
+ - **Kurz-Aliase**: `cch` und `ct`
15
+
16
+ ```bash
17
+ # 1. Schnelle statische Analyse (ohne KI)
18
+ cch scan
19
+
20
+ # 2. Vollautomatische Reparatur mit KI & automatischem .bak-Backup
21
+ cch fix samples/vulnerable_code.py
22
+
23
+ # 3. Schnellcheck einer einzelnen Datei
24
+ cch check samples/vulnerable_code.py
25
+
26
+ # 4. Reine KI-Analyse
27
+ cch ai samples/vulnerable_code.py
28
+
29
+ # 5. Interaktiver Einrichtungs-Assistent
30
+ cch setup
31
+ ```
32
+
33
+ ---
34
+
35
+ ## 📂 Neue Projekt- und Workspace-Struktur
36
+
37
+ ```
38
+ C:\CentiTools\
39
+ ├── centicodehelp\ # Code-Analyse, KI-Audit, Auto-Fixing und CLI
40
+ ├── config\ # Gemeinsame Konfigurationen (centicodehelp.yaml)
41
+ └── samples\ # Gemeinsame Testdateien (Python, JS, Java, C++)
42
+ ```
43
+
44
+ ---
45
+
46
+ ## 🤖 MCP-Server & Antigravity-Integration
47
+
48
+ CentiCodeHelp beinhaltet einen nativen FastMCP-Server unter:
49
+ `C:\CentiTools\centicodehelp\centicodehelp_mcp.py`
50
+
51
+ ### Verfügbare Tools:
52
+ - `centicodehelp_scan(pfad: str)`: Statische Analyse, liefert JSON-Findings.
53
+ - `centicodehelp_fix(pfad: str, provider: str, model: str)`: Automatische Reparatur mit Backup.
54
+ - `centicodehelp_providers()`: Listet alle KI-Anbieter & Modelle auf.
55
+ *(Aliase `centitool_scan`, `centitool_fix`, `centitool_providers` bleiben abwärtskompatibel erhalten).*
56
+
57
+ ---
58
+
59
+ ## 🔧 Installation
60
+
61
+ ```bash
62
+ cd C:\CentiTools\centicodehelp
63
+ pip install -e .
64
+ ```
@@ -0,0 +1,28 @@
1
+ [build-system]
2
+ requires = ["setuptools>=61.0"]
3
+ build-backend = "setuptools.build_meta"
4
+
5
+ [project]
6
+ name = "centicodehelp"
7
+ version = "0.2.0"
8
+ description = "Dein Code. Besser. Sauber. Cross-platform static and AI-assisted code & binary analysis and auto-fixing tool"
9
+ readme = "README.md"
10
+ requires-python = ">=3.12"
11
+ dependencies = [
12
+ "click>=8.1.0",
13
+ "rich>=13.0.0",
14
+ "litellm>=1.40.0",
15
+ "tree-sitter>=0.23.0",
16
+ "tree-sitter-python>=0.23.0",
17
+ "pyyaml>=6.0.0",
18
+ "pydantic>=2.0.0",
19
+ "fastmcp>=0.1.0"
20
+ ]
21
+
22
+ [project.scripts]
23
+ centicodehelp = "centicodehelp.cli.main:main"
24
+ cch = "centicodehelp.cli.main:main"
25
+ ct = "centicodehelp.cli.main:main"
26
+
27
+ [tool.setuptools.packages.find]
28
+ where = ["src"]
@@ -0,0 +1,4 @@
1
+ [egg_info]
2
+ tag_build =
3
+ tag_date = 0
4
+
@@ -0,0 +1,3 @@
1
+ """CentiCodeHelp - Dein Code. Besser. Sauber."""
2
+
3
+ __version__ = "0.2.0"
@@ -0,0 +1,150 @@
1
+ import os
2
+ import json
3
+ import time
4
+ import logging
5
+ from typing import Optional, Dict, Any, List
6
+ from pydantic import BaseModel, Field
7
+ from centicodehelp.core.config import load_config, centicodehelpConfig
8
+ from centicodehelp.ai.providers import SUPPORTED_PROVIDERS, get_provider
9
+
10
+ logger = logging.getLogger(__name__)
11
+
12
+ class LLMResponse(BaseModel):
13
+ content: str
14
+ model: str
15
+ duration_seconds: float = 0.0
16
+ prompt_tokens: int = 0
17
+ completion_tokens: int = 0
18
+ total_tokens: int = 0
19
+ raw_response: Optional[Any] = None
20
+
21
+
22
+ class LLMClient:
23
+ """Unified client wrapping LiteLLM for all AI providers."""
24
+
25
+ def __init__(
26
+ self,
27
+ provider: Optional[str] = None,
28
+ model: Optional[str] = None,
29
+ api_key: Optional[str] = None,
30
+ api_base: Optional[str] = None,
31
+ config: Optional[centicodehelpConfig] = None,
32
+ ):
33
+ self.config = config or load_config()
34
+ self.provider_id = (provider or self.config.default_provider).lower()
35
+ self.provider_info = get_provider(self.provider_id)
36
+
37
+ # Resolve model name
38
+ if model:
39
+ self.model = model
40
+ elif self.provider_info:
41
+ self.model = self.provider_info.default_model
42
+ else:
43
+ self.model = self.config.default_model
44
+
45
+ # Determine full LiteLLM model identifier
46
+ self.litellm_model = self._resolve_litellm_model(self.provider_id, self.model)
47
+
48
+ # Resolve API Key
49
+ self.api_key = api_key or self._resolve_api_key(self.provider_id)
50
+
51
+ # Resolve API Base
52
+ self.api_base = api_base or self._resolve_api_base(self.provider_id)
53
+
54
+ def _resolve_litellm_model(self, provider_id: str, model: str) -> str:
55
+ """Resolve to litellm standard format (e.g. openai/gpt-4o, ollama/llama3.2)."""
56
+ if "/" in model:
57
+ return model
58
+
59
+ if self.provider_info:
60
+ for m in self.provider_info.models:
61
+ if m.name.lower() == model.lower():
62
+ return m.litellm_id
63
+
64
+ # Fallback convention: <provider>/<model>
65
+ return f"{provider_id}/{model}"
66
+
67
+ def _resolve_api_key(self, provider_id: str) -> Optional[str]:
68
+ if provider_id in self.config.api_keys:
69
+ return self.config.api_keys[provider_id]
70
+
71
+ if self.provider_info:
72
+ for env_var in self.provider_info.env_keys:
73
+ val = os.getenv(env_var)
74
+ if val:
75
+ return val
76
+
77
+ return os.getenv(f"{provider_id.upper()}_API_KEY")
78
+
79
+ def _resolve_api_base(self, provider_id: str) -> Optional[str]:
80
+ if provider_id in self.config.api_bases:
81
+ return self.config.api_bases[provider_id]
82
+
83
+ if provider_id == "ollama":
84
+ return os.getenv("OLLAMA_API_BASE") or self.config.ollama_base_url
85
+
86
+ if self.provider_info and self.provider_info.default_api_base:
87
+ return self.provider_info.default_api_base
88
+
89
+ return None
90
+
91
+ def complete_with_metadata(
92
+ self, prompt: str, system: Optional[str] = None, temperature: float = 0.2
93
+ ) -> LLMResponse:
94
+ """Send completion request via LiteLLM and return rich telemetry."""
95
+ try:
96
+ import litellm
97
+ litellm.suppress_debug_info = True
98
+ except ImportError:
99
+ raise RuntimeError("LiteLLM is not installed. Run 'pip install litellm' first.")
100
+
101
+ messages = []
102
+ if system:
103
+ messages.append({"role": "system", "content": system})
104
+ messages.append({"role": "user", "content": prompt})
105
+
106
+ kwargs: Dict[str, Any] = {
107
+ "model": self.litellm_model,
108
+ "messages": messages,
109
+ "temperature": temperature,
110
+ }
111
+
112
+ if self.api_key:
113
+ kwargs["api_key"] = self.api_key
114
+ if self.api_base:
115
+ kwargs["api_base"] = self.api_base
116
+
117
+ start_time = time.time()
118
+ try:
119
+ response = litellm.completion(**kwargs)
120
+ duration = round(time.time() - start_time, 2)
121
+
122
+ content = response.choices[0].message.content or ""
123
+ usage = getattr(response, "usage", None)
124
+
125
+ p_tokens = getattr(usage, "prompt_tokens", 0) if usage else 0
126
+ c_tokens = getattr(usage, "completion_tokens", 0) if usage else 0
127
+ t_tokens = getattr(usage, "total_tokens", 0) if usage else (p_tokens + c_tokens)
128
+
129
+ return LLMResponse(
130
+ content=content,
131
+ model=self.litellm_model,
132
+ duration_seconds=duration,
133
+ prompt_tokens=p_tokens,
134
+ completion_tokens=c_tokens,
135
+ total_tokens=t_tokens,
136
+ raw_response=response,
137
+ )
138
+ except Exception as e:
139
+ err_str = str(e)
140
+ if self.provider_id == "ollama" and ("Connection" in err_str or "10061" in err_str or "ConnectError" in err_str):
141
+ raise RuntimeError(
142
+ "❌ Ollama läuft nicht. Starte es mit 'ollama serve' oder nutze 'ct setup' für einen Cloud-Anbieter."
143
+ ) from e
144
+ logger.error(f"LiteLLM completion error for model {self.litellm_model}: {e}")
145
+ raise
146
+
147
+ def complete(self, prompt: str, system: Optional[str] = None, temperature: float = 0.2) -> str:
148
+ """Backward-compatible complete method returning pure text."""
149
+ return self.complete_with_metadata(prompt, system=system, temperature=temperature).content
150
+
@@ -0,0 +1,63 @@
1
+ """Prompt templates for AI-assisted code review and auto-fixing."""
2
+
3
+ REVIEW_PROMPT_TEMPLATE = """You are an expert static analysis and code security auditor.
4
+ Analyze the following source code file and the static analysis findings below.
5
+ Your task:
6
+ 1. Validate whether the reported static findings are true positives.
7
+ 2. Identify any subtle logic bugs, unhandled edge cases, performance issues, or security flaws that were missed.
8
+ 3. Suggest concrete fixes for each issue.
9
+
10
+ File: {file_path}
11
+ Language: {language}
12
+
13
+ --- STATIC ANALYSIS FINDINGS ---
14
+ {static_findings}
15
+
16
+ --- SOURCE CODE ---
17
+ ```{language}
18
+ {source_code}
19
+ ```
20
+
21
+ Format your response strictly as a JSON object with this structure:
22
+ {{
23
+ "summary": "Brief summary of code health and key problems",
24
+ "issues": [
25
+ {{
26
+ "line": <line_number_or_null>,
27
+ "severity": "INFO" | "LOW" | "MEDIUM" | "HIGH" | "CRITICAL",
28
+ "rule_id": "<rule_identifier>",
29
+ "description": "<detailed problem description>",
30
+ "suggested_fix": "<how to fix it>"
31
+ }}
32
+ ]
33
+ }}
34
+ Only output valid JSON. Do not wrap in extra prose.
35
+ """
36
+
37
+ FIX_SYSTEM_PROMPT = """Du bist ein erstklassiger Code-Sicherheitsexperte und Entwickler. Deine Aufgabe ist es, den fehlerhaften Quellcode strikt nach Sicherheits- und Qualitätsregeln zu reparieren. Gib ausschließlich den fertig korrigierten Quellcode zurück."""
38
+
39
+ FIX_PROMPT_TEMPLATE = """Du bist ein Sicherheitsexperte. Behebe die folgenden Probleme im Code:
40
+ 1. SEC001: Ersetze hardcodierte Secrets durch os.environ.get().
41
+ 2. SEC101: Ersetze eval() IMMER durch ast.literal_eval(). Wenn das nicht möglich ist, entferne eval() komplett und wirf einen Fehler (ValueError). eval() darf unter KEINEN Umständen mehr im Code vorkommen! Stelle sicher, dass 'import ast' vorhanden ist.
42
+ 3. DEBUG002: Entferne ALLE print()-Debug-Statements KOMPLETT. Nicht auskommentieren, nicht ersetzen – LÖSCHEN. Die Zeile darf im Ergebnis nicht mehr vorkommen.
43
+ 4. ERR001/ERR003: Ersetze bare except durch except Exception as e.
44
+ 5. QUAL001: Implementiere die fehlende Logik (z. B. Validierung für negative Preise mit ValueError) und entferne das TODO.
45
+
46
+ WICHTIGE ANWEISUNGEN:
47
+ - Der Aufruf 'eval(...)' ist STRENG VERBOTEN. Verwende ausschließlich 'ast.literal_eval(...)'.
48
+ - Debug-Prints mit 'DEBUG' MÜSSEN komplett gelöscht werden.
49
+ - Gib NUR den korrigierten Code in einem Code-Block ``` zurück. Keine Erklärungen, kein Begleittext.
50
+
51
+ Datei: {file_path}
52
+ Sprache: {language}
53
+
54
+ --- ZU BEHEBENDE PROBLEME ---
55
+ {findings_text}
56
+
57
+ --- ORIGINALER CODE ---
58
+ ```{language}
59
+ {source_code}
60
+ ```
61
+
62
+ Gib NUR den korrigierten Code zurück:
63
+ """
@@ -0,0 +1,195 @@
1
+ from typing import Dict, List, Optional
2
+ from pydantic import BaseModel, Field
3
+
4
+ class ModelInfo(BaseModel):
5
+ name: str
6
+ litellm_id: str
7
+ description: str
8
+ is_default: bool = False
9
+ context_window: Optional[int] = None
10
+
11
+
12
+ class ProviderInfo(BaseModel):
13
+ id: str
14
+ name: str
15
+ env_keys: List[str]
16
+ default_model: str
17
+ description: str
18
+ models: List[ModelInfo]
19
+ requires_api_base: bool = False
20
+ default_api_base: Optional[str] = None
21
+
22
+
23
+ SUPPORTED_PROVIDERS: Dict[str, ProviderInfo] = {
24
+ "openai": ProviderInfo(
25
+ id="openai",
26
+ name="OpenAI",
27
+ env_keys=["OPENAI_API_KEY"],
28
+ default_model="gpt-4o",
29
+ description="OpenAI GPT-4o, GPT-4o-mini, o1, o3 models",
30
+ models=[
31
+ ModelInfo(name="gpt-4o", litellm_id="openai/gpt-4o", description="Flagship high-intelligence model", is_default=True),
32
+ ModelInfo(name="gpt-4o-mini", litellm_id="openai/gpt-4o-mini", description="Fast and cost-effective model"),
33
+ ModelInfo(name="o1-preview", litellm_id="openai/o1-preview", description="Reasoning model for hard problems"),
34
+ ModelInfo(name="o3-mini", litellm_id="openai/o3-mini", description="High-speed reasoning model"),
35
+ ]
36
+ ),
37
+ "anthropic": ProviderInfo(
38
+ id="anthropic",
39
+ name="Anthropic Claude",
40
+ env_keys=["ANTHROPIC_API_KEY"],
41
+ default_model="claude-3-5-sonnet",
42
+ description="Anthropic Claude 3.5 Sonnet / Haiku series",
43
+ models=[
44
+ ModelInfo(name="claude-3-5-sonnet", litellm_id="anthropic/claude-3-5-sonnet-20241022", description="State-of-the-art coding and analysis", is_default=True),
45
+ ModelInfo(name="claude-3-5-haiku", litellm_id="anthropic/claude-3-5-haiku-20241022", description="High-speed code reviewer"),
46
+ ]
47
+ ),
48
+ "gemini": ProviderInfo(
49
+ id="gemini",
50
+ name="Google Gemini",
51
+ env_keys=["GEMINI_API_KEY", "GOOGLE_API_KEY"],
52
+ default_model="gemini-1.5-pro",
53
+ description="Google Gemini 1.5 Pro and Flash with large context windows",
54
+ models=[
55
+ ModelInfo(name="gemini-1.5-pro", litellm_id="gemini/gemini-1.5-pro", description="Multimodal deep code reasoning", is_default=True),
56
+ ModelInfo(name="gemini-1.5-flash", litellm_id="gemini/gemini-1.5-flash", description="Ultra-fast code auditor"),
57
+ ModelInfo(name="gemini-2.0-flash-exp", litellm_id="gemini/gemini-2.0-flash-exp", description="Next-gen experimental Gemini"),
58
+ ]
59
+ ),
60
+ "deepseek": ProviderInfo(
61
+ id="deepseek",
62
+ name="DeepSeek",
63
+ env_keys=["DEEPSEEK_API_KEY"],
64
+ default_model="deepseek-coder",
65
+ description="Specialized code and reasoning models",
66
+ models=[
67
+ ModelInfo(name="deepseek-coder", litellm_id="deepseek/deepseek-coder", description="DeepSeek Coder V2 model", is_default=True),
68
+ ModelInfo(name="deepseek-chat", litellm_id="deepseek/deepseek-chat", description="General DeepSeek V3 chat model"),
69
+ ModelInfo(name="deepseek-reasoner", litellm_id="deepseek/deepseek-reasoner", description="DeepSeek R1 reasoning model"),
70
+ ]
71
+ ),
72
+ "ollama": ProviderInfo(
73
+ id="ollama",
74
+ name="Ollama (Local)",
75
+ env_keys=[],
76
+ default_model="qwen2.5-coder:7b",
77
+ description="Locally run open models without cloud API keys",
78
+ requires_api_base=True,
79
+ default_api_base="http://localhost:11434",
80
+ models=[
81
+ ModelInfo(name="qwen2.5-coder:7b", litellm_id="ollama/qwen2.5-coder:7b", description="High performance open coding LLM", is_default=True),
82
+ ModelInfo(name="qwen2.5-coder", litellm_id="ollama/qwen2.5-coder:7b", description="High performance open coding LLM"),
83
+ ModelInfo(name="llama3.2", litellm_id="ollama/llama3.2", description="Meta Llama 3.2 lightweight local model"),
84
+ ModelInfo(name="deepseek-coder-v2", litellm_id="ollama/deepseek-coder-v2", description="Local DeepSeek coder model"),
85
+ ModelInfo(name="mistral", litellm_id="ollama/mistral", description="Mistral 7B local model"),
86
+ ]
87
+ ),
88
+ "openrouter": ProviderInfo(
89
+ id="openrouter",
90
+ name="OpenRouter",
91
+ env_keys=["OPENROUTER_API_KEY"],
92
+ default_model="anthropic/claude-3.5-sonnet",
93
+ description="Universal router for hundreds of models with unified credits",
94
+ models=[
95
+ ModelInfo(name="claude-3.5-sonnet", litellm_id="openrouter/anthropic/claude-3.5-sonnet", description="Claude 3.5 Sonnet via OpenRouter", is_default=True),
96
+ ModelInfo(name="deepseek-v3", litellm_id="openrouter/deepseek/deepseek-chat", description="DeepSeek V3 via OpenRouter"),
97
+ ModelInfo(name="meta-llama-3.3-70b", litellm_id="openrouter/meta-llama/llama-3.3-70b-instruct", description="Llama 3.3 70B via OpenRouter"),
98
+ ]
99
+ ),
100
+ "groq": ProviderInfo(
101
+ id="groq",
102
+ name="Groq (LPU Inference)",
103
+ env_keys=["GROQ_API_KEY"],
104
+ default_model="llama-3.3-70b-versatile",
105
+ description="Ultra-fast LPU hardware accelerated inference",
106
+ models=[
107
+ ModelInfo(name="llama-3.3-70b-versatile", litellm_id="groq/llama-3.3-70b-versatile", description="Fast Llama 3.3 70B inference", is_default=True),
108
+ ModelInfo(name="mixtral-8x7b-32768", litellm_id="groq/mixtral-8x7b-32768", description="Mixtral 8x7B high speed"),
109
+ ]
110
+ ),
111
+ "mistral": ProviderInfo(
112
+ id="mistral",
113
+ name="Mistral AI",
114
+ env_keys=["MISTRAL_API_KEY"],
115
+ default_model="codestral-latest",
116
+ description="Mistral AI European enterprise models & Codestral",
117
+ models=[
118
+ ModelInfo(name="codestral-latest", litellm_id="mistral/codestral-latest", description="Dedicated code generation/fixing model", is_default=True),
119
+ ModelInfo(name="mistral-large-latest", litellm_id="mistral/mistral-large-latest", description="Mistral flagship model"),
120
+ ]
121
+ ),
122
+ "cohere": ProviderInfo(
123
+ id="cohere",
124
+ name="Cohere",
125
+ env_keys=["COHERE_API_KEY"],
126
+ default_model="command-r-plus",
127
+ description="Cohere Command R / Command R+ models",
128
+ models=[
129
+ ModelInfo(name="command-r-plus", litellm_id="cohere/command-r-plus", description="Enterprise reasoning and search", is_default=True),
130
+ ModelInfo(name="command-r", litellm_id="cohere/command-r", description="Fast Command R model"),
131
+ ]
132
+ ),
133
+ "xai": ProviderInfo(
134
+ id="xai",
135
+ name="xAI (Grok)",
136
+ env_keys=["XAI_API_KEY"],
137
+ default_model="grok-beta",
138
+ description="xAI Grok models",
139
+ models=[
140
+ ModelInfo(name="grok-beta", litellm_id="xai/grok-beta", description="xAI Grok Beta LLM", is_default=True),
141
+ ModelInfo(name="grok-2-latest", litellm_id="xai/grok-2-latest", description="xAI Grok 2 reasoning"),
142
+ ]
143
+ ),
144
+ "together": ProviderInfo(
145
+ id="together",
146
+ name="Together AI",
147
+ env_keys=["TOGETHERAI_API_KEY", "TOGETHER_API_KEY"],
148
+ default_model="meta-llama/Meta-Llama-3.1-70B-Instruct-Turbo",
149
+ description="Together AI cloud inference for open weights",
150
+ models=[
151
+ ModelInfo(name="llama-3.1-70b-turbo", litellm_id="together_ai/meta-llama/Meta-Llama-3.1-70B-Instruct-Turbo", description="Llama 3.1 70B Turbo", is_default=True),
152
+ ModelInfo(name="qwen-2.5-coder-32b", litellm_id="together_ai/Qwen/Qwen2.5-Coder-32B-Instruct", description="Qwen 2.5 Coder 32B Turbo"),
153
+ ]
154
+ ),
155
+ "perplexity": ProviderInfo(
156
+ id="perplexity",
157
+ name="Perplexity AI",
158
+ env_keys=["PERPLEXITYAI_API_KEY", "PPLX_API_KEY"],
159
+ default_model="sonar-pro",
160
+ description="Perplexity Sonar online search models",
161
+ models=[
162
+ ModelInfo(name="sonar-pro", litellm_id="perplexity/sonar-pro", description="Sonar Pro online search model", is_default=True),
163
+ ModelInfo(name="sonar", litellm_id="perplexity/sonar", description="Standard Sonar search model"),
164
+ ]
165
+ ),
166
+ "azure": ProviderInfo(
167
+ id="azure",
168
+ name="Azure OpenAI",
169
+ env_keys=["AZURE_API_KEY"],
170
+ default_model="azure-gpt-4o",
171
+ description="Microsoft Azure OpenAI enterprise deployments",
172
+ requires_api_base=True,
173
+ models=[
174
+ ModelInfo(name="azure-gpt-4o", litellm_id="azure/gpt-4o", description="Azure deployed GPT-4o", is_default=True),
175
+ ]
176
+ ),
177
+ "bedrock": ProviderInfo(
178
+ id="bedrock",
179
+ name="AWS Bedrock",
180
+ env_keys=["AWS_ACCESS_KEY_ID", "AWS_SECRET_ACCESS_KEY"],
181
+ default_model="anthropic.claude-3-5-sonnet",
182
+ description="Amazon Web Services Bedrock foundation models",
183
+ models=[
184
+ ModelInfo(name="claude-3-5-sonnet", litellm_id="bedrock/anthropic.claude-3-5-sonnet-20241022-v2:0", description="Claude 3.5 Sonnet on AWS Bedrock", is_default=True),
185
+ ]
186
+ ),
187
+ }
188
+
189
+
190
+ def get_provider(provider_id: str) -> Optional[ProviderInfo]:
191
+ return SUPPORTED_PROVIDERS.get(provider_id.lower())
192
+
193
+
194
+ def list_providers() -> List[ProviderInfo]:
195
+ return list(SUPPORTED_PROVIDERS.values())