provider.go

v0.6.1
Doc Versions Source
1
package provider
2
3
// StaticModel represents a model available from a provider (no API fetch needed).
4
type StaticModel struct {
5
	ID     string
6
	Name   string
7
	Family string
8
}
9
10
// Plan describes one billing/access plan for a provider with multiple base URLs.
11
type Plan struct {
12
	Key         string // e.g. "api", "coding"
13
	Name        string // display name, e.g. "API (pay per token)"
14
	Description string
15
	BaseURL     string
16
	Compat      string // optional override; when set, switches the provider's Compat mode
17
	AuthEnvVar  string // optional override; when set, switches the auth env var
18
}
19
20
var zaiModels = []StaticModel{
21
	{ID: "glm-5", Name: "GLM-5", Family: "GLM-5"},
22
	{ID: "glm-4.7", Name: "GLM-4.7", Family: "GLM-4.7"},
23
	{ID: "glm-4.7-flash", Name: "GLM-4.7 Flash", Family: "GLM-4.7"},
24
	{ID: "glm-4.7-flashx", Name: "GLM-4.7 FlashX", Family: "GLM-4.7"},
25
	{ID: "glm-4.6", Name: "GLM-4.6", Family: "GLM-4.6"},
26
	{ID: "glm-4.5", Name: "GLM-4.5", Family: "GLM-4.5"},
27
	{ID: "glm-4.5-air", Name: "GLM-4.5 Air", Family: "GLM-4.5"},
28
	{ID: "glm-4.5-x", Name: "GLM-4.5 X", Family: "GLM-4.5"},
29
	{ID: "glm-4.5-airx", Name: "GLM-4.5 AirX", Family: "GLM-4.5"},
30
	{ID: "glm-4.5-flash", Name: "GLM-4.5 Flash", Family: "GLM-4.5"},
31
	{ID: "glm-4-32b-0414-128k", Name: "GLM-4 32B", Family: "GLM-4"},
32
}
33
34
// StaticModels maps provider keys to their available models.
35
var StaticModels = map[string][]StaticModel{
36
	"zai":        zaiModels,
37
	"zai-coding": zaiModels,
38
}
39
40
// Provider defines an alternative Claude Code API provider.
41
type Provider struct {
42
	Name        string
43
	Description string
44
	BaseURL     string
45
	Model       string
46
	SmallModel  string
47
	SonnetModel string
48
	OpusModel   string
49
	HaikuModel  string
50
	TimeoutMS   string
51
	// AuthEnvVar is the env var name used for the API key (some use AUTH_TOKEN, some API_KEY).
52
	AuthEnvVar string
53
	// Compat is "anthropic" (default) or "openai". When "openai", a local
54
	// translation proxy is started to convert Anthropic ↔ OpenAI API format.
55
	Compat string
56
	// ContextWindow is the model's context window size in tokens.
57
	// Claude Code assumes 200k by default; when this is smaller,
58
	// CLAUDE_AUTOCOMPACT_PCT_OVERRIDE is set so compaction triggers before
59
	// the real limit is hit.
60
	ContextWindow int
61
	// NoAuth indicates the provider does not require an API key (e.g. local Ollama).
62
	NoAuth bool
63
	// Plans lists alternative billing/access plans with different base URLs.
64
	// When non-empty, the TUI prompts the user to choose a plan.
65
	// BaseURL holds the default plan's URL.
66
	Plans []Plan
67
}
68
69
var Registry = map[string]Provider{
70
	"deepseek": {
71
		Name:          "DeepSeek",
72
		Description:   "DeepSeek Reasoner / V3 via Anthropic-compatible API",
73
		BaseURL:       "https://api.deepseek.com/anthropic",
74
		Model:         "deepseek-reasoner",
75
		SmallModel:    "deepseek-chat",
76
		SonnetModel:   "deepseek-reasoner",
77
		OpusModel:     "deepseek-reasoner",
78
		HaikuModel:    "deepseek-chat",
79
		TimeoutMS:     "600000",
80
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
81
		ContextWindow: 128_000,
82
	},
83
	"zai": {
84
		Name:          "z.AI API",
85
		Description:   "GLM-5 / GLM-4.7 via z.AI (pay-per-token)",
86
		BaseURL:       "https://api.z.ai/api/anthropic",
87
		Model:         "glm-5",
88
		SmallModel:    "glm-4.5-air",
89
		SonnetModel:   "glm-5",
90
		OpusModel:     "glm-5",
91
		HaikuModel:    "glm-4.5-air",
92
		TimeoutMS:     "3000000",
93
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
94
		ContextWindow: 205_000,
95
	},
96
	"zai-coding": {
97
		Name:          "z.AI Coding",
98
		Description:   "GLM-5 / GLM-4.7 via z.AI (subscription)",
99
		BaseURL:       "https://api.z.ai/api/coding/anthropic",
100
		Model:         "glm-5",
101
		SmallModel:    "glm-4.5-air",
102
		SonnetModel:   "glm-5",
103
		OpusModel:     "glm-5",
104
		HaikuModel:    "glm-4.5-air",
105
		TimeoutMS:     "3000000",
106
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
107
		ContextWindow: 205_000,
108
	},
109
	"minimax": {
110
		Name:          "MiniMax",
111
		Description:   "MiniMax-M2.5 via MiniMax Anthropic gateway",
112
		BaseURL:       "https://api.minimax.io/anthropic",
113
		Model:         "MiniMax-M2.5",
114
		SmallModel:    "MiniMax-M2.5",
115
		SonnetModel:   "MiniMax-M2.5",
116
		OpusModel:     "MiniMax-M2.5",
117
		HaikuModel:    "MiniMax-M2.5",
118
		TimeoutMS:     "3000000",
119
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
120
		ContextWindow: 205_000,
121
	},
122
	"kimi": {
123
		Name:          "Kimi Code",
124
		Description:   "Kimi K2.5 / K2 via Kimi Code (International)",
125
		BaseURL:       "https://api.kimi.com/coding/",
126
		Model:         "kimi-k2.5",
127
		SmallModel:    "kimi-k2-turbo-preview",
128
		SonnetModel:   "kimi-k2.5",
129
		OpusModel:     "kimi-k2.5",
130
		HaikuModel:    "kimi-k2-turbo-preview",
131
		TimeoutMS:     "600000",
132
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
133
		ContextWindow: 256_000,
134
	},
135
	"kimi-api-cn": {
136
		Name:          "Kimi API (China)",
137
		Description:   "Kimi via Moonshot Open Platform (api.moonshot.cn)",
138
		BaseURL:       "https://api.moonshot.cn/v1/",
139
		Model:         "kimi-k2.5",
140
		SmallModel:    "kimi-k2-turbo-preview",
141
		SonnetModel:   "kimi-k2.5",
142
		OpusModel:     "kimi-k2.5",
143
		HaikuModel:    "kimi-k2-turbo-preview",
144
		TimeoutMS:     "600000",
145
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
146
		ContextWindow: 256_000,
147
		Compat:        "openai",
148
	},
149
	"kimi-api-intl": {
150
		Name:          "Kimi API (Intl)",
151
		Description:   "Kimi via Moonshot Open Platform (api.moonshot.ai)",
152
		BaseURL:       "https://api.moonshot.ai/v1/",
153
		Model:         "kimi-k2.5",
154
		SmallModel:    "kimi-k2-turbo-preview",
155
		SonnetModel:   "kimi-k2.5",
156
		OpusModel:     "kimi-k2.5",
157
		HaikuModel:    "kimi-k2-turbo-preview",
158
		TimeoutMS:     "600000",
159
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
160
		ContextWindow: 256_000,
161
		Compat:        "openai",
162
	},
163
	"mistral": {
164
		Name:          "Mistral",
165
		Description:   "Devstral / Mistral Large via OpenAI-compatible API",
166
		BaseURL:       "https://api.mistral.ai/v1",
167
		Model:         "devstral-latest",
168
		SmallModel:    "devstral-small-latest",
169
		SonnetModel:   "devstral-latest",
170
		OpusModel:     "devstral-latest",
171
		HaikuModel:    "devstral-small-latest",
172
		TimeoutMS:     "600000",
173
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
174
		Compat:        "openai",
175
		ContextWindow: 256_000,
176
	},
177
	"copilot": {
178
		Name:          "GitHub Copilot",
179
		Description:   "Claude via GitHub Copilot",
180
		BaseURL:       "https://api.githubcopilot.com",
181
		Model:         "claude-sonnet-4.6",
182
		SmallModel:    "claude-haiku-4.5",
183
		SonnetModel:   "claude-sonnet-4.6",
184
		OpusModel:     "claude-opus-4.6",
185
		HaikuModel:    "claude-haiku-4.5",
186
		TimeoutMS:     "600000",
187
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
188
		Compat:        "openai",
189
		ContextWindow: 200_000,
190
	},
191
	"nvidia": {
192
		Name:          "NVIDIA NIM",
193
		Description:   "Access NVIDIA NIM models via OpenAI-compatible API",
194
		BaseURL:       "https://integrate.api.nvidia.com/v1",
195
		Model:         "nvidia/llama-3.1-nemotron-ultra-253b-v1",
196
		SmallModel:    "nvidia/llama-3.3-nemotron-super-49b-v1.5",
197
		SonnetModel:   "nvidia/llama-3.1-nemotron-ultra-253b-v1",
198
		OpusModel:     "nvidia/llama-3.1-nemotron-ultra-253b-v1",
199
		HaikuModel:    "nvidia/llama-3.3-nemotron-super-49b-v1.5",
200
		TimeoutMS:     "600000",
201
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
202
		Compat:        "openai",
203
		ContextWindow: 128_000,
204
	},
205
	"openrouter": {
206
		Name:          "OpenRouter",
207
		Description:   "Access multiple models via OpenRouter",
208
		BaseURL:       "https://openrouter.ai/api/v1",
209
		Model:         "anthropic/claude-sonnet-4.6",
210
		SmallModel:    "anthropic/claude-haiku-4.5",
211
		SonnetModel:   "anthropic/claude-sonnet-4.6",
212
		OpusModel:     "anthropic/claude-opus-4.6",
213
		HaikuModel:    "anthropic/claude-haiku-4.5",
214
		TimeoutMS:     "600000",
215
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
216
		Compat:        "openai",
217
		ContextWindow: 200_000,
218
	},
219
	"vkproxy": {
220
		Name:          "VK LLM Proxy",
221
		Description:   "Import models from claude-code-config.zip",
222
		BaseURL:       "https://llm-proxy.vkteam.ru",
223
		Model:         "deepseek-reasoner",
224
		SmallModel:    "deepseek-reasoner",
225
		SonnetModel:   "deepseek-reasoner",
226
		OpusModel:     "deepseek-reasoner",
227
		HaikuModel:    "deepseek-reasoner",
228
		TimeoutMS:     "600000",
229
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
230
		ContextWindow: 128_000,
231
	},
232
	"ollama": {
233
		Name:          "Ollama (local)",
234
		Description:   "Local Ollama with native Anthropic-compatible API",
235
		BaseURL:       "http://localhost:11434",
236
		Model:         "qwen3-coder",
237
		SmallModel:    "qwen3-coder",
238
		SonnetModel:   "qwen3-coder",
239
		OpusModel:     "qwen3-coder",
240
		HaikuModel:    "qwen3-coder",
241
		TimeoutMS:     "600000",
242
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
243
		ContextWindow: 32_000,
244
		NoAuth:        true,
245
	},
246
	"ollama-cloud": {
247
		Name:          "Ollama Cloud",
248
		Description:   "Cloud models via ollama.com API",
249
		BaseURL:       "https://ollama.com",
250
		Model:         "qwen3.5:397b",
251
		SmallModel:    "devstral-small-2:24b",
252
		SonnetModel:   "devstral-2:123b",
253
		OpusModel:     "qwen3.5:397b",
254
		HaikuModel:    "devstral-small-2:24b",
255
		TimeoutMS:     "600000",
256
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
257
		ContextWindow: 32_000,
258
	},
259
	"lmstudio": {
260
		Name:          "LM Studio",
261
		Description:   "Local LM Studio server with OpenAI-compatible API",
262
		BaseURL:       "http://localhost:1234/v1",
263
		Model:         "local-model",
264
		SmallModel:    "local-model",
265
		SonnetModel:   "local-model",
266
		OpusModel:     "local-model",
267
		HaikuModel:    "local-model",
268
		TimeoutMS:     "600000",
269
		AuthEnvVar:    "ANTHROPIC_AUTH_TOKEN",
270
		ContextWindow: 128_000,
271
		Compat:        "openai",
272
		NoAuth:        true,
273
	},
274
	"claude": {
275
		Name:        "Claude (Anthropic)",
276
		Description: "Native Claude API via Anthropic (passthrough proxy for accounting)",
277
		BaseURL:     "https://api.anthropic.com",
278
		Model:       "claude-sonnet-4-6-20250514",
279
		SmallModel:  "claude-haiku-4-5-20251001",
280
		SonnetModel: "claude-sonnet-4-6-20250514",
281
		OpusModel:   "claude-opus-4-6-20250610",
282
		HaikuModel:  "claude-haiku-4-5-20251001",
283
		TimeoutMS:   "600000",
284
		NoAuth:      true,
285
	},
286
}
287
288
// Order defines the display order of providers.
289
var Order = []string{"claude", "deepseek", "mistral", "zai", "zai-coding", "minimax", "kimi", "kimi-api-cn", "kimi-api-intl", "copilot", "nvidia", "openrouter", "ollama", "ollama-cloud", "lmstudio", "vkproxy"}
290

Source Files