-
Notifications
You must be signed in to change notification settings - Fork 23
Expand file tree
/
Copy pathChatServiceInterface.ts
More file actions
134 lines (121 loc) · 3.52 KB
/
ChatServiceInterface.ts
File metadata and controls
134 lines (121 loc) · 3.52 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
/**
* ChatService 接口抽象
* 定义统一的聊天服务接口,支持多种 API 提供商
*/
import type { ChatCompletionMessageToolCall } from 'openai/resources/chat';
import type { ProviderType } from '../config/types.js';
import { createLogger, LogCategory } from '../logging/Logger.js';
import { OpenAIChatService } from './OpenAIChatService.js';
const logger = createLogger(LogCategory.SERVICE);
/**
* 消息类型
*/
export type Message = {
role: 'user' | 'assistant' | 'system' | 'tool';
content: string;
tool_call_id?: string; // tool 角色必需
name?: string; // 工具名称
tool_calls?: ChatCompletionMessageToolCall[]; // assistant 返回工具调用时需要
};
/**
* ChatConfig - 聊天服务所需的配置
* 注意:这些字段现在从 ModelConfig 中获取,而非直接从 BladeConfig
*/
export interface ChatConfig {
provider: ProviderType;
apiKey: string;
baseUrl: string;
model: string;
temperature?: number;
maxContextTokens?: number; // 上下文窗口大小(用于压缩判断)
maxOutputTokens?: number; // 输出 token 限制(传给 API 的 max_tokens)
timeout?: number;
}
/**
* 聊天响应
*/
export interface ChatResponse {
content: string;
reasoningContent?: string; // Thinking 模型的推理过程(如 DeepSeek R1)
toolCalls?: ChatCompletionMessageToolCall[];
usage?: {
promptTokens: number;
completionTokens: number;
totalTokens: number;
reasoningTokens?: number; // Thinking 模型消耗的推理 tokens
};
}
/**
* 流式响应块
*/
export interface StreamChunk {
content?: string;
reasoningContent?: string; // Thinking 模型的推理过程片段
// biome-ignore lint/suspicious/noExplicitAny: 不同 provider 的 tool call 类型不同
toolCalls?: any[];
finishReason?: string;
}
/**
* 聊天服务接口
* 所有 Provider 实现必须实现此接口
*/
export interface IChatService {
/**
* 发送聊天请求(非流式)
*/
chat(
messages: Message[],
tools?: Array<{
name: string;
description: string;
// biome-ignore lint/suspicious/noExplicitAny: 工具参数格式不确定
parameters: any;
}>,
signal?: AbortSignal
): Promise<ChatResponse>;
/**
* 发送聊天请求(流式)
*/
streamChat(
messages: Message[],
tools?: Array<{
name: string;
description: string;
// biome-ignore lint/suspicious/noExplicitAny: 工具参数格式不确定
parameters: any;
}>,
signal?: AbortSignal
): AsyncGenerator<StreamChunk, void, unknown>;
/**
* 获取当前配置
*/
getConfig(): ChatConfig;
/**
* 更新配置
*/
updateConfig(newConfig: Partial<ChatConfig>): void;
}
/**
* ChatService 工厂函数
* 根据配置中的 provider 创建对应的服务实例
*
* @param config ChatConfig + provider 字段
* @returns IChatService 实例
*/
export function createChatService(config: ChatConfig): IChatService {
switch (config.provider) {
case 'openai-compatible':
return new OpenAIChatService(config);
case 'anthropic':
// Anthropic 暂未实现,抛出友好错误
throw new Error(
'❌ Anthropic provider 暂未实现\n\n' +
'请使用 "openai-compatible" 提供商,或者:\n' +
'1. 等待官方实现\n' +
'2. 贡献代码实现此功能: https://github.com/echoVic/blade-code\n'
);
default:
logger.warn(`⚠️ 未知的 provider: ${config.provider}, 回退到 openai-compatible`);
return new OpenAIChatService(config);
}
}