mirror of
https://github.com/tiennm99/ccs.git
synced 2026-07-16 10:16:49 +00:00
feat(copilot): add complete model catalog with plan tiers
Add 19 GitHub Copilot supported models with metadata: - Anthropic: claude-sonnet-4.5, claude-sonnet-4, claude-opus-4.5, claude-opus-4.1, claude-haiku-4.5 - OpenAI: gpt-5.2, gpt-5.1-codex-max, gpt-5.1-codex, gpt-5.1-codex-mini, gpt-5.1, gpt-5-codex, gpt-5, gpt-5-mini, gpt-4.1 - Google: gemini-3-pro, gemini-3-flash, gemini-2.5-pro - xAI: grok-code-fast-1 - Fine-tuned: raptor-mini Each model includes: - minPlan: free, pro, pro+, business, enterprise - multiplier: 0 = free tier, 0.25-0.33 = cheap, 1 = standard, 3-10 = premium - preview: boolean for non-GA models Update default model to claude-sonnet-4.5 (standard multiplier).
This commit is contained in:
@@ -325,7 +325,7 @@ function generateYamlWithComments(config: UnifiedConfig): string {
|
||||
lines.push('# Setup: npx copilot-api auth (authenticate with GitHub)');
|
||||
lines.push('# Usage: ccs copilot (switch to copilot profile)');
|
||||
lines.push('#');
|
||||
lines.push('# Models: claude-opus-4-5-20250514, claude-sonnet-4-20250514, gpt-4.1, o3');
|
||||
lines.push('# Models: claude-sonnet-4.5, claude-opus-4.5, gpt-5.1, gemini-2.5-pro');
|
||||
lines.push('# Account types: individual, business, enterprise');
|
||||
lines.push('# ----------------------------------------------------------------------------');
|
||||
lines.push(
|
||||
|
||||
@@ -175,7 +175,7 @@ export interface CopilotConfig {
|
||||
rate_limit: number | null;
|
||||
/** Wait instead of error when rate limit is hit (default: true) */
|
||||
wait_on_limit: boolean;
|
||||
/** Default model ID (e.g., claude-opus-4-5-20250514) */
|
||||
/** Default model ID (e.g., claude-sonnet-4.5) */
|
||||
model: string;
|
||||
/** Model mapping for Claude tiers - maps opus/sonnet/haiku to specific models */
|
||||
opus_model?: string;
|
||||
@@ -259,7 +259,7 @@ export const DEFAULT_COPILOT_CONFIG: CopilotConfig = {
|
||||
account_type: 'individual',
|
||||
rate_limit: null,
|
||||
wait_on_limit: true,
|
||||
model: 'claude-opus-4-5-20250514',
|
||||
model: 'claude-sonnet-4.5',
|
||||
};
|
||||
|
||||
/**
|
||||
|
||||
+146
-20
@@ -2,6 +2,8 @@
|
||||
* Copilot Model Catalog
|
||||
*
|
||||
* Manages available models from copilot-api.
|
||||
* Based on GitHub Copilot supported models:
|
||||
* https://docs.github.com/copilot/reference/ai-models/supported-models
|
||||
*/
|
||||
|
||||
import * as http from 'http';
|
||||
@@ -10,19 +12,132 @@ import { CopilotModel } from './types';
|
||||
/**
|
||||
* Default models available through copilot-api.
|
||||
* Used as fallback when API is not reachable.
|
||||
* Source: GitHub Copilot Supported Models (Dec 2025)
|
||||
*
|
||||
* Plan tiers: free, pro, pro+, business, enterprise
|
||||
* Multipliers: 0 = free tier, 0.25-0.33 = cheap, 1 = standard, 3-10 = premium
|
||||
*/
|
||||
export const DEFAULT_COPILOT_MODELS: CopilotModel[] = [
|
||||
// Anthropic Models
|
||||
{
|
||||
id: 'claude-opus-4-5-20250514',
|
||||
name: 'Claude Opus 4.5',
|
||||
id: 'claude-sonnet-4.5',
|
||||
name: 'Claude Sonnet 4.5',
|
||||
provider: 'anthropic',
|
||||
isDefault: true,
|
||||
minPlan: 'pro',
|
||||
multiplier: 1,
|
||||
},
|
||||
{
|
||||
id: 'claude-sonnet-4',
|
||||
name: 'Claude Sonnet 4',
|
||||
provider: 'anthropic',
|
||||
minPlan: 'pro',
|
||||
multiplier: 1,
|
||||
},
|
||||
{
|
||||
id: 'claude-opus-4.5',
|
||||
name: 'Claude Opus 4.5',
|
||||
provider: 'anthropic',
|
||||
minPlan: 'pro',
|
||||
multiplier: 3,
|
||||
preview: true,
|
||||
},
|
||||
{
|
||||
id: 'claude-opus-4.1',
|
||||
name: 'Claude Opus 4.1',
|
||||
provider: 'anthropic',
|
||||
minPlan: 'pro',
|
||||
multiplier: 10,
|
||||
},
|
||||
{
|
||||
id: 'claude-haiku-4.5',
|
||||
name: 'Claude Haiku 4.5',
|
||||
provider: 'anthropic',
|
||||
minPlan: 'free',
|
||||
multiplier: 0.33,
|
||||
},
|
||||
|
||||
// OpenAI Models
|
||||
{
|
||||
id: 'gpt-5.2',
|
||||
name: 'GPT-5.2',
|
||||
provider: 'openai',
|
||||
minPlan: 'pro',
|
||||
multiplier: 1,
|
||||
preview: true,
|
||||
},
|
||||
{
|
||||
id: 'gpt-5.1-codex-max',
|
||||
name: 'GPT-5.1 Codex Max',
|
||||
provider: 'openai',
|
||||
minPlan: 'pro',
|
||||
multiplier: 1,
|
||||
},
|
||||
{ id: 'gpt-5.1-codex', name: 'GPT-5.1 Codex', provider: 'openai', minPlan: 'pro', multiplier: 1 },
|
||||
{
|
||||
id: 'gpt-5.1-codex-mini',
|
||||
name: 'GPT-5.1 Codex Mini',
|
||||
provider: 'openai',
|
||||
minPlan: 'pro',
|
||||
multiplier: 0.33,
|
||||
preview: true,
|
||||
},
|
||||
{ id: 'gpt-5.1', name: 'GPT-5.1', provider: 'openai', minPlan: 'pro', multiplier: 1 },
|
||||
{
|
||||
id: 'gpt-5-codex',
|
||||
name: 'GPT-5 Codex',
|
||||
provider: 'openai',
|
||||
minPlan: 'pro',
|
||||
multiplier: 1,
|
||||
preview: true,
|
||||
},
|
||||
{ id: 'gpt-5', name: 'GPT-5', provider: 'openai', minPlan: 'pro', multiplier: 1 },
|
||||
{ id: 'gpt-5-mini', name: 'GPT-5 Mini', provider: 'openai', minPlan: 'free', multiplier: 0 },
|
||||
{ id: 'gpt-4.1', name: 'GPT-4.1', provider: 'openai', minPlan: 'free', multiplier: 0 },
|
||||
|
||||
// Google Models
|
||||
{
|
||||
id: 'gemini-3-pro',
|
||||
name: 'Gemini 3 Pro',
|
||||
provider: 'openai',
|
||||
minPlan: 'pro',
|
||||
multiplier: 1,
|
||||
preview: true,
|
||||
},
|
||||
{
|
||||
id: 'gemini-3-flash',
|
||||
name: 'Gemini 3 Flash',
|
||||
provider: 'openai',
|
||||
minPlan: 'pro',
|
||||
multiplier: 0.33,
|
||||
preview: true,
|
||||
},
|
||||
{
|
||||
id: 'gemini-2.5-pro',
|
||||
name: 'Gemini 2.5 Pro',
|
||||
provider: 'openai',
|
||||
minPlan: 'pro',
|
||||
multiplier: 1,
|
||||
},
|
||||
|
||||
// xAI Models
|
||||
{
|
||||
id: 'grok-code-fast-1',
|
||||
name: 'Grok Code Fast 1',
|
||||
provider: 'openai',
|
||||
minPlan: 'pro',
|
||||
multiplier: 0.25,
|
||||
},
|
||||
|
||||
// Fine-tuned Models
|
||||
{
|
||||
id: 'raptor-mini',
|
||||
name: 'Raptor Mini',
|
||||
provider: 'openai',
|
||||
minPlan: 'free',
|
||||
multiplier: 0,
|
||||
preview: true,
|
||||
},
|
||||
{ id: 'claude-sonnet-4-20250514', name: 'Claude Sonnet 4', provider: 'anthropic' },
|
||||
{ id: 'gpt-4.1', name: 'GPT-4.1', provider: 'openai' },
|
||||
{ id: 'gpt-4.1-mini', name: 'GPT-4.1 Mini', provider: 'openai' },
|
||||
{ id: 'o3', name: 'O3', provider: 'openai' },
|
||||
{ id: 'o4-mini', name: 'O4 Mini', provider: 'openai' },
|
||||
];
|
||||
|
||||
/**
|
||||
@@ -55,8 +170,8 @@ export async function fetchModelsFromDaemon(port: number): Promise<CopilotModel[
|
||||
const models: CopilotModel[] = response.data.map((m) => ({
|
||||
id: m.id,
|
||||
name: formatModelName(m.id),
|
||||
provider: m.id.includes('claude') ? 'anthropic' : 'openai',
|
||||
isDefault: m.id === 'claude-opus-4-5-20250514',
|
||||
provider: detectProvider(m.id),
|
||||
isDefault: m.id === 'claude-sonnet-4.5',
|
||||
}));
|
||||
resolve(models.length > 0 ? models : DEFAULT_COPILOT_MODELS);
|
||||
} else {
|
||||
@@ -93,22 +208,33 @@ export async function getAvailableModels(port: number): Promise<CopilotModel[]>
|
||||
* Get the default model.
|
||||
*/
|
||||
export function getDefaultModel(): string {
|
||||
return 'claude-opus-4-5-20250514';
|
||||
return 'claude-sonnet-4.5';
|
||||
}
|
||||
|
||||
/**
|
||||
* Detect provider from model ID.
|
||||
*/
|
||||
function detectProvider(modelId: string): 'openai' | 'anthropic' {
|
||||
if (modelId.includes('claude')) return 'anthropic';
|
||||
return 'openai';
|
||||
}
|
||||
|
||||
/**
|
||||
* Format model ID to human-readable name.
|
||||
* Includes badges for preview and plan tier.
|
||||
*/
|
||||
function formatModelName(modelId: string): string {
|
||||
// Convert model IDs to readable names
|
||||
const nameMap: Record<string, string> = {
|
||||
'claude-opus-4-5-20250514': 'Claude Opus 4.5',
|
||||
'claude-sonnet-4-20250514': 'Claude Sonnet 4',
|
||||
'gpt-4.1': 'GPT-4.1',
|
||||
'gpt-4.1-mini': 'GPT-4.1 Mini',
|
||||
o3: 'O3',
|
||||
'o4-mini': 'O4 Mini',
|
||||
};
|
||||
// Find model in catalog for metadata
|
||||
const model = DEFAULT_COPILOT_MODELS.find((m) => m.id === modelId);
|
||||
if (model) {
|
||||
let name = model.name;
|
||||
if (model.preview) name += ' (Preview)';
|
||||
return name;
|
||||
}
|
||||
|
||||
return nameMap[modelId] || modelId;
|
||||
// Fallback: convert kebab-case to title case
|
||||
return modelId
|
||||
.split('-')
|
||||
.map((word) => word.charAt(0).toUpperCase() + word.slice(1))
|
||||
.join(' ');
|
||||
}
|
||||
|
||||
@@ -35,6 +35,12 @@ export interface CopilotStatus {
|
||||
daemon: CopilotDaemonStatus;
|
||||
}
|
||||
|
||||
/**
|
||||
* Copilot plan tier for model availability.
|
||||
* Based on GitHub Copilot plans.
|
||||
*/
|
||||
export type CopilotPlanTier = 'free' | 'pro' | 'pro+' | 'business' | 'enterprise';
|
||||
|
||||
/**
|
||||
* Copilot model information.
|
||||
*/
|
||||
@@ -45,6 +51,12 @@ export interface CopilotModel {
|
||||
provider: 'openai' | 'anthropic';
|
||||
/** Whether this is the default model */
|
||||
isDefault?: boolean;
|
||||
/** Minimum plan tier required (free = available to all) */
|
||||
minPlan?: CopilotPlanTier;
|
||||
/** Premium request multiplier (0 = free, higher = more expensive) */
|
||||
multiplier?: number;
|
||||
/** Whether this model is in preview */
|
||||
preview?: boolean;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
Reference in New Issue
Block a user