@imenam/unified-llm-client 1.2.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.
Files changed (93) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +233 -0
  3. package/dist/adapters/anthropic/AnthropicLogAdapter.d.ts +6 -0
  4. package/dist/adapters/anthropic/AnthropicLogAdapter.d.ts.map +1 -0
  5. package/dist/adapters/anthropic/AnthropicLogAdapter.js +41 -0
  6. package/dist/adapters/anthropic/AnthropicOutputAdapter.d.ts +6 -0
  7. package/dist/adapters/anthropic/AnthropicOutputAdapter.d.ts.map +1 -0
  8. package/dist/adapters/anthropic/AnthropicOutputAdapter.js +41 -0
  9. package/dist/adapters/anthropic/AnthropicPromptAdapter.d.ts +12 -0
  10. package/dist/adapters/anthropic/AnthropicPromptAdapter.d.ts.map +1 -0
  11. package/dist/adapters/anthropic/AnthropicPromptAdapter.js +249 -0
  12. package/dist/adapters/anthropic/AnthropicToolAdapter.d.ts +6 -0
  13. package/dist/adapters/anthropic/AnthropicToolAdapter.d.ts.map +1 -0
  14. package/dist/adapters/anthropic/AnthropicToolAdapter.js +20 -0
  15. package/dist/adapters/gemini/GeminiAudioAdapter.d.ts +40 -0
  16. package/dist/adapters/gemini/GeminiAudioAdapter.d.ts.map +1 -0
  17. package/dist/adapters/gemini/GeminiAudioAdapter.js +273 -0
  18. package/dist/adapters/gemini/GeminiLogAdapter.d.ts +6 -0
  19. package/dist/adapters/gemini/GeminiLogAdapter.d.ts.map +1 -0
  20. package/dist/adapters/gemini/GeminiLogAdapter.js +43 -0
  21. package/dist/adapters/gemini/GeminiOutputAdapter.d.ts +6 -0
  22. package/dist/adapters/gemini/GeminiOutputAdapter.d.ts.map +1 -0
  23. package/dist/adapters/gemini/GeminiOutputAdapter.js +38 -0
  24. package/dist/adapters/gemini/GeminiPromptAdapter.d.ts +26 -0
  25. package/dist/adapters/gemini/GeminiPromptAdapter.d.ts.map +1 -0
  26. package/dist/adapters/gemini/GeminiPromptAdapter.js +334 -0
  27. package/dist/adapters/gemini/GeminiToolAdapter.d.ts +8 -0
  28. package/dist/adapters/gemini/GeminiToolAdapter.d.ts.map +1 -0
  29. package/dist/adapters/gemini/GeminiToolAdapter.js +42 -0
  30. package/dist/adapters/gemini/types.d.ts +14 -0
  31. package/dist/adapters/gemini/types.d.ts.map +1 -0
  32. package/dist/adapters/gemini/types.js +2 -0
  33. package/dist/adapters/openai/OpenAIOutputAdapter.d.ts +6 -0
  34. package/dist/adapters/openai/OpenAIOutputAdapter.d.ts.map +1 -0
  35. package/dist/adapters/openai/OpenAIOutputAdapter.js +18 -0
  36. package/dist/adapters/openai/OpenAIPromptAdapter.d.ts +13 -0
  37. package/dist/adapters/openai/OpenAIPromptAdapter.d.ts.map +1 -0
  38. package/dist/adapters/openai/OpenAIPromptAdapter.js +215 -0
  39. package/dist/adapters/openai/OpenAiLogAdapter.d.ts +6 -0
  40. package/dist/adapters/openai/OpenAiLogAdapter.d.ts.map +1 -0
  41. package/dist/adapters/openai/OpenAiLogAdapter.js +37 -0
  42. package/dist/adapters/openai/OpenAiToolAdapter.d.ts +6 -0
  43. package/dist/adapters/openai/OpenAiToolAdapter.d.ts.map +1 -0
  44. package/dist/adapters/openai/OpenAiToolAdapter.js +20 -0
  45. package/dist/adapters/qwen/QwenLogAdapter.d.ts +7 -0
  46. package/dist/adapters/qwen/QwenLogAdapter.d.ts.map +1 -0
  47. package/dist/adapters/qwen/QwenLogAdapter.js +49 -0
  48. package/dist/adapters/qwen/QwenOutputAdapter.d.ts +6 -0
  49. package/dist/adapters/qwen/QwenOutputAdapter.d.ts.map +1 -0
  50. package/dist/adapters/qwen/QwenOutputAdapter.js +9 -0
  51. package/dist/adapters/qwen/QwenPromptAdapter.d.ts +13 -0
  52. package/dist/adapters/qwen/QwenPromptAdapter.d.ts.map +1 -0
  53. package/dist/adapters/qwen/QwenPromptAdapter.js +313 -0
  54. package/dist/adapters/qwen/QwenToolAdapter.d.ts +6 -0
  55. package/dist/adapters/qwen/QwenToolAdapter.d.ts.map +1 -0
  56. package/dist/adapters/qwen/QwenToolAdapter.js +20 -0
  57. package/dist/common/types.d.ts +106 -0
  58. package/dist/common/types.d.ts.map +1 -0
  59. package/dist/common/types.js +2 -0
  60. package/dist/core/LLMAdapter.d.ts +74 -0
  61. package/dist/core/LLMAdapter.d.ts.map +1 -0
  62. package/dist/core/LLMAdapter.js +70 -0
  63. package/dist/core/Models.d.ts +16 -0
  64. package/dist/core/Models.d.ts.map +1 -0
  65. package/dist/core/Models.js +118 -0
  66. package/dist/core/UnifiedLLMClient.d.ts +68 -0
  67. package/dist/core/UnifiedLLMClient.d.ts.map +1 -0
  68. package/dist/core/UnifiedLLMClient.js +185 -0
  69. package/dist/examples/anthropic-example.d.ts +2 -0
  70. package/dist/examples/anthropic-example.d.ts.map +1 -0
  71. package/dist/examples/anthropic-example.js +243 -0
  72. package/dist/examples/audio-example.d.ts +14 -0
  73. package/dist/examples/audio-example.d.ts.map +1 -0
  74. package/dist/examples/audio-example.js +204 -0
  75. package/dist/examples/example-logging.d.ts +2 -0
  76. package/dist/examples/example-logging.d.ts.map +1 -0
  77. package/dist/examples/example-logging.js +53 -0
  78. package/dist/examples/example.d.ts +2 -0
  79. package/dist/examples/example.d.ts.map +1 -0
  80. package/dist/examples/example.js +373 -0
  81. package/dist/examples/qwen-vl-example.d.ts +26 -0
  82. package/dist/examples/qwen-vl-example.d.ts.map +1 -0
  83. package/dist/examples/qwen-vl-example.js +314 -0
  84. package/dist/examples/test-multiturn-tools.d.ts +2 -0
  85. package/dist/examples/test-multiturn-tools.d.ts.map +1 -0
  86. package/dist/examples/test-multiturn-tools.js +139 -0
  87. package/dist/index.d.ts +7 -0
  88. package/dist/index.d.ts.map +1 -0
  89. package/dist/index.js +7 -0
  90. package/dist/utils/audioUtils.d.ts +41 -0
  91. package/dist/utils/audioUtils.d.ts.map +1 -0
  92. package/dist/utils/audioUtils.js +185 -0
  93. package/package.json +64 -0
@@ -0,0 +1,118 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.MODELS = void 0;
4
+ exports.MODELS = {
5
+ GEMINI_FLASH_2_5: {
6
+ provider: "gemini",
7
+ modelName: "gemini-2.5-flash",
8
+ costsPer1MTokens: {
9
+ prompt: 0.3,
10
+ prompt_cache: 0.075,
11
+ prompt_image: 0.0000774,
12
+ output: 2.5,
13
+ },
14
+ currency: "USD",
15
+ },
16
+ GEMINI_2_5_PRO: {
17
+ provider: "gemini",
18
+ modelName: "gemini-2.5-pro",
19
+ costsPer1MTokens: {
20
+ prompt: 1.25,
21
+ prompt_cache: 0.3125,
22
+ prompt_image: 0.0003225,
23
+ output: 10.0,
24
+ },
25
+ currency: "USD",
26
+ },
27
+ GPT_4O_MINI: {
28
+ provider: "openai",
29
+ modelName: "gpt-4o-mini",
30
+ costsPer1MTokens: {
31
+ prompt: 0.6,
32
+ prompt_cache: 0.15,
33
+ prompt_image: 0.0012,
34
+ output: 2.4,
35
+ },
36
+ currency: "USD",
37
+ },
38
+ GPT_5: {
39
+ provider: "openai",
40
+ modelName: "gpt-5.2-2025-12-11",
41
+ costsPer1MTokens: {
42
+ prompt: 1.75,
43
+ prompt_cache: 0.175,
44
+ output: 14,
45
+ },
46
+ currency: "USD",
47
+ },
48
+ QWEN_VL_3: {
49
+ provider: "qwen",
50
+ modelName: "qwen3-vl-235b-a22b-instruct",
51
+ costsPer1MTokens: {
52
+ prompt: 0.2,
53
+ prompt_cache: 0.04,
54
+ output: 1.6,
55
+ },
56
+ currency: "USD",
57
+ },
58
+ QWEN_VL_FLASH: {
59
+ provider: "qwen",
60
+ modelName: "qwen3-vl-flash",
61
+ costsPer1MTokens: {
62
+ prompt: 0.05,
63
+ prompt_cache: 0.01,
64
+ output: 0.4,
65
+ },
66
+ currency: "USD",
67
+ },
68
+ QWEN_VL_3_FLASH: {
69
+ provider: "qwen",
70
+ modelName: "qwen3-vl-flash",
71
+ costsPer1MTokens: {
72
+ prompt: 0.05,
73
+ prompt_cache: 0.01,
74
+ output: 0.4,
75
+ },
76
+ currency: "USD",
77
+ },
78
+ GEMINI_3_PRO: {
79
+ provider: "gemini",
80
+ modelName: "gemini-3-pro-preview",
81
+ costsPer1MTokens: {
82
+ prompt: 2,
83
+ prompt_cache: 0.2,
84
+ output: 12,
85
+ },
86
+ currency: "USD",
87
+ },
88
+ GEMINI_3_1_PRO: {
89
+ provider: "gemini",
90
+ modelName: "gemini-3.1-pro-preview",
91
+ costsPer1MTokens: {
92
+ prompt: 2,
93
+ prompt_cache: 0.2,
94
+ output: 12,
95
+ },
96
+ currency: "USD",
97
+ },
98
+ GEMINI_3_FLASH: {
99
+ provider: "gemini",
100
+ modelName: "gemini-3-flash-preview",
101
+ costsPer1MTokens: {
102
+ prompt: 0.5,
103
+ prompt_cache: 0.05,
104
+ prompt_audio: 1,
105
+ prompt_audio_cache: 0.1,
106
+ output: 3.0,
107
+ },
108
+ currency: "USD",
109
+ },
110
+ CLAUDE_SONNET_4_6: {
111
+ provider: "anthropic",
112
+ modelName: "claude-sonnet-4-6",
113
+ },
114
+ CLAUDE_OPUS_4_6: {
115
+ provider: "anthropic",
116
+ modelName: "claude-opus-4-6",
117
+ },
118
+ };
@@ -0,0 +1,68 @@
1
+ import { ChatMessage, ChatResponse, ToolDefinition, AudioGenerationOptions, AudioGenerationResponse, UnifiedLog } from "../common/types";
2
+ import { PromptAdapterOptions, StreamedChatChunk, ChatOptionalConfig } from "./LLMAdapter";
3
+ import { Model } from "../common/types";
4
+ export type UnifiedLLMClientOptions = {
5
+ provider: "openai" | "gemini" | "qwen" | "anthropic";
6
+ adapterOptions?: PromptAdapterOptions;
7
+ logger?: (log: UnifiedLog) => any | Promise<any>;
8
+ };
9
+ export type ChatOptions = {
10
+ message: string | ChatMessage | ChatMessage[];
11
+ tools?: ToolDefinition[];
12
+ toolChoice?: "auto" | "none" | string;
13
+ onChunk?: (chunk: StreamedChatChunk) => void;
14
+ onFinalResponse?: (finalResponse: ChatResponse) => void;
15
+ onLog?: (log: UnifiedLog) => void;
16
+ stream?: boolean;
17
+ config?: ChatOptionalConfig;
18
+ };
19
+ export declare class UnifiedLLMClient {
20
+ private promptAdapter;
21
+ private outputAdapter;
22
+ private toolAdapter;
23
+ private audioAdapter?;
24
+ private rawMessages;
25
+ private model;
26
+ private logger?;
27
+ static setDefaultLogger(logger: (log: UnifiedLog) => any | Promise<any>): void;
28
+ constructor(model: Model, options?: {
29
+ logger?: (log: UnifiedLog) => any | Promise<any>;
30
+ });
31
+ private checkNotImplementedFeatures;
32
+ chat({ message, tools, toolChoice, onChunk, onFinalResponse, onLog, stream, config }: ChatOptions): Promise<ChatResponse>;
33
+ private handleLogging;
34
+ /**
35
+ * Vérifie si la génération d'audio est supportée pour le provider actuel
36
+ */
37
+ isAudioSupported(): boolean;
38
+ /**
39
+ * Génère de l'audio à partir de texte
40
+ */
41
+ generateAudio(options: AudioGenerationOptions): Promise<AudioGenerationResponse>;
42
+ /**
43
+ * Génère de l'audio en streaming
44
+ */
45
+ generateAudioStream(options: AudioGenerationOptions): AsyncIterable<Buffer>;
46
+ /**
47
+ * Récupère la liste des voix supportées
48
+ */
49
+ getSupportedAudioVoices(): Promise<string[]>;
50
+ /**
51
+ * Génère de l'audio simple avec une voix
52
+ */
53
+ generateSingleVoiceAudio(text: string, voiceName: string, options?: {
54
+ outputPath?: string;
55
+ temperature?: number;
56
+ }): Promise<AudioGenerationResponse>;
57
+ /**
58
+ * Génère de l'audio multi-voix
59
+ */
60
+ generateMultiVoiceAudio(text: string, speakers: Array<{
61
+ speaker: string;
62
+ voiceName: string;
63
+ }>, options?: {
64
+ outputPath?: string;
65
+ temperature?: number;
66
+ }): Promise<AudioGenerationResponse>;
67
+ }
68
+ //# sourceMappingURL=UnifiedLLMClient.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"UnifiedLLMClient.d.ts","sourceRoot":"","sources":["../../src/core/UnifiedLLMClient.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,185 @@
1
+ "use strict";
2
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
+ return new (P || (P = Promise))(function (resolve, reject) {
5
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
6
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
7
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
8
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
9
+ });
10
+ };
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ exports.UnifiedLLMClient = void 0;
13
+ const LLMAdapter_1 = require("./LLMAdapter");
14
+ class UnifiedLLMClient {
15
+ static setDefaultLogger(logger) {
16
+ global._unifiedLlmDefaultLogger = logger;
17
+ }
18
+ constructor(model, options) {
19
+ this.rawMessages = [];
20
+ this.model = model;
21
+ this.promptAdapter = LLMAdapter_1.PROVIDERS_CONFIG[model.provider].promptAdapter;
22
+ this.outputAdapter = LLMAdapter_1.PROVIDERS_CONFIG[model.provider].outputAdapter;
23
+ this.toolAdapter = LLMAdapter_1.PROVIDERS_CONFIG[model.provider].toolAdapter;
24
+ this.audioAdapter = LLMAdapter_1.PROVIDERS_CONFIG[model.provider].audioAdapter;
25
+ this.logger = (options === null || options === void 0 ? void 0 : options.logger) || global._unifiedLlmDefaultLogger;
26
+ }
27
+ checkNotImplementedFeatures(message) {
28
+ if (message.attachedFile && this.model.provider !== "gemini" && this.model.provider !== "qwen" && this.model.provider !== "anthropic" && this.model.provider !== "openai") {
29
+ throw new Error("Attached files are not supported for this provider");
30
+ }
31
+ }
32
+ chat(_a) {
33
+ return __awaiter(this, arguments, void 0, function* ({ message, tools, toolChoice = "auto", onChunk, onFinalResponse, onLog, stream = false, config }) {
34
+ const startTime = Date.now();
35
+ const messageArray = Array.isArray(message)
36
+ ? message
37
+ : [typeof message === "string" ? { role: "user", content: message } : message];
38
+ for (const m of messageArray)
39
+ this.checkNotImplementedFeatures(m);
40
+ const messages = yield Promise.all(messageArray.map(m => this.promptAdapter.formatMessage(m)));
41
+ let finalResponse;
42
+ if (stream) {
43
+ if (!this.promptAdapter.streamFromProvider) {
44
+ throw new Error("The current adapter does not support streaming.");
45
+ }
46
+ let aggregatedContent = "";
47
+ finalResponse = yield this.promptAdapter.streamFromProvider({
48
+ messages,
49
+ tools,
50
+ toolChoice,
51
+ model: this.model.modelName,
52
+ onChunk: (chunk) => {
53
+ aggregatedContent += chunk.contentChunk || "";
54
+ if (onChunk) {
55
+ onChunk(chunk);
56
+ }
57
+ },
58
+ onFinalResponse: (resp) => {
59
+ resp.content = aggregatedContent;
60
+ if (onFinalResponse) {
61
+ onFinalResponse(resp);
62
+ }
63
+ }
64
+ });
65
+ finalResponse.content = aggregatedContent;
66
+ }
67
+ else {
68
+ const providerResponse = yield this.promptAdapter.sendToProvider(messages, tools, toolChoice, undefined, this.model.modelName, config);
69
+ finalResponse = this.outputAdapter.parse(providerResponse);
70
+ }
71
+ const latencyMs = Date.now() - startTime;
72
+ yield this.handleLogging(messageArray, finalResponse, latencyMs, config === null || config === void 0 ? void 0 : config.metadata, onLog);
73
+ return finalResponse;
74
+ });
75
+ }
76
+ handleLogging(messages, response, latencyMs, metadata, onLog) {
77
+ return __awaiter(this, void 0, void 0, function* () {
78
+ const logAdapter = LLMAdapter_1.PROVIDERS_CONFIG[this.model.provider].logAdapter;
79
+ if (logAdapter) {
80
+ try {
81
+ const unifiedLog = logAdapter.toUnifiedLog({
82
+ model: this.model.modelName,
83
+ provider: this.model.provider,
84
+ messages,
85
+ response,
86
+ latencyMs,
87
+ metadata
88
+ });
89
+ response.requestId = unifiedLog.requestId;
90
+ if (onLog) {
91
+ onLog(unifiedLog);
92
+ }
93
+ if (this.logger) {
94
+ try {
95
+ const logResult = yield this.logger(unifiedLog);
96
+ if (logResult && typeof logResult === 'object' && 'id' in logResult) {
97
+ response.llmLogId = logResult.id;
98
+ }
99
+ }
100
+ catch (err) {
101
+ console.error("[Logger Error]:", err);
102
+ }
103
+ }
104
+ }
105
+ catch (err) {
106
+ console.error("[LogAdapter Error]:", err);
107
+ }
108
+ }
109
+ });
110
+ }
111
+ // ===== AUDIO GENERATION METHODS =====
112
+ /**
113
+ * Vérifie si la génération d'audio est supportée pour le provider actuel
114
+ */
115
+ isAudioSupported() {
116
+ return this.audioAdapter !== undefined;
117
+ }
118
+ /**
119
+ * Génère de l'audio à partir de texte
120
+ */
121
+ generateAudio(options) {
122
+ return __awaiter(this, void 0, void 0, function* () {
123
+ if (!this.audioAdapter) {
124
+ throw new Error(`La génération d'audio n'est pas supportée pour le provider ${this.model.provider}`);
125
+ }
126
+ return this.audioAdapter.generateAudio(options);
127
+ });
128
+ }
129
+ /**
130
+ * Génère de l'audio en streaming
131
+ */
132
+ generateAudioStream(options) {
133
+ if (!this.audioAdapter) {
134
+ throw new Error(`Le streaming audio n'est pas supporté pour le provider ${this.model.provider}`);
135
+ }
136
+ return this.audioAdapter.generateAudioStream(options);
137
+ }
138
+ /**
139
+ * Récupère la liste des voix supportées
140
+ */
141
+ getSupportedAudioVoices() {
142
+ return __awaiter(this, void 0, void 0, function* () {
143
+ if (!this.audioAdapter) {
144
+ throw new Error(`La génération d'audio n'est pas supportée pour le provider ${this.model.provider}`);
145
+ }
146
+ return this.audioAdapter.getSupportedVoices();
147
+ });
148
+ }
149
+ /**
150
+ * Génère de l'audio simple avec une voix
151
+ */
152
+ generateSingleVoiceAudio(text, voiceName, options) {
153
+ return __awaiter(this, void 0, void 0, function* () {
154
+ return this.generateAudio({
155
+ text,
156
+ outputPath: options === null || options === void 0 ? void 0 : options.outputPath,
157
+ voiceConfig: {
158
+ voiceName,
159
+ temperature: options === null || options === void 0 ? void 0 : options.temperature
160
+ },
161
+ multiSpeaker: false
162
+ });
163
+ });
164
+ }
165
+ /**
166
+ * Génère de l'audio multi-voix
167
+ */
168
+ generateMultiVoiceAudio(text, speakers, options) {
169
+ return __awaiter(this, void 0, void 0, function* () {
170
+ return this.generateAudio({
171
+ text,
172
+ outputPath: options === null || options === void 0 ? void 0 : options.outputPath,
173
+ multiSpeaker: true,
174
+ speakers: speakers.map(s => ({
175
+ speaker: s.speaker,
176
+ voiceConfig: {
177
+ voiceName: s.voiceName,
178
+ temperature: options === null || options === void 0 ? void 0 : options.temperature
179
+ }
180
+ }))
181
+ });
182
+ });
183
+ }
184
+ }
185
+ exports.UnifiedLLMClient = UnifiedLLMClient;
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=anthropic-example.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"anthropic-example.d.ts","sourceRoot":"","sources":["../../src/examples/anthropic-example.ts"],"names":[],"mappings":""}
@@ -0,0 +1,243 @@
1
+ "use strict";
2
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
+ return new (P || (P = Promise))(function (resolve, reject) {
5
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
6
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
7
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
8
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
9
+ });
10
+ };
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ const __1 = require("..");
13
+ // ───────────────────────────────────────────────
14
+ // 1. Chat simple
15
+ // ───────────────────────────────────────────────
16
+ function basicChat() {
17
+ return __awaiter(this, void 0, void 0, function* () {
18
+ console.log("=== 1. Chat simple ===");
19
+ const client = new __1.UnifiedLLMClient(__1.MODELS.CLAUDE_SONNET_4_6);
20
+ const response = yield client.chat({
21
+ message: "Présente-toi en une phrase.",
22
+ });
23
+ console.log("Réponse :", response.content);
24
+ console.log("Usage :", response.usage);
25
+ console.log();
26
+ });
27
+ }
28
+ // ───────────────────────────────────────────────
29
+ // 2. Streaming
30
+ // ───────────────────────────────────────────────
31
+ function streamingChat() {
32
+ return __awaiter(this, void 0, void 0, function* () {
33
+ console.log("=== 2. Streaming ===");
34
+ const client = new __1.UnifiedLLMClient(__1.MODELS.CLAUDE_SONNET_4_6);
35
+ process.stdout.write("Réponse : ");
36
+ const response = yield client.chat({
37
+ message: "Explique-moi le principe de la relativité restreinte en 3 phrases.",
38
+ stream: true,
39
+ onChunk: (chunk) => {
40
+ if (chunk.contentChunk) {
41
+ process.stdout.write(chunk.contentChunk);
42
+ }
43
+ },
44
+ });
45
+ console.log("\nUsage final :", response.usage);
46
+ console.log();
47
+ });
48
+ }
49
+ // ───────────────────────────────────────────────
50
+ // 3. Tool calling
51
+ // ───────────────────────────────────────────────
52
+ function toolCallingChat() {
53
+ return __awaiter(this, void 0, void 0, function* () {
54
+ console.log("=== 3. Tool calling ===");
55
+ const tools = [
56
+ {
57
+ name: "get_weather",
58
+ description: "Retourne la météo actuelle pour une ville donnée.",
59
+ parameters: {
60
+ type: "object",
61
+ properties: {
62
+ city: { type: "string", description: "Nom de la ville" },
63
+ },
64
+ required: ["city"],
65
+ },
66
+ executor: (_a) => __awaiter(this, [_a], void 0, function* ({ city }) {
67
+ const temperature = Math.floor(10 + Math.random() * 20);
68
+ return `Météo à ${city} : ${temperature}°C, ensoleillé.`;
69
+ }),
70
+ },
71
+ ];
72
+ const client = new __1.UnifiedLLMClient(__1.MODELS.CLAUDE_SONNET_4_6);
73
+ const response = yield client.chat({
74
+ message: "Quel temps fait-il à Paris en ce moment ?",
75
+ tools,
76
+ toolChoice: "auto",
77
+ });
78
+ if (response.toolCalls && response.toolCalls.length > 0) {
79
+ console.log("Tool call détecté :", response.toolCalls[0].name);
80
+ console.log("Arguments :", response.toolCalls[0].arguments);
81
+ }
82
+ else {
83
+ console.log("Réponse directe :", response.content);
84
+ }
85
+ console.log();
86
+ });
87
+ }
88
+ // ───────────────────────────────────────────────
89
+ // 4. Logging
90
+ // ───────────────────────────────────────────────
91
+ function chatWithLogging() {
92
+ return __awaiter(this, void 0, void 0, function* () {
93
+ console.log("=== 4. Chat avec logging ===");
94
+ const client = new __1.UnifiedLLMClient(__1.MODELS.CLAUDE_SONNET_4_6, {
95
+ logger: (log) => {
96
+ console.log("[LOG]", {
97
+ requestId: log.requestId,
98
+ model: log.model,
99
+ promptTokens: log.usage.promptTokens,
100
+ completionTokens: log.usage.completionTokens,
101
+ totalTokens: log.usage.totalTokens,
102
+ latencyMs: log.latencyMs,
103
+ finishReason: log.output.finishReason,
104
+ });
105
+ },
106
+ });
107
+ const response = yield client.chat({
108
+ message: "Quelle est la capitale de la France ?",
109
+ });
110
+ console.log("Réponse :", response.content);
111
+ console.log();
112
+ });
113
+ }
114
+ // ───────────────────────────────────────────────
115
+ // 5. OCR — extraction de texte depuis une image
116
+ // ───────────────────────────────────────────────
117
+ function ocrFromImage() {
118
+ return __awaiter(this, void 0, void 0, function* () {
119
+ console.log("=== 5. OCR depuis une image ===");
120
+ const tools = [
121
+ {
122
+ name: "save_ocr_result",
123
+ description: "Sauvegarde le texte extrait d'une image.",
124
+ parameters: {
125
+ type: "object",
126
+ properties: {
127
+ text: {
128
+ type: "string",
129
+ description: "Texte intégral extrait de l'image, dans l'ordre de lecture.",
130
+ },
131
+ language: {
132
+ type: "string",
133
+ description: "Langue détectée dans le document (ex: 'fr', 'en').",
134
+ },
135
+ confidence: {
136
+ type: "string",
137
+ enum: ["high", "medium", "low"],
138
+ description: "Niveau de confiance global sur la transcription.",
139
+ },
140
+ },
141
+ required: ["text", "language", "confidence"],
142
+ },
143
+ executor: (_a) => __awaiter(this, [_a], void 0, function* ({ text, language, confidence }) {
144
+ return `OCR enregistré (${language}, confiance: ${confidence}) — ${String(text).length} caractères extraits.`;
145
+ }),
146
+ },
147
+ ];
148
+ const client = new __1.UnifiedLLMClient(__1.MODELS.CLAUDE_SONNET_4_6);
149
+ // Remplace "./media/document.png" par le chemin de ton image ou PDF
150
+ const response = yield client.chat({
151
+ message: {
152
+ role: "user",
153
+ content: "Extrais tout le texte visible dans ce document, mot pour mot, en respectant l'ordre de lecture.",
154
+ attachedFile: "./media/document.png",
155
+ },
156
+ tools,
157
+ toolChoice: "save_ocr_result",
158
+ });
159
+ if (response.toolCalls && response.toolCalls.length > 0) {
160
+ const args = response.toolCalls[0].arguments;
161
+ console.log("Langue détectée :", args.language);
162
+ console.log("Confiance :", args.confidence);
163
+ console.log("Texte extrait :\n", args.text);
164
+ }
165
+ else {
166
+ console.log("Réponse texte :", response.content);
167
+ }
168
+ console.log();
169
+ });
170
+ }
171
+ // ───────────────────────────────────────────────
172
+ // 6. OCR — extraction structurée depuis un PDF
173
+ // ───────────────────────────────────────────────
174
+ function ocrFromPdf() {
175
+ return __awaiter(this, void 0, void 0, function* () {
176
+ console.log("=== 6. OCR structuré depuis un PDF ===");
177
+ const tools = [
178
+ {
179
+ name: "save_structured_document",
180
+ description: "Sauvegarde le contenu structuré extrait d'un document PDF.",
181
+ parameters: {
182
+ type: "object",
183
+ properties: {
184
+ title: { type: "string", description: "Titre principal du document." },
185
+ sections: {
186
+ type: "array",
187
+ description: "Sections du document dans l'ordre.",
188
+ items: {
189
+ type: "object",
190
+ properties: {
191
+ heading: { type: "string", description: "Titre de la section." },
192
+ content: { type: "string", description: "Contenu textuel de la section." },
193
+ },
194
+ required: ["heading", "content"],
195
+ },
196
+ },
197
+ page_count: { type: "number", description: "Nombre de pages du document." },
198
+ },
199
+ required: ["title", "sections", "page_count"],
200
+ },
201
+ executor: (_a) => __awaiter(this, [_a], void 0, function* ({ title, sections, page_count }) {
202
+ return `Document "${title}" analysé — ${page_count} page(s), ${sections.length} section(s).`;
203
+ }),
204
+ },
205
+ ];
206
+ const client = new __1.UnifiedLLMClient(__1.MODELS.CLAUDE_SONNET_4_6);
207
+ // Remplace "./media/document.pdf" par le chemin de ton PDF
208
+ const response = yield client.chat({
209
+ message: {
210
+ role: "user",
211
+ content: "Analyse ce document PDF et extrais le contenu de la première page de manière structurée : titre, sections et leur contenu.",
212
+ attachedFile: "./media/document.pdf",
213
+ },
214
+ tools,
215
+ toolChoice: "save_structured_document",
216
+ });
217
+ if (response.toolCalls && response.toolCalls.length > 0) {
218
+ const args = response.toolCalls[0].arguments;
219
+ console.log("Titre :", args.title);
220
+ console.log("Pages :", args.page_count);
221
+ console.log("Sections :", args.sections.length);
222
+ args.sections.forEach((s, i) => {
223
+ console.log(`\n [${i + 1}] ${s.heading}`);
224
+ console.log(` ${s.content.slice(0, 120)}...`);
225
+ });
226
+ }
227
+ else {
228
+ console.log("Réponse texte :", response.content);
229
+ }
230
+ console.log();
231
+ });
232
+ }
233
+ // ───────────────────────────────────────────────
234
+ // Exécution
235
+ // ───────────────────────────────────────────────
236
+ (() => __awaiter(void 0, void 0, void 0, function* () {
237
+ yield basicChat();
238
+ yield streamingChat();
239
+ yield toolCallingChat();
240
+ yield chatWithLogging();
241
+ yield ocrFromImage();
242
+ yield ocrFromPdf();
243
+ }))();
@@ -0,0 +1,14 @@
1
+ import { UnifiedLLMClient } from "../core/UnifiedLLMClient";
2
+ declare function listAvailableVoices(client: UnifiedLLMClient): Promise<string[]>;
3
+ declare function generateSimpleAudio(client: UnifiedLLMClient): Promise<import("../index").AudioGenerationResponse>;
4
+ declare function generateMultiVoiceAudio(client: UnifiedLLMClient): Promise<import("../index").AudioGenerationResponse>;
5
+ declare function generateAdvancedAudio(client: UnifiedLLMClient): Promise<import("../index").AudioGenerationResponse>;
6
+ declare function generateStreamingAudio(client: UnifiedLLMClient): Promise<{
7
+ totalChunks: number;
8
+ totalBytes: number;
9
+ }>;
10
+ declare function generateInMemoryAudio(client: UnifiedLLMClient): Promise<import("../index").AudioGenerationResponse>;
11
+ declare function runAudioExamples(): Promise<void>;
12
+ export declare function cleanupAudioExamples(): void;
13
+ export { runAudioExamples, listAvailableVoices, generateSimpleAudio, generateMultiVoiceAudio, generateAdvancedAudio, generateStreamingAudio, generateInMemoryAudio };
14
+ //# sourceMappingURL=audio-example.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audio-example.d.ts","sourceRoot":"","sources":["../../src/examples/audio-example.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAW5D,iBAAe,mBAAmB,CAAC,MAAM,EAAE,gBAAgB,qBAG1D;AAED,iBAAe,mBAAmB,CAAC,MAAM,EAAE,gBAAgB,uDAU1D;AAED,iBAAe,uBAAuB,CAAC,MAAM,EAAE,gBAAgB,uDAgB9D;AAED,iBAAe,qBAAqB,CAAC,MAAM,EAAE,gBAAgB,uDAe5D;AAED,iBAAe,sBAAsB,CAAC,MAAM,EAAE,gBAAgB;;;GAiB7D;AAED,iBAAe,qBAAqB,CAAC,MAAM,EAAE,gBAAgB,uDAQ5D;AAED,iBAAe,gBAAgB,kBAwB9B;AAQD,wBAAgB,oBAAoB,SAkBnC;AAaD,OAAO,EACL,gBAAgB,EAChB,mBAAmB,EACnB,mBAAmB,EACnB,uBAAuB,EACvB,qBAAqB,EACrB,sBAAsB,EACtB,qBAAqB,EACtB,CAAC"}