feat(provider): 添加独立的 Provider 模块管理模型提供商

实现可扩展的 Provider 系统,支持动态注册自定义提供商:

Core 模块 (packages/core/src/provider/):
- types.ts: Provider 相关类型定义
- builtin/: 内置提供商 (Anthropic, OpenAI, DeepSeek)
- registry.ts: ProviderRegistry 单例类
- config.ts: 配置持久化 (~/.ai-terminal-assistant/providers.json)
- utils.ts: 连接测试等工具函数

Server API (packages/server/src/routes/providers.ts):
- GET/POST/PUT/DELETE /providers 提供商管理
- POST /providers/:id/test 连接测试
- 自定义模型管理接口

Frontend (packages/ui/):
- ProvidersPanel 组件用于管理提供商
- API client 函数和类型定义

主要功能:
- 支持动态注册 OpenAI 兼容服务 (Ollama, vLLM 等)
- 每个提供商独立的 API Key 配置
- 预设模型列表 + 自定义模型输入
- 连接测试验证
This commit is contained in:
2025-12-13 01:50:27 +08:00
parent 1d69fd876d
commit 6ec6fe2f9f
24 changed files with 2609 additions and 342 deletions
+132
View File
@@ -38,6 +38,13 @@ import type {
SafetyCheckResult,
UnrevertStatus,
UnrevertResult,
// Provider types
ProviderListItem,
ProviderDetail,
ModelInfo,
CustomProviderDefinition,
ProviderConfig,
ConnectionTestResult,
} from './types.js';
// Re-export types
@@ -96,6 +103,16 @@ export type {
CheckpointStats,
UnrevertStatus,
UnrevertResult,
// Provider types
BuiltinProviderType,
ProviderType,
ModelCapabilities,
ModelInfo,
ProviderListItem,
ProviderDetail,
CustomProviderDefinition,
ProviderConfig,
ConnectionTestResult,
} from './types.js';
// API Configuration
@@ -804,3 +821,118 @@ export async function getMessageCheckpoints(messageId: string): Promise<{
}> {
return request('GET', `/checkpoints/messages/${encodeURIComponent(messageId)}`);
}
// ============ Providers API ============
/**
* 获取所有提供商列表
*/
export async function listProviders(): Promise<{
success: boolean;
data: ProviderListItem[];
error?: string;
}> {
return request('GET', '/providers');
}
/**
* 获取单个提供商详情
*/
export async function getProvider(id: string): Promise<{
success: boolean;
data?: ProviderDetail;
error?: string;
}> {
return request('GET', `/providers/${encodeURIComponent(id)}`);
}
/**
* 获取提供商的模型列表
*/
export async function getProviderModels(id: string): Promise<{
success: boolean;
data: ModelInfo[];
error?: string;
}> {
return request('GET', `/providers/${encodeURIComponent(id)}/models`);
}
/**
* 测试提供商连接
*/
export async function testProviderConnection(
id: string,
apiKey?: string
): Promise<{
success: boolean;
data: ConnectionTestResult;
error?: string;
}> {
return request('POST', `/providers/${encodeURIComponent(id)}/test`, apiKey ? { apiKey } : {});
}
/**
* 注册自定义提供商
*/
export async function registerProvider(
definition: CustomProviderDefinition
): Promise<{
success: boolean;
message?: string;
error?: string;
}> {
return request('POST', '/providers', definition);
}
/**
* 更新提供商配置
*/
export async function updateProviderConfig(
id: string,
config: ProviderConfig
): Promise<{
success: boolean;
message?: string;
error?: string;
}> {
return request('PUT', `/providers/${encodeURIComponent(id)}`, config);
}
/**
* 删除自定义提供商
*/
export async function deleteProvider(id: string): Promise<{
success: boolean;
message?: string;
error?: string;
}> {
return request('DELETE', `/providers/${encodeURIComponent(id)}`);
}
/**
* 添加自定义模型
*/
export async function addProviderModel(
providerId: string,
model: ModelInfo
): Promise<{
success: boolean;
message?: string;
error?: string;
}> {
return request('POST', `/providers/${encodeURIComponent(providerId)}/models`, model);
}
/**
* 删除自定义模型
*/
export async function deleteProviderModel(
providerId: string,
modelId: string
): Promise<{
success: boolean;
message?: string;
error?: string;
}> {
return request('DELETE', `/providers/${encodeURIComponent(providerId)}/models/${encodeURIComponent(modelId)}`);
}
+121
View File
@@ -590,3 +590,124 @@ export interface UnrevertResult {
/** 错误信息 */
error?: string;
}
// ============ Provider 相关 ============
/** 内置提供商类型 */
export type BuiltinProviderType = 'anthropic' | 'deepseek' | 'openai';
/** 提供商类型(内置 + 自定义) */
export type ProviderType = BuiltinProviderType | string;
/** 模型能力 */
export interface ModelCapabilities {
/** 是否支持视觉 */
vision?: boolean;
/** 是否支持函数调用 */
functionCalling?: boolean;
/** 是否支持流式输出 */
streaming?: boolean;
}
/** 模型信息 */
export interface ModelInfo {
/** 模型 ID */
id: string;
/** 显示名称 */
name: string;
/** 模型能力 */
capabilities?: ModelCapabilities;
/** 上下文窗口大小 */
contextWindow?: number;
/** 最大输出 Token */
maxOutput?: number;
}
/** 提供商列表项 */
export interface ProviderListItem {
/** 提供商 ID */
id: string;
/** 显示名称 */
name: string;
/** 描述 */
description?: string;
/** 是否为内置提供商 */
builtin: boolean;
/** 是否启用 */
enabled: boolean;
/** 是否配置了 API Key */
hasApiKey: boolean;
/** 模型数量 */
modelCount: number;
}
/** 提供商详情 */
export interface ProviderDetail {
/** 提供商 ID */
id: string;
/** 显示名称 */
name: string;
/** 描述 */
description?: string;
/** 是否为内置提供商 */
builtin: boolean;
/** API 基础 URL */
baseUrl?: string;
/** API Key 环境变量名 */
apiKeyEnvVar?: string;
/** 可用模型列表 */
models: ModelInfo[];
/** 是否允许自定义模型 */
allowCustomModels: boolean;
/** 配置信息 */
config: {
enabled: boolean;
hasApiKey: boolean;
baseUrl?: string;
customModels: ModelInfo[];
};
}
/** 自定义提供商定义 */
export interface CustomProviderDefinition {
/** 提供商 ID */
id: string;
/** 显示名称 */
name: string;
/** 描述 */
description?: string;
/** API 基础 URL(必填) */
baseUrl: string;
/** API Key 环境变量名 */
apiKeyEnvVar?: string;
/** 预设模型列表 */
models?: ModelInfo[];
/** 是否允许自定义模型 */
allowCustomModels?: boolean;
}
/** 提供商配置(用户设置) */
export interface ProviderConfig {
/** 提供商 ID */
id?: string;
/** API Key */
apiKey?: string;
/** API Key 环境变量名 */
apiKeyEnvVar?: string;
/** 自定义 API 基础 URL */
baseUrl?: string;
/** 是否启用 */
enabled?: boolean;
/** 自定义模型列表 */
customModels?: ModelInfo[];
}
/** 连接测试结果 */
export interface ConnectionTestResult {
/** 是否成功 */
success: boolean;
/** 延迟(毫秒) */
latency?: number;
/** 错误信息 */
error?: string;
}