@aituber-onair/core 0.3.0 → 0.4.0

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.
package/README.md CHANGED
@@ -198,9 +198,14 @@ src/
198
198
  │ │ ├── ChatServiceFactory.ts # Factory for providers
199
199
  │ │ └── providers/ # AI provider implementations
200
200
  │ │ ├── ChatServiceProvider.ts # Provider interface
201
+ │ │ ├── claude/ # Claude-specific
202
+ │ │ │ ├── ClaudeChatService.ts
203
+ │ │ │ ├── ClaudeChatServiceProvider.ts
204
+ │ │ │ └── ClaudeSummarizer.ts
201
205
  │ │ ├── gemini/ # Gemini-specific
202
206
  │ │ │ ├── GeminiChatService.ts
203
- │ │ │ └── GeminiChatServiceProvider.ts
207
+ │ │ │ ├── GeminiChatServiceProvider.ts
208
+ │ │ │ └── GeminiSummarizer.ts
204
209
  │ │ └── openai/ # OpenAI-specific
205
210
  │ │ ├── OpenAIChatService.ts
206
211
  │ │ ├── OpenAIChatServiceProvider.ts
@@ -435,7 +440,7 @@ This is useful when running voice engines on different ports or remote servers.
435
440
  ## AI Provider System
436
441
 
437
442
  AITuber OnAir Core adopts an extensible provider system, enabling integration with various AI APIs.
438
- Currently, OpenAI API and Gemini API is available, but other API providers (such as Claude API, etc.) are planned to be added soon.
443
+ Currently, OpenAI API, Gemini API, and Claude API are available. If you would like to use any other API, please submit a PR or send us a message.
439
444
 
440
445
  ### Available Providers
441
446
 
@@ -443,6 +448,7 @@ Currently, the following AI provider is built-in:
443
448
 
444
449
  - **OpenAI**: Supports models like GPT-4o, GPT-4o-mini, O3-mini, o1, o1-mini, GPT-4.5(Preview)
445
450
  - **Gemini**: Supports models like Gemini 2.0 Flash, Gemini 2.0 Flash-Lite, Gemini 1.5 Flash, Gemini 1.5 Pro, Gemini 2.5 Pro(Experimental)
451
+ - **Claude**: Supports models like Claude 3 Haiku, Claude 3.5 Haiku, Claude 3.5 Sonnet v2, Claude 3.7 Sonnet
446
452
 
447
453
  ### Specifying a Provider
448
454
 
@@ -0,0 +1,6 @@
1
+ export declare const ENDPOINT_CLAUDE_API = "https://api.anthropic.com/v1/messages";
2
+ export declare const MODEL_CLAUDE_3_HAIKU = "claude-3-haiku-20240307";
3
+ export declare const MODEL_CLAUDE_3_5_HAIKU = "claude-3-5-haiku-20241022";
4
+ export declare const MODEL_CLAUDE_3_5_SONNET = "claude-3-5-sonnet-20241022";
5
+ export declare const MODEL_CLAUDE_3_7_SONNET = "claude-3-7-sonnet-20250219";
6
+ export declare const CLAUDE_VISION_SUPPORTED_MODELS: string[];
@@ -0,0 +1,13 @@
1
+ export const ENDPOINT_CLAUDE_API = 'https://api.anthropic.com/v1/messages';
2
+ // claude model
3
+ export const MODEL_CLAUDE_3_HAIKU = 'claude-3-haiku-20240307';
4
+ export const MODEL_CLAUDE_3_5_HAIKU = 'claude-3-5-haiku-20241022';
5
+ export const MODEL_CLAUDE_3_5_SONNET = 'claude-3-5-sonnet-20241022';
6
+ export const MODEL_CLAUDE_3_7_SONNET = 'claude-3-7-sonnet-20250219';
7
+ export const CLAUDE_VISION_SUPPORTED_MODELS = [
8
+ MODEL_CLAUDE_3_HAIKU,
9
+ MODEL_CLAUDE_3_5_HAIKU,
10
+ MODEL_CLAUDE_3_5_SONNET,
11
+ MODEL_CLAUDE_3_7_SONNET,
12
+ ];
13
+ //# sourceMappingURL=claude.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"claude.js","sourceRoot":"","sources":["../../src/constants/claude.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,mBAAmB,GAAG,uCAAuC,CAAC;AAE3E,eAAe;AACf,MAAM,CAAC,MAAM,oBAAoB,GAAG,yBAAyB,CAAC;AAC9D,MAAM,CAAC,MAAM,sBAAsB,GAAG,2BAA2B,CAAC;AAClE,MAAM,CAAC,MAAM,uBAAuB,GAAG,4BAA4B,CAAC;AACpE,MAAM,CAAC,MAAM,uBAAuB,GAAG,4BAA4B,CAAC;AAEpE,MAAM,CAAC,MAAM,8BAA8B,GAAG;IAC5C,oBAAoB;IACpB,sBAAsB;IACtB,uBAAuB;IACvB,uBAAuB;CACxB,CAAC"}
@@ -5,5 +5,6 @@ export * from './voiceEngine';
5
5
  export * from './youtube';
6
6
  export * from './openai';
7
7
  export * from './gemini';
8
+ export * from './claude';
8
9
  export * from './chat';
9
10
  export * from './prompts';
@@ -5,6 +5,7 @@ export * from './voiceEngine';
5
5
  export * from './youtube';
6
6
  export * from './openai';
7
7
  export * from './gemini';
8
+ export * from './claude';
8
9
  export * from './chat';
9
10
  export * from './prompts';
10
11
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/constants/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,cAAc,eAAe,CAAC;AAC9B,cAAc,WAAW,CAAC;AAC1B,cAAc,UAAU,CAAC;AACzB,cAAc,UAAU,CAAC;AACzB,cAAc,QAAQ,CAAC;AACvB,cAAc,WAAW,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/constants/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,cAAc,eAAe,CAAC;AAC9B,cAAc,WAAW,CAAC;AAC1B,cAAc,UAAU,CAAC;AACzB,cAAc,UAAU,CAAC;AACzB,cAAc,UAAU,CAAC;AACzB,cAAc,QAAQ,CAAC;AACvB,cAAc,WAAW,CAAC"}
package/dist/index.d.ts CHANGED
@@ -11,6 +11,7 @@ export type { ChatServiceOptions, ChatServiceProvider, } from './services/chat/p
11
11
  export { ChatServiceFactory } from './services/chat/ChatServiceFactory';
12
12
  export { OpenAIChatServiceProvider } from './services/chat/providers/openai/OpenAIChatServiceProvider';
13
13
  export { GeminiChatServiceProvider } from './services/chat/providers/gemini/GeminiChatServiceProvider';
14
+ export { ClaudeChatServiceProvider } from './services/chat/providers/claude/ClaudeChatServiceProvider';
14
15
  export type { VoiceService, VoiceServiceOptions, AudioPlayOptions, } from './services/voice/VoiceService';
15
16
  export { VoiceEngineAdapter } from './services/voice/VoiceEngineAdapter';
16
17
  export { EventEmitter } from './core/EventEmitter';
package/dist/index.js CHANGED
@@ -10,6 +10,7 @@ export { GeminiSummarizer } from './services/chat/providers/gemini/GeminiSummari
10
10
  export { ChatServiceFactory } from './services/chat/ChatServiceFactory';
11
11
  export { OpenAIChatServiceProvider } from './services/chat/providers/openai/OpenAIChatServiceProvider';
12
12
  export { GeminiChatServiceProvider } from './services/chat/providers/gemini/GeminiChatServiceProvider';
13
+ export { ClaudeChatServiceProvider } from './services/chat/providers/claude/ClaudeChatServiceProvider';
13
14
  export { VoiceEngineAdapter } from './services/voice/VoiceEngineAdapter';
14
15
  // Core module exports
15
16
  export { EventEmitter } from './core/EventEmitter';
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,2BAA2B;AAC3B,cAAc,SAAS,CAAC;AAIxB,OAAO,EAAE,iBAAiB,EAAE,MAAM,oDAAoD,CAAC;AACvF,OAAO,EAAE,gBAAgB,EAAE,MAAM,mDAAmD,CAAC;AACrF,OAAO,EAAE,gBAAgB,EAAE,MAAM,mDAAmD,CAAC;AAOrF,OAAO,EAAE,kBAAkB,EAAE,MAAM,oCAAoC,CAAC;AACxE,OAAO,EAAE,yBAAyB,EAAE,MAAM,4DAA4D,CAAC;AACvG,OAAO,EAAE,yBAAyB,EAAE,MAAM,4DAA4D,CAAC;AAQvG,OAAO,EAAE,kBAAkB,EAAE,MAAM,qCAAqC,CAAC;AAEzE,sBAAsB;AACtB,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AAEnD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AAErD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AAErD,OAAO,EACL,gBAAgB,EAChB,qBAAqB,GACtB,MAAM,yBAAyB,CAAC;AAEjC,oBAAoB;AACpB,cAAc,aAAa,CAAC;AAE5B,kBAAkB;AAClB,cAAc,SAAS,CAAC;AACxB,OAAO,EAAE,mBAAmB,EAAE,MAAM,iBAAiB,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,2BAA2B;AAC3B,cAAc,SAAS,CAAC;AAIxB,OAAO,EAAE,iBAAiB,EAAE,MAAM,oDAAoD,CAAC;AACvF,OAAO,EAAE,gBAAgB,EAAE,MAAM,mDAAmD,CAAC;AACrF,OAAO,EAAE,gBAAgB,EAAE,MAAM,mDAAmD,CAAC;AAOrF,OAAO,EAAE,kBAAkB,EAAE,MAAM,oCAAoC,CAAC;AACxE,OAAO,EAAE,yBAAyB,EAAE,MAAM,4DAA4D,CAAC;AACvG,OAAO,EAAE,yBAAyB,EAAE,MAAM,4DAA4D,CAAC;AACvG,OAAO,EAAE,yBAAyB,EAAE,MAAM,4DAA4D,CAAC;AAQvG,OAAO,EAAE,kBAAkB,EAAE,MAAM,qCAAqC,CAAC;AAEzE,sBAAsB;AACtB,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AAEnD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AAErD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AAErD,OAAO,EACL,gBAAgB,EAChB,qBAAqB,GACtB,MAAM,yBAAyB,CAAC;AAEjC,oBAAoB;AACpB,cAAc,aAAa,CAAC;AAE5B,kBAAkB;AAClB,cAAc,SAAS,CAAC;AACxB,OAAO,EAAE,mBAAmB,EAAE,MAAM,iBAAiB,CAAC"}
@@ -1,5 +1,6 @@
1
1
  import { OpenAIChatServiceProvider } from './providers/openai/OpenAIChatServiceProvider';
2
2
  import { GeminiChatServiceProvider } from './providers/gemini/GeminiChatServiceProvider';
3
+ import { ClaudeChatServiceProvider } from './providers/claude/ClaudeChatServiceProvider';
3
4
  /**
4
5
  * Chat service factory
5
6
  * Manages and creates various AI providers
@@ -55,4 +56,6 @@ ChatServiceFactory.providers = new Map();
55
56
  ChatServiceFactory.registerProvider(new OpenAIChatServiceProvider());
56
57
  // Register Gemini as a provider
57
58
  ChatServiceFactory.registerProvider(new GeminiChatServiceProvider());
59
+ // Register Claude as a provider
60
+ ChatServiceFactory.registerProvider(new ClaudeChatServiceProvider());
58
61
  //# sourceMappingURL=ChatServiceFactory.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"ChatServiceFactory.js","sourceRoot":"","sources":["../../../src/services/chat/ChatServiceFactory.ts"],"names":[],"mappings":"AAKA,OAAO,EAAE,yBAAyB,EAAE,MAAM,8CAA8C,CAAC;AACzF,OAAO,EAAE,yBAAyB,EAAE,MAAM,8CAA8C,CAAC;AAEzF;;;GAGG;AACH,MAAM,OAAO,kBAAkB;IAI7B;;;OAGG;IACH,MAAM,CAAC,gBAAgB,CAAC,QAA6B;QACnD,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,QAAQ,CAAC,eAAe,EAAE,EAAE,QAAQ,CAAC,CAAC;IAC3D,CAAC;IAED;;;;;OAKG;IACH,MAAM,CAAC,iBAAiB,CACtB,YAAoB,EACpB,OAA2B;QAE3B,MAAM,QAAQ,GAAG,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,YAAY,CAAC,CAAC;QAClD,IAAI,CAAC,QAAQ,EAAE,CAAC;YACd,MAAM,IAAI,KAAK,CAAC,0BAA0B,YAAY,EAAE,CAAC,CAAC;QAC5D,CAAC;QACD,OAAO,QAAQ,CAAC,iBAAiB,CAAC,OAAO,CAAC,CAAC;IAC7C,CAAC;IAED;;;OAGG;IACH,MAAM,CAAC,YAAY;QACjB,OAAO,IAAI,CAAC,SAAS,CAAC;IACxB,CAAC;IAED;;;OAGG;IACH,MAAM,CAAC,qBAAqB;QAC1B,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,SAAS,CAAC,IAAI,EAAE,CAAC,CAAC;IAC3C,CAAC;IAED;;;;OAIG;IACH,MAAM,CAAC,kBAAkB,CAAC,YAAoB;QAC5C,MAAM,QAAQ,GAAG,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,YAAY,CAAC,CAAC;QAClD,OAAO,QAAQ,CAAC,CAAC,CAAC,QAAQ,CAAC,kBAAkB,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;IACvD,CAAC;;AApDD,kCAAkC;AACnB,4BAAS,GAAqC,IAAI,GAAG,EAAE,CAAC;AAsDzE,gCAAgC;AAChC,kBAAkB,CAAC,gBAAgB,CAAC,IAAI,yBAAyB,EAAE,CAAC,CAAC;AACrE,gCAAgC;AAChC,kBAAkB,CAAC,gBAAgB,CAAC,IAAI,yBAAyB,EAAE,CAAC,CAAC"}
1
+ {"version":3,"file":"ChatServiceFactory.js","sourceRoot":"","sources":["../../../src/services/chat/ChatServiceFactory.ts"],"names":[],"mappings":"AAKA,OAAO,EAAE,yBAAyB,EAAE,MAAM,8CAA8C,CAAC;AACzF,OAAO,EAAE,yBAAyB,EAAE,MAAM,8CAA8C,CAAC;AACzF,OAAO,EAAE,yBAAyB,EAAE,MAAM,8CAA8C,CAAC;AAEzF;;;GAGG;AACH,MAAM,OAAO,kBAAkB;IAI7B;;;OAGG;IACH,MAAM,CAAC,gBAAgB,CAAC,QAA6B;QACnD,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,QAAQ,CAAC,eAAe,EAAE,EAAE,QAAQ,CAAC,CAAC;IAC3D,CAAC;IAED;;;;;OAKG;IACH,MAAM,CAAC,iBAAiB,CACtB,YAAoB,EACpB,OAA2B;QAE3B,MAAM,QAAQ,GAAG,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,YAAY,CAAC,CAAC;QAClD,IAAI,CAAC,QAAQ,EAAE,CAAC;YACd,MAAM,IAAI,KAAK,CAAC,0BAA0B,YAAY,EAAE,CAAC,CAAC;QAC5D,CAAC;QACD,OAAO,QAAQ,CAAC,iBAAiB,CAAC,OAAO,CAAC,CAAC;IAC7C,CAAC;IAED;;;OAGG;IACH,MAAM,CAAC,YAAY;QACjB,OAAO,IAAI,CAAC,SAAS,CAAC;IACxB,CAAC;IAED;;;OAGG;IACH,MAAM,CAAC,qBAAqB;QAC1B,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,SAAS,CAAC,IAAI,EAAE,CAAC,CAAC;IAC3C,CAAC;IAED;;;;OAIG;IACH,MAAM,CAAC,kBAAkB,CAAC,YAAoB;QAC5C,MAAM,QAAQ,GAAG,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,YAAY,CAAC,CAAC;QAClD,OAAO,QAAQ,CAAC,CAAC,CAAC,QAAQ,CAAC,kBAAkB,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;IACvD,CAAC;;AApDD,kCAAkC;AACnB,4BAAS,GAAqC,IAAI,GAAG,EAAE,CAAC;AAsDzE,gCAAgC;AAChC,kBAAkB,CAAC,gBAAgB,CAAC,IAAI,yBAAyB,EAAE,CAAC,CAAC;AACrE,gCAAgC;AAChC,kBAAkB,CAAC,gBAAgB,CAAC,IAAI,yBAAyB,EAAE,CAAC,CAAC;AACrE,gCAAgC;AAChC,kBAAkB,CAAC,gBAAgB,CAAC,IAAI,yBAAyB,EAAE,CAAC,CAAC"}
@@ -0,0 +1,68 @@
1
+ import { ChatService } from '../../ChatService';
2
+ import { Message, MessageWithVision } from '../../../../types';
3
+ /**
4
+ * Claude implementation of ChatService
5
+ */
6
+ export declare class ClaudeChatService implements ChatService {
7
+ private apiKey;
8
+ private model;
9
+ private visionModel;
10
+ /** Provider name */
11
+ readonly provider: string;
12
+ /**
13
+ * Constructor
14
+ * @param apiKey Anthropic API key
15
+ * @param model Name of the model to use
16
+ * @param visionModel Name of the vision model
17
+ */
18
+ constructor(apiKey: string, model?: string, visionModel?: string);
19
+ /**
20
+ * Get the current model name
21
+ * @returns Model name
22
+ */
23
+ getModel(): string;
24
+ /**
25
+ * Get the current vision model name
26
+ * @returns Vision model name
27
+ */
28
+ getVisionModel(): string;
29
+ /**
30
+ * Process chat messages
31
+ * @param messages Array of messages to send
32
+ * @param onPartialResponse Callback to receive each part of streaming response
33
+ * @param onCompleteResponse Callback to execute when response is complete
34
+ */
35
+ processChat(messages: Message[], onPartialResponse: (text: string) => void, onCompleteResponse: (text: string) => Promise<void>): Promise<void>;
36
+ /**
37
+ * Process chat messages with images
38
+ * @param messages Array of messages to send (including images)
39
+ * @param onPartialResponse Callback to receive each part of streaming response
40
+ * @param onCompleteResponse Callback to execute when response is complete
41
+ * @throws Error if the selected model doesn't support vision
42
+ */
43
+ processVisionChat(messages: MessageWithVision[], onPartialResponse: (text: string) => void, onCompleteResponse: (text: string) => Promise<void>): Promise<void>;
44
+ /**
45
+ * Convert AITuber OnAir messages to Claude format
46
+ * @param messages Array of messages
47
+ * @returns Claude formatted messages
48
+ */
49
+ private convertMessagesToClaudeFormat;
50
+ /**
51
+ * Convert AITuber OnAir vision messages to Claude format
52
+ * @param messages Array of vision messages
53
+ * @returns Claude formatted vision messages
54
+ */
55
+ private convertVisionMessagesToClaudeFormat;
56
+ /**
57
+ * Map AITuber OnAir roles to Claude roles
58
+ * @param role AITuber OnAir role
59
+ * @returns Claude role
60
+ */
61
+ private mapRoleToClaude;
62
+ /**
63
+ * Get MIME type from URL
64
+ * @param url Image URL
65
+ * @returns MIME type
66
+ */
67
+ private getMimeTypeFromUrl;
68
+ }
@@ -0,0 +1,337 @@
1
+ import { ENDPOINT_CLAUDE_API, MODEL_CLAUDE_3_HAIKU, CLAUDE_VISION_SUPPORTED_MODELS, } from '../../../../constants';
2
+ /**
3
+ * Claude implementation of ChatService
4
+ */
5
+ export class ClaudeChatService {
6
+ /**
7
+ * Constructor
8
+ * @param apiKey Anthropic API key
9
+ * @param model Name of the model to use
10
+ * @param visionModel Name of the vision model
11
+ */
12
+ constructor(apiKey, model = MODEL_CLAUDE_3_HAIKU, visionModel = MODEL_CLAUDE_3_HAIKU) {
13
+ /** Provider name */
14
+ this.provider = 'claude';
15
+ this.apiKey = apiKey;
16
+ this.model = model || MODEL_CLAUDE_3_HAIKU;
17
+ this.visionModel = visionModel || MODEL_CLAUDE_3_HAIKU;
18
+ }
19
+ /**
20
+ * Get the current model name
21
+ * @returns Model name
22
+ */
23
+ getModel() {
24
+ return this.model;
25
+ }
26
+ /**
27
+ * Get the current vision model name
28
+ * @returns Vision model name
29
+ */
30
+ getVisionModel() {
31
+ return this.visionModel;
32
+ }
33
+ /**
34
+ * Process chat messages
35
+ * @param messages Array of messages to send
36
+ * @param onPartialResponse Callback to receive each part of streaming response
37
+ * @param onCompleteResponse Callback to execute when response is complete
38
+ */
39
+ async processChat(messages, onPartialResponse, onCompleteResponse) {
40
+ try {
41
+ // Extract system message (if any) and regular messages
42
+ const systemMessage = messages.find((msg) => msg.role === 'system');
43
+ const nonSystemMessages = messages.filter((msg) => msg.role !== 'system');
44
+ // Convert messages to Claude format
45
+ const claudeMessages = this.convertMessagesToClaudeFormat(nonSystemMessages);
46
+ // Request to Claude API
47
+ const response = await fetch(ENDPOINT_CLAUDE_API, {
48
+ method: 'POST',
49
+ headers: {
50
+ 'Content-Type': 'application/json',
51
+ 'x-api-key': this.apiKey,
52
+ 'anthropic-version': '2023-06-01',
53
+ 'anthropic-dangerous-direct-browser-access': 'true',
54
+ },
55
+ body: JSON.stringify({
56
+ model: this.model,
57
+ messages: claudeMessages,
58
+ system: systemMessage?.content || '',
59
+ stream: true,
60
+ max_tokens: 1000,
61
+ }),
62
+ });
63
+ if (!response.ok) {
64
+ const errorData = await response.json();
65
+ throw new Error(`Claude API error: ${errorData.error?.message || response.statusText}`);
66
+ }
67
+ // Process streaming response
68
+ const reader = response.body?.getReader();
69
+ const decoder = new TextDecoder('utf-8');
70
+ let fullText = '';
71
+ if (!reader) {
72
+ throw new Error('Failed to get response reader');
73
+ }
74
+ while (true) {
75
+ const { done, value } = await reader.read();
76
+ if (done)
77
+ break;
78
+ const chunk = decoder.decode(value);
79
+ // Claude API serves responses as Server-Sent Events (SSE)
80
+ // Each event is prefixed with "event: " and "data: "
81
+ const lines = chunk.split('\n').filter((line) => line.trim() !== '');
82
+ for (const line of lines) {
83
+ try {
84
+ // Check if this is a data line
85
+ if (line.startsWith('data: ')) {
86
+ const data = line.slice(6); // Remove 'data: ' prefix
87
+ // Ignore [DONE] marker
88
+ if (data === '[DONE]')
89
+ continue;
90
+ const json = JSON.parse(data);
91
+ // Extract delta content if available
92
+ if (json.type === 'content_block_delta') {
93
+ const deltaText = json.delta?.text || '';
94
+ if (deltaText) {
95
+ fullText += deltaText;
96
+ onPartialResponse(deltaText);
97
+ }
98
+ }
99
+ // Extract full message content if this is a message_start event
100
+ else if (json.type === 'message_start') {
101
+ // Initial message metadata, no text yet
102
+ }
103
+ // Extract content blocks from message
104
+ else if (json.type === 'content_block_start') {
105
+ // Content block metadata, no text yet
106
+ }
107
+ // Message completion
108
+ else if (json.type === 'message_stop') {
109
+ // Message is complete
110
+ }
111
+ }
112
+ }
113
+ catch (e) {
114
+ console.error('Error parsing Claude stream:', e);
115
+ }
116
+ }
117
+ }
118
+ // Complete response callback
119
+ await onCompleteResponse(fullText);
120
+ }
121
+ catch (error) {
122
+ console.error('Error in processChat:', error);
123
+ throw error;
124
+ }
125
+ }
126
+ /**
127
+ * Process chat messages with images
128
+ * @param messages Array of messages to send (including images)
129
+ * @param onPartialResponse Callback to receive each part of streaming response
130
+ * @param onCompleteResponse Callback to execute when response is complete
131
+ * @throws Error if the selected model doesn't support vision
132
+ */
133
+ async processVisionChat(messages, onPartialResponse, onCompleteResponse) {
134
+ try {
135
+ // Check if the vision model supports vision capabilities
136
+ if (!CLAUDE_VISION_SUPPORTED_MODELS.includes(this.visionModel)) {
137
+ throw new Error(`Model ${this.visionModel} does not support vision capabilities.`);
138
+ }
139
+ // Extract system message (if any) and regular messages
140
+ const systemMessage = messages.find((msg) => msg.role === 'system');
141
+ const nonSystemMessages = messages.filter((msg) => msg.role !== 'system');
142
+ // Convert messages to Claude vision format
143
+ const claudeMessages = this.convertVisionMessagesToClaudeFormat(nonSystemMessages);
144
+ // Request to Claude API
145
+ const response = await fetch(ENDPOINT_CLAUDE_API, {
146
+ method: 'POST',
147
+ headers: {
148
+ 'Content-Type': 'application/json',
149
+ 'x-api-key': this.apiKey,
150
+ 'anthropic-version': '2023-06-01',
151
+ 'anthropic-dangerous-direct-browser-access': 'true',
152
+ },
153
+ body: JSON.stringify({
154
+ model: this.visionModel,
155
+ messages: claudeMessages,
156
+ system: systemMessage?.content || '',
157
+ stream: true,
158
+ max_tokens: 1000,
159
+ }),
160
+ });
161
+ if (!response.ok) {
162
+ const errorData = await response.json();
163
+ throw new Error(`Claude API error: ${errorData.error?.message || response.statusText}`);
164
+ }
165
+ // Process streaming response
166
+ const reader = response.body?.getReader();
167
+ const decoder = new TextDecoder('utf-8');
168
+ let fullText = '';
169
+ if (!reader) {
170
+ throw new Error('Failed to get response reader');
171
+ }
172
+ while (true) {
173
+ const { done, value } = await reader.read();
174
+ if (done)
175
+ break;
176
+ const chunk = decoder.decode(value);
177
+ // Claude API serves responses as Server-Sent Events (SSE)
178
+ // Each event is prefixed with "event: " and "data: "
179
+ const lines = chunk.split('\n').filter((line) => line.trim() !== '');
180
+ for (const line of lines) {
181
+ try {
182
+ // Check if this is a data line
183
+ if (line.startsWith('data: ')) {
184
+ const data = line.slice(6); // Remove 'data: ' prefix
185
+ // Ignore [DONE] marker
186
+ if (data === '[DONE]')
187
+ continue;
188
+ const json = JSON.parse(data);
189
+ // Extract delta content if available
190
+ if (json.type === 'content_block_delta') {
191
+ const deltaText = json.delta?.text || '';
192
+ if (deltaText) {
193
+ fullText += deltaText;
194
+ onPartialResponse(deltaText);
195
+ }
196
+ }
197
+ // Other event types (handled same as in processChat)
198
+ }
199
+ }
200
+ catch (e) {
201
+ console.error('Error parsing Claude stream:', e);
202
+ }
203
+ }
204
+ }
205
+ // Complete response callback
206
+ await onCompleteResponse(fullText);
207
+ }
208
+ catch (error) {
209
+ console.error('Error in processVisionChat:', error);
210
+ throw error;
211
+ }
212
+ }
213
+ /**
214
+ * Convert AITuber OnAir messages to Claude format
215
+ * @param messages Array of messages
216
+ * @returns Claude formatted messages
217
+ */
218
+ convertMessagesToClaudeFormat(messages) {
219
+ return messages.map((msg) => {
220
+ return {
221
+ role: this.mapRoleToClaude(msg.role),
222
+ content: msg.content,
223
+ };
224
+ });
225
+ }
226
+ /**
227
+ * Convert AITuber OnAir vision messages to Claude format
228
+ * @param messages Array of vision messages
229
+ * @returns Claude formatted vision messages
230
+ */
231
+ convertVisionMessagesToClaudeFormat(messages) {
232
+ return messages.map((msg) => {
233
+ // If message content is a string, create a text-only message
234
+ if (typeof msg.content === 'string') {
235
+ return {
236
+ role: this.mapRoleToClaude(msg.role),
237
+ content: [
238
+ {
239
+ type: 'text',
240
+ text: msg.content,
241
+ },
242
+ ],
243
+ };
244
+ }
245
+ // If message content is an array of blocks, convert each block
246
+ else if (Array.isArray(msg.content)) {
247
+ const content = msg.content
248
+ .map((block) => {
249
+ if (block.type === 'text') {
250
+ return {
251
+ type: 'text',
252
+ text: block.text,
253
+ };
254
+ }
255
+ else if (block.type === 'image_url') {
256
+ // check if the image url is a data url
257
+ if (block.image_url.url.startsWith('data:')) {
258
+ // extract the base64 data from the data url
259
+ const matches = block.image_url.url.match(/^data:([A-Za-z-+/]+);base64,(.+)$/);
260
+ if (matches && matches.length >= 3) {
261
+ const mediaType = matches[1];
262
+ const base64Data = matches[2];
263
+ return {
264
+ type: 'image',
265
+ source: {
266
+ type: 'base64',
267
+ media_type: mediaType,
268
+ data: base64Data,
269
+ },
270
+ };
271
+ }
272
+ }
273
+ // if the image url is a normal url
274
+ return {
275
+ type: 'image',
276
+ source: {
277
+ type: 'url',
278
+ url: block.image_url.url,
279
+ media_type: this.getMimeTypeFromUrl(block.image_url.url),
280
+ },
281
+ };
282
+ }
283
+ return null;
284
+ })
285
+ .filter((item) => item !== null);
286
+ return {
287
+ role: this.mapRoleToClaude(msg.role),
288
+ content,
289
+ };
290
+ }
291
+ return {
292
+ role: this.mapRoleToClaude(msg.role),
293
+ content: [],
294
+ };
295
+ });
296
+ }
297
+ /**
298
+ * Map AITuber OnAir roles to Claude roles
299
+ * @param role AITuber OnAir role
300
+ * @returns Claude role
301
+ */
302
+ mapRoleToClaude(role) {
303
+ switch (role) {
304
+ case 'system':
305
+ // Claude handles system messages separately, but we'll map it anyway
306
+ return 'system';
307
+ case 'user':
308
+ return 'user';
309
+ case 'assistant':
310
+ return 'assistant';
311
+ default:
312
+ return 'user';
313
+ }
314
+ }
315
+ /**
316
+ * Get MIME type from URL
317
+ * @param url Image URL
318
+ * @returns MIME type
319
+ */
320
+ getMimeTypeFromUrl(url) {
321
+ const extension = url.split('.').pop()?.toLowerCase();
322
+ switch (extension) {
323
+ case 'jpg':
324
+ case 'jpeg':
325
+ return 'image/jpeg';
326
+ case 'png':
327
+ return 'image/png';
328
+ case 'gif':
329
+ return 'image/gif';
330
+ case 'webp':
331
+ return 'image/webp';
332
+ default:
333
+ return 'image/jpeg';
334
+ }
335
+ }
336
+ }
337
+ //# sourceMappingURL=ClaudeChatService.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ClaudeChatService.js","sourceRoot":"","sources":["../../../../../src/services/chat/providers/claude/ClaudeChatService.ts"],"names":[],"mappings":"AAEA,OAAO,EACL,mBAAmB,EACnB,oBAAoB,EACpB,8BAA8B,GAC/B,MAAM,uBAAuB,CAAC;AAE/B;;GAEG;AACH,MAAM,OAAO,iBAAiB;IAO5B;;;;;OAKG;IACH,YACE,MAAc,EACd,QAAgB,oBAAoB,EACpC,cAAsB,oBAAoB;QAZ5C,oBAAoB;QACX,aAAQ,GAAW,QAAQ,CAAC;QAanC,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;QACrB,IAAI,CAAC,KAAK,GAAG,KAAK,IAAI,oBAAoB,CAAC;QAC3C,IAAI,CAAC,WAAW,GAAG,WAAW,IAAI,oBAAoB,CAAC;IACzD,CAAC;IAED;;;OAGG;IACH,QAAQ;QACN,OAAO,IAAI,CAAC,KAAK,CAAC;IACpB,CAAC;IAED;;;OAGG;IACH,cAAc;QACZ,OAAO,IAAI,CAAC,WAAW,CAAC;IAC1B,CAAC;IAED;;;;;OAKG;IACH,KAAK,CAAC,WAAW,CACf,QAAmB,EACnB,iBAAyC,EACzC,kBAAmD;QAEnD,IAAI,CAAC;YACH,uDAAuD;YACvD,MAAM,aAAa,GAAG,QAAQ,CAAC,IAAI,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,IAAI,KAAK,QAAQ,CAAC,CAAC;YACpE,MAAM,iBAAiB,GAAG,QAAQ,CAAC,MAAM,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,IAAI,KAAK,QAAQ,CAAC,CAAC;YAE1E,oCAAoC;YACpC,MAAM,cAAc,GAClB,IAAI,CAAC,6BAA6B,CAAC,iBAAiB,CAAC,CAAC;YAExD,wBAAwB;YACxB,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,mBAAmB,EAAE;gBAChD,MAAM,EAAE,MAAM;gBACd,OAAO,EAAE;oBACP,cAAc,EAAE,kBAAkB;oBAClC,WAAW,EAAE,IAAI,CAAC,MAAM;oBACxB,mBAAmB,EAAE,YAAY;oBACjC,2CAA2C,EAAE,MAAM;iBACpD;gBACD,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC;oBACnB,KAAK,EAAE,IAAI,CAAC,KAAK;oBACjB,QAAQ,EAAE,cAAc;oBACxB,MAAM,EAAE,aAAa,EAAE,OAAO,IAAI,EAAE;oBACpC,MAAM,EAAE,IAAI;oBACZ,UAAU,EAAE,IAAI;iBACjB,CAAC;aACH,CAAC,CAAC;YAEH,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC;gBACjB,MAAM,SAAS,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;gBACxC,MAAM,IAAI,KAAK,CACb,qBAAqB,SAAS,CAAC,KAAK,EAAE,OAAO,IAAI,QAAQ,CAAC,UAAU,EAAE,CACvE,CAAC;YACJ,CAAC;YAED,6BAA6B;YAC7B,MAAM,MAAM,GAAG,QAAQ,CAAC,IAAI,EAAE,SAAS,EAAE,CAAC;YAC1C,MAAM,OAAO,GAAG,IAAI,WAAW,CAAC,OAAO,CAAC,CAAC;YACzC,IAAI,QAAQ,GAAG,EAAE,CAAC;YAElB,IAAI,CAAC,MAAM,EAAE,CAAC;gBACZ,MAAM,IAAI,KAAK,CAAC,+BAA+B,CAAC,CAAC;YACnD,CAAC;YAED,OAAO,IAAI,EAAE,CAAC;gBACZ,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,GAAG,MAAM,MAAM,CAAC,IAAI,EAAE,CAAC;gBAC5C,IAAI,IAAI;oBAAE,MAAM;gBAEhB,MAAM,KAAK,GAAG,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;gBACpC,0DAA0D;gBAC1D,qDAAqD;gBACrD,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,IAAI,EAAE,KAAK,EAAE,CAAC,CAAC;gBAErE,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;oBACzB,IAAI,CAAC;wBACH,+BAA+B;wBAC/B,IAAI,IAAI,CAAC,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;4BAC9B,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,yBAAyB;4BAErD,uBAAuB;4BACvB,IAAI,IAAI,KAAK,QAAQ;gCAAE,SAAS;4BAEhC,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;4BAE9B,qCAAqC;4BACrC,IAAI,IAAI,CAAC,IAAI,KAAK,qBAAqB,EAAE,CAAC;gCACxC,MAAM,SAAS,GAAG,IAAI,CAAC,KAAK,EAAE,IAAI,IAAI,EAAE,CAAC;gCACzC,IAAI,SAAS,EAAE,CAAC;oCACd,QAAQ,IAAI,SAAS,CAAC;oCACtB,iBAAiB,CAAC,SAAS,CAAC,CAAC;gCAC/B,CAAC;4BACH,CAAC;4BACD,gEAAgE;iCAC3D,IAAI,IAAI,CAAC,IAAI,KAAK,eAAe,EAAE,CAAC;gCACvC,wCAAwC;4BAC1C,CAAC;4BACD,sCAAsC;iCACjC,IAAI,IAAI,CAAC,IAAI,KAAK,qBAAqB,EAAE,CAAC;gCAC7C,sCAAsC;4BACxC,CAAC;4BACD,qBAAqB;iCAChB,IAAI,IAAI,CAAC,IAAI,KAAK,cAAc,EAAE,CAAC;gCACtC,sBAAsB;4BACxB,CAAC;wBACH,CAAC;oBACH,CAAC;oBAAC,OAAO,CAAC,EAAE,CAAC;wBACX,OAAO,CAAC,KAAK,CAAC,8BAA8B,EAAE,CAAC,CAAC,CAAC;oBACnD,CAAC;gBACH,CAAC;YACH,CAAC;YAED,6BAA6B;YAC7B,MAAM,kBAAkB,CAAC,QAAQ,CAAC,CAAC;QACrC,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,CAAC,KAAK,CAAC,uBAAuB,EAAE,KAAK,CAAC,CAAC;YAC9C,MAAM,KAAK,CAAC;QACd,CAAC;IACH,CAAC;IAED;;;;;;OAMG;IACH,KAAK,CAAC,iBAAiB,CACrB,QAA6B,EAC7B,iBAAyC,EACzC,kBAAmD;QAEnD,IAAI,CAAC;YACH,yDAAyD;YACzD,IAAI,CAAC,8BAA8B,CAAC,QAAQ,CAAC,IAAI,CAAC,WAAW,CAAC,EAAE,CAAC;gBAC/D,MAAM,IAAI,KAAK,CACb,SAAS,IAAI,CAAC,WAAW,wCAAwC,CAClE,CAAC;YACJ,CAAC;YAED,uDAAuD;YACvD,MAAM,aAAa,GAAG,QAAQ,CAAC,IAAI,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,IAAI,KAAK,QAAQ,CAAC,CAAC;YACpE,MAAM,iBAAiB,GAAG,QAAQ,CAAC,MAAM,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,IAAI,KAAK,QAAQ,CAAC,CAAC;YAE1E,2CAA2C;YAC3C,MAAM,cAAc,GAClB,IAAI,CAAC,mCAAmC,CAAC,iBAAiB,CAAC,CAAC;YAE9D,wBAAwB;YACxB,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,mBAAmB,EAAE;gBAChD,MAAM,EAAE,MAAM;gBACd,OAAO,EAAE;oBACP,cAAc,EAAE,kBAAkB;oBAClC,WAAW,EAAE,IAAI,CAAC,MAAM;oBACxB,mBAAmB,EAAE,YAAY;oBACjC,2CAA2C,EAAE,MAAM;iBACpD;gBACD,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC;oBACnB,KAAK,EAAE,IAAI,CAAC,WAAW;oBACvB,QAAQ,EAAE,cAAc;oBACxB,MAAM,EAAE,aAAa,EAAE,OAAO,IAAI,EAAE;oBACpC,MAAM,EAAE,IAAI;oBACZ,UAAU,EAAE,IAAI;iBACjB,CAAC;aACH,CAAC,CAAC;YAEH,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC;gBACjB,MAAM,SAAS,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;gBACxC,MAAM,IAAI,KAAK,CACb,qBAAqB,SAAS,CAAC,KAAK,EAAE,OAAO,IAAI,QAAQ,CAAC,UAAU,EAAE,CACvE,CAAC;YACJ,CAAC;YAED,6BAA6B;YAC7B,MAAM,MAAM,GAAG,QAAQ,CAAC,IAAI,EAAE,SAAS,EAAE,CAAC;YAC1C,MAAM,OAAO,GAAG,IAAI,WAAW,CAAC,OAAO,CAAC,CAAC;YACzC,IAAI,QAAQ,GAAG,EAAE,CAAC;YAElB,IAAI,CAAC,MAAM,EAAE,CAAC;gBACZ,MAAM,IAAI,KAAK,CAAC,+BAA+B,CAAC,CAAC;YACnD,CAAC;YAED,OAAO,IAAI,EAAE,CAAC;gBACZ,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,GAAG,MAAM,MAAM,CAAC,IAAI,EAAE,CAAC;gBAC5C,IAAI,IAAI;oBAAE,MAAM;gBAEhB,MAAM,KAAK,GAAG,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;gBACpC,0DAA0D;gBAC1D,qDAAqD;gBACrD,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,IAAI,EAAE,KAAK,EAAE,CAAC,CAAC;gBAErE,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;oBACzB,IAAI,CAAC;wBACH,+BAA+B;wBAC/B,IAAI,IAAI,CAAC,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;4BAC9B,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,yBAAyB;4BAErD,uBAAuB;4BACvB,IAAI,IAAI,KAAK,QAAQ;gCAAE,SAAS;4BAEhC,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;4BAE9B,qCAAqC;4BACrC,IAAI,IAAI,CAAC,IAAI,KAAK,qBAAqB,EAAE,CAAC;gCACxC,MAAM,SAAS,GAAG,IAAI,CAAC,KAAK,EAAE,IAAI,IAAI,EAAE,CAAC;gCACzC,IAAI,SAAS,EAAE,CAAC;oCACd,QAAQ,IAAI,SAAS,CAAC;oCACtB,iBAAiB,CAAC,SAAS,CAAC,CAAC;gCAC/B,CAAC;4BACH,CAAC;4BACD,qDAAqD;wBACvD,CAAC;oBACH,CAAC;oBAAC,OAAO,CAAC,EAAE,CAAC;wBACX,OAAO,CAAC,KAAK,CAAC,8BAA8B,EAAE,CAAC,CAAC,CAAC;oBACnD,CAAC;gBACH,CAAC;YACH,CAAC;YAED,6BAA6B;YAC7B,MAAM,kBAAkB,CAAC,QAAQ,CAAC,CAAC;QACrC,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,CAAC,KAAK,CAAC,6BAA6B,EAAE,KAAK,CAAC,CAAC;YACpD,MAAM,KAAK,CAAC;QACd,CAAC;IACH,CAAC;IAED;;;;OAIG;IACK,6BAA6B,CAAC,QAAmB;QACvD,OAAO,QAAQ,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE;YAC1B,OAAO;gBACL,IAAI,EAAE,IAAI,CAAC,eAAe,CAAC,GAAG,CAAC,IAAI,CAAC;gBACpC,OAAO,EAAE,GAAG,CAAC,OAAO;aACrB,CAAC;QACJ,CAAC,CAAC,CAAC;IACL,CAAC;IAED;;;;OAIG;IACK,mCAAmC,CACzC,QAA6B;QAE7B,OAAO,QAAQ,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE;YAC1B,6DAA6D;YAC7D,IAAI,OAAO,GAAG,CAAC,OAAO,KAAK,QAAQ,EAAE,CAAC;gBACpC,OAAO;oBACL,IAAI,EAAE,IAAI,CAAC,eAAe,CAAC,GAAG,CAAC,IAAI,CAAC;oBACpC,OAAO,EAAE;wBACP;4BACE,IAAI,EAAE,MAAM;4BACZ,IAAI,EAAE,GAAG,CAAC,OAAO;yBAClB;qBACF;iBACF,CAAC;YACJ,CAAC;YACD,+DAA+D;iBAC1D,IAAI,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,EAAE,CAAC;gBACpC,MAAM,OAAO,GAAG,GAAG,CAAC,OAAO;qBACxB,GAAG,CAAC,CAAC,KAAK,EAAE,EAAE;oBACb,IAAI,KAAK,CAAC,IAAI,KAAK,MAAM,EAAE,CAAC;wBAC1B,OAAO;4BACL,IAAI,EAAE,MAAM;4BACZ,IAAI,EAAE,KAAK,CAAC,IAAI;yBACjB,CAAC;oBACJ,CAAC;yBAAM,IAAI,KAAK,CAAC,IAAI,KAAK,WAAW,EAAE,CAAC;wBACtC,uCAAuC;wBACvC,IAAI,KAAK,CAAC,SAAS,CAAC,GAAG,CAAC,UAAU,CAAC,OAAO,CAAC,EAAE,CAAC;4BAC5C,4CAA4C;4BAC5C,MAAM,OAAO,GAAG,KAAK,CAAC,SAAS,CAAC,GAAG,CAAC,KAAK,CACvC,mCAAmC,CACpC,CAAC;4BACF,IAAI,OAAO,IAAI,OAAO,CAAC,MAAM,IAAI,CAAC,EAAE,CAAC;gCACnC,MAAM,SAAS,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;gCAC7B,MAAM,UAAU,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;gCAC9B,OAAO;oCACL,IAAI,EAAE,OAAO;oCACb,MAAM,EAAE;wCACN,IAAI,EAAE,QAAQ;wCACd,UAAU,EAAE,SAAS;wCACrB,IAAI,EAAE,UAAU;qCACjB;iCACF,CAAC;4BACJ,CAAC;wBACH,CAAC;wBAED,mCAAmC;wBACnC,OAAO;4BACL,IAAI,EAAE,OAAO;4BACb,MAAM,EAAE;gCACN,IAAI,EAAE,KAAK;gCACX,GAAG,EAAE,KAAK,CAAC,SAAS,CAAC,GAAG;gCACxB,UAAU,EAAE,IAAI,CAAC,kBAAkB,CAAC,KAAK,CAAC,SAAS,CAAC,GAAG,CAAC;6BACzD;yBACF,CAAC;oBACJ,CAAC;oBACD,OAAO,IAAI,CAAC;gBACd,CAAC,CAAC;qBACD,MAAM,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,KAAK,IAAI,CAAC,CAAC;gBAEnC,OAAO;oBACL,IAAI,EAAE,IAAI,CAAC,eAAe,CAAC,GAAG,CAAC,IAAI,CAAC;oBACpC,OAAO;iBACR,CAAC;YACJ,CAAC;YAED,OAAO;gBACL,IAAI,EAAE,IAAI,CAAC,eAAe,CAAC,GAAG,CAAC,IAAI,CAAC;gBACpC,OAAO,EAAE,EAAE;aACZ,CAAC;QACJ,CAAC,CAAC,CAAC;IACL,CAAC;IAED;;;;OAIG;IACK,eAAe,CAAC,IAAY;QAClC,QAAQ,IAAI,EAAE,CAAC;YACb,KAAK,QAAQ;gBACX,qEAAqE;gBACrE,OAAO,QAAQ,CAAC;YAClB,KAAK,MAAM;gBACT,OAAO,MAAM,CAAC;YAChB,KAAK,WAAW;gBACd,OAAO,WAAW,CAAC;YACrB;gBACE,OAAO,MAAM,CAAC;QAClB,CAAC;IACH,CAAC;IAED;;;;OAIG;IACK,kBAAkB,CAAC,GAAW;QACpC,MAAM,SAAS,GAAG,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE,WAAW,EAAE,CAAC;QACtD,QAAQ,SAAS,EAAE,CAAC;YAClB,KAAK,KAAK,CAAC;YACX,KAAK,MAAM;gBACT,OAAO,YAAY,CAAC;YACtB,KAAK,KAAK;gBACR,OAAO,WAAW,CAAC;YACrB,KAAK,KAAK;gBACR,OAAO,WAAW,CAAC;YACrB,KAAK,MAAM;gBACT,OAAO,YAAY,CAAC;YACtB;gBACE,OAAO,YAAY,CAAC;QACxB,CAAC;IACH,CAAC;CACF"}
@@ -0,0 +1,39 @@
1
+ import { ChatService } from '../../ChatService';
2
+ import { ChatServiceOptions, ChatServiceProvider } from '../ChatServiceProvider';
3
+ /**
4
+ * Claude API provider implementation
5
+ */
6
+ export declare class ClaudeChatServiceProvider implements ChatServiceProvider {
7
+ /**
8
+ * Create a chat service instance
9
+ * @param options Service options
10
+ * @returns ClaudeChatService instance
11
+ */
12
+ createChatService(options: ChatServiceOptions): ChatService;
13
+ /**
14
+ * Get the provider name
15
+ * @returns Provider name ('claude')
16
+ */
17
+ getProviderName(): string;
18
+ /**
19
+ * Get the list of supported models
20
+ * @returns Array of supported model names
21
+ */
22
+ getSupportedModels(): string[];
23
+ /**
24
+ * Get the default model
25
+ * @returns Default model name
26
+ */
27
+ getDefaultModel(): string;
28
+ /**
29
+ * Check if this provider supports vision (image processing)
30
+ * @returns Vision support status (true)
31
+ */
32
+ supportsVision(): boolean;
33
+ /**
34
+ * Check if a specific model supports vision capabilities
35
+ * @param model The model name to check
36
+ * @returns True if the model supports vision, false otherwise
37
+ */
38
+ supportsVisionForModel(model: string): boolean;
39
+ }
@@ -0,0 +1,62 @@
1
+ import { MODEL_CLAUDE_3_HAIKU, MODEL_CLAUDE_3_5_HAIKU, MODEL_CLAUDE_3_5_SONNET, MODEL_CLAUDE_3_7_SONNET, CLAUDE_VISION_SUPPORTED_MODELS, } from '../../../../constants';
2
+ import { ClaudeChatService } from './ClaudeChatService';
3
+ /**
4
+ * Claude API provider implementation
5
+ */
6
+ export class ClaudeChatServiceProvider {
7
+ /**
8
+ * Create a chat service instance
9
+ * @param options Service options
10
+ * @returns ClaudeChatService instance
11
+ */
12
+ createChatService(options) {
13
+ // Use the visionModel if provided, otherwise use the model that supports vision
14
+ const visionModel = options.visionModel ||
15
+ (this.supportsVisionForModel(options.model || this.getDefaultModel())
16
+ ? options.model
17
+ : this.getDefaultModel());
18
+ return new ClaudeChatService(options.apiKey, options.model || this.getDefaultModel(), visionModel);
19
+ }
20
+ /**
21
+ * Get the provider name
22
+ * @returns Provider name ('claude')
23
+ */
24
+ getProviderName() {
25
+ return 'claude';
26
+ }
27
+ /**
28
+ * Get the list of supported models
29
+ * @returns Array of supported model names
30
+ */
31
+ getSupportedModels() {
32
+ return [
33
+ MODEL_CLAUDE_3_HAIKU,
34
+ MODEL_CLAUDE_3_5_HAIKU,
35
+ MODEL_CLAUDE_3_5_SONNET,
36
+ MODEL_CLAUDE_3_7_SONNET,
37
+ ];
38
+ }
39
+ /**
40
+ * Get the default model
41
+ * @returns Default model name
42
+ */
43
+ getDefaultModel() {
44
+ return MODEL_CLAUDE_3_HAIKU;
45
+ }
46
+ /**
47
+ * Check if this provider supports vision (image processing)
48
+ * @returns Vision support status (true)
49
+ */
50
+ supportsVision() {
51
+ return true;
52
+ }
53
+ /**
54
+ * Check if a specific model supports vision capabilities
55
+ * @param model The model name to check
56
+ * @returns True if the model supports vision, false otherwise
57
+ */
58
+ supportsVisionForModel(model) {
59
+ return CLAUDE_VISION_SUPPORTED_MODELS.includes(model);
60
+ }
61
+ }
62
+ //# sourceMappingURL=ClaudeChatServiceProvider.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ClaudeChatServiceProvider.js","sourceRoot":"","sources":["../../../../../src/services/chat/providers/claude/ClaudeChatServiceProvider.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,oBAAoB,EACpB,sBAAsB,EACtB,uBAAuB,EACvB,uBAAuB,EACvB,8BAA8B,GAC/B,MAAM,uBAAuB,CAAC;AAE/B,OAAO,EAAE,iBAAiB,EAAE,MAAM,qBAAqB,CAAC;AAMxD;;GAEG;AACH,MAAM,OAAO,yBAAyB;IACpC;;;;OAIG;IACH,iBAAiB,CAAC,OAA2B;QAC3C,gFAAgF;QAChF,MAAM,WAAW,GACf,OAAO,CAAC,WAAW;YACnB,CAAC,IAAI,CAAC,sBAAsB,CAAC,OAAO,CAAC,KAAK,IAAI,IAAI,CAAC,eAAe,EAAE,CAAC;gBACnE,CAAC,CAAC,OAAO,CAAC,KAAK;gBACf,CAAC,CAAC,IAAI,CAAC,eAAe,EAAE,CAAC,CAAC;QAE9B,OAAO,IAAI,iBAAiB,CAC1B,OAAO,CAAC,MAAM,EACd,OAAO,CAAC,KAAK,IAAI,IAAI,CAAC,eAAe,EAAE,EACvC,WAAW,CACZ,CAAC;IACJ,CAAC;IAED;;;OAGG;IACH,eAAe;QACb,OAAO,QAAQ,CAAC;IAClB,CAAC;IAED;;;OAGG;IACH,kBAAkB;QAChB,OAAO;YACL,oBAAoB;YACpB,sBAAsB;YACtB,uBAAuB;YACvB,uBAAuB;SACxB,CAAC;IACJ,CAAC;IAED;;;OAGG;IACH,eAAe;QACb,OAAO,oBAAoB,CAAC;IAC9B,CAAC;IAED;;;OAGG;IACH,cAAc;QACZ,OAAO,IAAI,CAAC;IACd,CAAC;IAED;;;;OAIG;IACH,sBAAsB,CAAC,KAAa;QAClC,OAAO,8BAA8B,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC;IACxD,CAAC;CACF"}
@@ -0,0 +1,25 @@
1
+ import { Message } from '../../../../types';
2
+ import { Summarizer } from '../../../../core/MemoryManager';
3
+ /**
4
+ * Implementation of summarization functionality using Claude
5
+ */
6
+ export declare class ClaudeSummarizer implements Summarizer {
7
+ private apiKey;
8
+ private model;
9
+ private defaultPromptTemplate;
10
+ /**
11
+ * Constructor
12
+ * @param apiKey Anthropic API key
13
+ * @param model Name of the model to use
14
+ * @param defaultPromptTemplate Default prompt template for summarization
15
+ */
16
+ constructor(apiKey: string, model?: string, defaultPromptTemplate?: string);
17
+ /**
18
+ * Summarize chat messages
19
+ * @param messages Array of messages to summarize
20
+ * @param maxLength Maximum number of characters (default 256)
21
+ * @param customPrompt Custom prompt template for summarization (optional)
22
+ * @returns Summarized text
23
+ */
24
+ summarize(messages: Message[], maxLength?: number, customPrompt?: string): Promise<string>;
25
+ }
@@ -0,0 +1,68 @@
1
+ import { ENDPOINT_CLAUDE_API, MODEL_CLAUDE_3_HAIKU, } from '../../../../constants';
2
+ import { DEFAULT_SUMMARY_PROMPT_TEMPLATE } from '../../../../constants';
3
+ /**
4
+ * Implementation of summarization functionality using Claude
5
+ */
6
+ export class ClaudeSummarizer {
7
+ /**
8
+ * Constructor
9
+ * @param apiKey Anthropic API key
10
+ * @param model Name of the model to use
11
+ * @param defaultPromptTemplate Default prompt template for summarization
12
+ */
13
+ constructor(apiKey, model = MODEL_CLAUDE_3_HAIKU, defaultPromptTemplate = DEFAULT_SUMMARY_PROMPT_TEMPLATE) {
14
+ this.apiKey = apiKey;
15
+ this.model = model;
16
+ this.defaultPromptTemplate = defaultPromptTemplate;
17
+ }
18
+ /**
19
+ * Summarize chat messages
20
+ * @param messages Array of messages to summarize
21
+ * @param maxLength Maximum number of characters (default 256)
22
+ * @param customPrompt Custom prompt template for summarization (optional)
23
+ * @returns Summarized text
24
+ */
25
+ async summarize(messages, maxLength = 256, customPrompt) {
26
+ try {
27
+ // Create system prompt
28
+ const promptTemplate = customPrompt || this.defaultPromptTemplate;
29
+ const systemPrompt = promptTemplate.replace('{maxLength}', maxLength.toString());
30
+ // Join message content
31
+ const conversationText = messages
32
+ .map((msg) => `${msg.role}: ${msg.content}`)
33
+ .join('\n');
34
+ // API request
35
+ const response = await fetch(ENDPOINT_CLAUDE_API, {
36
+ method: 'POST',
37
+ headers: {
38
+ 'Content-Type': 'application/json',
39
+ 'x-api-key': this.apiKey,
40
+ 'anthropic-version': '2023-06-01',
41
+ 'anthropic-dangerous-direct-browser-access': 'true',
42
+ },
43
+ body: JSON.stringify({
44
+ model: this.model,
45
+ messages: [
46
+ {
47
+ role: 'user',
48
+ content: `${systemPrompt}\n\n${conversationText}`,
49
+ },
50
+ ],
51
+ max_tokens: maxLength,
52
+ }),
53
+ });
54
+ if (!response.ok) {
55
+ const errorData = await response.json();
56
+ throw new Error(`Claude API error: ${errorData.error?.message || response.statusText}`);
57
+ }
58
+ const data = await response.json();
59
+ return data.content?.[0]?.text || '';
60
+ }
61
+ catch (error) {
62
+ console.error('Error in summarize:', error);
63
+ // Error fallback - simple summary
64
+ return `${messages.length} messages. Latest topic: ${messages[messages.length - 1]?.content.substring(0, 50) || 'none'}...`;
65
+ }
66
+ }
67
+ }
68
+ //# sourceMappingURL=ClaudeSummarizer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ClaudeSummarizer.js","sourceRoot":"","sources":["../../../../../src/services/chat/providers/claude/ClaudeSummarizer.ts"],"names":[],"mappings":"AAEA,OAAO,EACL,mBAAmB,EACnB,oBAAoB,GACrB,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EAAE,+BAA+B,EAAE,MAAM,uBAAuB,CAAC;AAExE;;GAEG;AACH,MAAM,OAAO,gBAAgB;IAK3B;;;;;OAKG;IACH,YACE,MAAc,EACd,QAAgB,oBAAoB,EACpC,wBAAgC,+BAA+B;QAE/D,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;QACrB,IAAI,CAAC,KAAK,GAAG,KAAK,CAAC;QACnB,IAAI,CAAC,qBAAqB,GAAG,qBAAqB,CAAC;IACrD,CAAC;IAED;;;;;;OAMG;IACH,KAAK,CAAC,SAAS,CACb,QAAmB,EACnB,YAAoB,GAAG,EACvB,YAAqB;QAErB,IAAI,CAAC;YACH,uBAAuB;YACvB,MAAM,cAAc,GAAG,YAAY,IAAI,IAAI,CAAC,qBAAqB,CAAC;YAClE,MAAM,YAAY,GAAG,cAAc,CAAC,OAAO,CACzC,aAAa,EACb,SAAS,CAAC,QAAQ,EAAE,CACrB,CAAC;YAEF,uBAAuB;YACvB,MAAM,gBAAgB,GAAG,QAAQ;iBAC9B,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,GAAG,CAAC,IAAI,KAAK,GAAG,CAAC,OAAO,EAAE,CAAC;iBAC3C,IAAI,CAAC,IAAI,CAAC,CAAC;YAEd,cAAc;YACd,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,mBAAmB,EAAE;gBAChD,MAAM,EAAE,MAAM;gBACd,OAAO,EAAE;oBACP,cAAc,EAAE,kBAAkB;oBAClC,WAAW,EAAE,IAAI,CAAC,MAAM;oBACxB,mBAAmB,EAAE,YAAY;oBACjC,2CAA2C,EAAE,MAAM;iBACpD;gBACD,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC;oBACnB,KAAK,EAAE,IAAI,CAAC,KAAK;oBACjB,QAAQ,EAAE;wBACR;4BACE,IAAI,EAAE,MAAM;4BACZ,OAAO,EAAE,GAAG,YAAY,OAAO,gBAAgB,EAAE;yBAClD;qBACF;oBACD,UAAU,EAAE,SAAS;iBACtB,CAAC;aACH,CAAC,CAAC;YAEH,IAAI,CAAC,QAAQ,CAAC,EAAE,EAAE,CAAC;gBACjB,MAAM,SAAS,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;gBACxC,MAAM,IAAI,KAAK,CACb,qBAAqB,SAAS,CAAC,KAAK,EAAE,OAAO,IAAI,QAAQ,CAAC,UAAU,EAAE,CACvE,CAAC;YACJ,CAAC;YAED,MAAM,IAAI,GAAG,MAAM,QAAQ,CAAC,IAAI,EAAE,CAAC;YACnC,OAAO,IAAI,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC,EAAE,IAAI,IAAI,EAAE,CAAC;QACvC,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,CAAC,KAAK,CAAC,qBAAqB,EAAE,KAAK,CAAC,CAAC;YAC5C,kCAAkC;YAClC,OAAO,GAAG,QAAQ,CAAC,MAAM,4BACvB,QAAQ,CAAC,QAAQ,CAAC,MAAM,GAAG,CAAC,CAAC,EAAE,OAAO,CAAC,SAAS,CAAC,CAAC,EAAE,EAAE,CAAC,IAAI,MAC7D,KAAK,CAAC;QACR,CAAC;IACH,CAAC;CACF"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@aituber-onair/core",
3
- "version": "0.3.0",
3
+ "version": "0.4.0",
4
4
  "description": "Core library for AITuber OnAir providing voice synthesis and chat processing",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.js",