@antseed/node 0.2.7 → 0.2.8
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 +17 -22
- package/dist/discovery/announcer.d.ts +7 -7
- package/dist/discovery/announcer.d.ts.map +1 -1
- package/dist/discovery/announcer.js +38 -38
- package/dist/discovery/announcer.js.map +1 -1
- package/dist/discovery/dht-node.d.ts +4 -4
- package/dist/discovery/dht-node.d.ts.map +1 -1
- package/dist/discovery/dht-node.js +8 -8
- package/dist/discovery/dht-node.js.map +1 -1
- package/dist/discovery/index.d.ts +2 -2
- package/dist/discovery/index.d.ts.map +1 -1
- package/dist/discovery/index.js +2 -2
- package/dist/discovery/index.js.map +1 -1
- package/dist/discovery/metadata-codec.d.ts +7 -7
- package/dist/discovery/metadata-codec.js +113 -113
- package/dist/discovery/metadata-codec.js.map +1 -1
- package/dist/discovery/metadata-validator.d.ts +5 -5
- package/dist/discovery/metadata-validator.d.ts.map +1 -1
- package/dist/discovery/metadata-validator.js +74 -74
- package/dist/discovery/metadata-validator.js.map +1 -1
- package/dist/discovery/peer-lookup.d.ts +1 -1
- package/dist/discovery/peer-lookup.d.ts.map +1 -1
- package/dist/discovery/peer-lookup.js +7 -7
- package/dist/discovery/peer-lookup.js.map +1 -1
- package/dist/discovery/peer-metadata.d.ts +9 -9
- package/dist/discovery/peer-metadata.d.ts.map +1 -1
- package/dist/discovery/peer-metadata.js +3 -3
- package/dist/discovery/peer-metadata.js.map +1 -1
- package/dist/index.d.ts +2 -2
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +2 -2
- package/dist/index.js.map +1 -1
- package/dist/interfaces/seller-provider.d.ts +9 -9
- package/dist/interfaces/seller-provider.d.ts.map +1 -1
- package/dist/node.d.ts +2 -2
- package/dist/node.d.ts.map +1 -1
- package/dist/node.js +41 -41
- package/dist/node.js.map +1 -1
- package/dist/payments/seller-payment-manager.d.ts +12 -42
- package/dist/payments/seller-payment-manager.d.ts.map +1 -1
- package/dist/payments/seller-payment-manager.js +96 -140
- package/dist/payments/seller-payment-manager.js.map +1 -1
- package/dist/proxy/index.d.ts +1 -1
- package/dist/proxy/index.d.ts.map +1 -1
- package/dist/proxy/index.js +1 -1
- package/dist/proxy/index.js.map +1 -1
- package/dist/proxy/service-api-adapter.d.ts +30 -0
- package/dist/proxy/service-api-adapter.d.ts.map +1 -0
- package/dist/proxy/service-api-adapter.js +891 -0
- package/dist/proxy/service-api-adapter.js.map +1 -0
- package/dist/types/capability.d.ts +2 -2
- package/dist/types/capability.d.ts.map +1 -1
- package/dist/types/index.d.ts +1 -1
- package/dist/types/index.d.ts.map +1 -1
- package/dist/types/index.js +1 -1
- package/dist/types/index.js.map +1 -1
- package/dist/types/peer.d.ts +11 -11
- package/dist/types/peer.d.ts.map +1 -1
- package/dist/types/protocol.d.ts +0 -6
- package/dist/types/protocol.d.ts.map +1 -1
- package/dist/types/protocol.js +0 -8
- package/dist/types/protocol.js.map +1 -1
- package/dist/types/provider.d.ts +1 -1
- package/dist/types/provider.d.ts.map +1 -1
- package/dist/types/service-api.d.ts +4 -0
- package/dist/types/service-api.d.ts.map +1 -0
- package/dist/types/service-api.js +11 -0
- package/dist/types/service-api.js.map +1 -0
- package/package.json +1 -1
|
@@ -0,0 +1,891 @@
|
|
|
1
|
+
const ANTHROPIC_PROVIDER_NAMES = new Set(['anthropic', 'claude-code', 'claude-oauth']);
|
|
2
|
+
const OPENAI_CHAT_PROVIDER_NAMES = new Set(['openai', 'local-llm']);
|
|
3
|
+
function parseJsonObject(body) {
|
|
4
|
+
try {
|
|
5
|
+
const parsed = JSON.parse(new TextDecoder().decode(body));
|
|
6
|
+
if (!parsed || typeof parsed !== 'object' || Array.isArray(parsed)) {
|
|
7
|
+
return null;
|
|
8
|
+
}
|
|
9
|
+
return parsed;
|
|
10
|
+
}
|
|
11
|
+
catch {
|
|
12
|
+
return null;
|
|
13
|
+
}
|
|
14
|
+
}
|
|
15
|
+
function encodeJson(value) {
|
|
16
|
+
return new TextEncoder().encode(JSON.stringify(value));
|
|
17
|
+
}
|
|
18
|
+
function toStringContent(value) {
|
|
19
|
+
if (typeof value === 'string') {
|
|
20
|
+
return value;
|
|
21
|
+
}
|
|
22
|
+
if (Array.isArray(value)) {
|
|
23
|
+
return value
|
|
24
|
+
.map((entry) => {
|
|
25
|
+
if (!entry || typeof entry !== 'object') {
|
|
26
|
+
return '';
|
|
27
|
+
}
|
|
28
|
+
const block = entry;
|
|
29
|
+
if ((block.type === 'text' || block.type === 'input_text') && typeof block.text === 'string') {
|
|
30
|
+
return block.text;
|
|
31
|
+
}
|
|
32
|
+
if (block.type === 'output_text' && typeof block.text === 'string') {
|
|
33
|
+
return block.text;
|
|
34
|
+
}
|
|
35
|
+
if (block.type === 'refusal' && typeof block.refusal === 'string') {
|
|
36
|
+
return block.refusal;
|
|
37
|
+
}
|
|
38
|
+
if (block.type === 'tool_result') {
|
|
39
|
+
return toStringContent(block.content);
|
|
40
|
+
}
|
|
41
|
+
return '';
|
|
42
|
+
})
|
|
43
|
+
.filter((entry) => entry.length > 0)
|
|
44
|
+
.join('\n');
|
|
45
|
+
}
|
|
46
|
+
if (value === null || value === undefined) {
|
|
47
|
+
return '';
|
|
48
|
+
}
|
|
49
|
+
// Handle a single content block object (e.g. {type:'text', text:'...'})
|
|
50
|
+
if (typeof value === 'object') {
|
|
51
|
+
const block = value;
|
|
52
|
+
if ((block.type === 'text' || block.type === 'input_text') && typeof block.text === 'string') {
|
|
53
|
+
return block.text;
|
|
54
|
+
}
|
|
55
|
+
if (block.type === 'output_text' && typeof block.text === 'string') {
|
|
56
|
+
return block.text;
|
|
57
|
+
}
|
|
58
|
+
if (block.type === 'refusal' && typeof block.refusal === 'string') {
|
|
59
|
+
return block.refusal;
|
|
60
|
+
}
|
|
61
|
+
if (block.type === 'tool_result') {
|
|
62
|
+
return toStringContent(block.content);
|
|
63
|
+
}
|
|
64
|
+
return '';
|
|
65
|
+
}
|
|
66
|
+
return String(value);
|
|
67
|
+
}
|
|
68
|
+
function parseJsonSafe(raw) {
|
|
69
|
+
try {
|
|
70
|
+
return JSON.parse(raw);
|
|
71
|
+
}
|
|
72
|
+
catch {
|
|
73
|
+
return raw;
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
function mapFinishReasonToAnthropicStopReason(value) {
|
|
77
|
+
if (typeof value !== 'string' || value.length === 0) {
|
|
78
|
+
return null;
|
|
79
|
+
}
|
|
80
|
+
if (value === 'stop')
|
|
81
|
+
return 'end_turn';
|
|
82
|
+
if (value === 'length')
|
|
83
|
+
return 'max_tokens';
|
|
84
|
+
if (value === 'tool_calls' || value === 'function_call')
|
|
85
|
+
return 'tool_use';
|
|
86
|
+
return value;
|
|
87
|
+
}
|
|
88
|
+
function toNonNegativeInt(value) {
|
|
89
|
+
const parsed = Number(value);
|
|
90
|
+
if (!Number.isFinite(parsed) || parsed <= 0) {
|
|
91
|
+
return 0;
|
|
92
|
+
}
|
|
93
|
+
return Math.floor(parsed);
|
|
94
|
+
}
|
|
95
|
+
function convertAnthropicMessagesToOpenAI(body) {
|
|
96
|
+
const out = [];
|
|
97
|
+
if (body.system !== undefined) {
|
|
98
|
+
const systemText = toStringContent(body.system);
|
|
99
|
+
if (systemText.length > 0) {
|
|
100
|
+
out.push({ role: 'system', content: systemText });
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
const messagesRaw = body.messages;
|
|
104
|
+
if (!Array.isArray(messagesRaw)) {
|
|
105
|
+
return out;
|
|
106
|
+
}
|
|
107
|
+
for (const messageRaw of messagesRaw) {
|
|
108
|
+
if (!messageRaw || typeof messageRaw !== 'object') {
|
|
109
|
+
continue;
|
|
110
|
+
}
|
|
111
|
+
const message = messageRaw;
|
|
112
|
+
const role = typeof message.role === 'string' ? message.role : 'user';
|
|
113
|
+
const content = message.content;
|
|
114
|
+
if (role === 'assistant' && Array.isArray(content)) {
|
|
115
|
+
const textParts = [];
|
|
116
|
+
const toolCalls = [];
|
|
117
|
+
for (const blockRaw of content) {
|
|
118
|
+
if (!blockRaw || typeof blockRaw !== 'object') {
|
|
119
|
+
continue;
|
|
120
|
+
}
|
|
121
|
+
const block = blockRaw;
|
|
122
|
+
const blockType = typeof block.type === 'string' ? block.type : '';
|
|
123
|
+
if (blockType === 'tool_use') {
|
|
124
|
+
const callName = typeof block.name === 'string' && block.name.length > 0 ? block.name : 'tool';
|
|
125
|
+
const callId = typeof block.id === 'string' && block.id.length > 0
|
|
126
|
+
? block.id
|
|
127
|
+
: `call_${toolCalls.length + 1}`;
|
|
128
|
+
const input = block.input && typeof block.input === 'object' ? block.input : {};
|
|
129
|
+
toolCalls.push({
|
|
130
|
+
id: callId,
|
|
131
|
+
type: 'function',
|
|
132
|
+
function: {
|
|
133
|
+
name: callName,
|
|
134
|
+
arguments: JSON.stringify(input),
|
|
135
|
+
},
|
|
136
|
+
});
|
|
137
|
+
continue;
|
|
138
|
+
}
|
|
139
|
+
const text = toStringContent(block);
|
|
140
|
+
if (text.length > 0) {
|
|
141
|
+
textParts.push(text);
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
const assistantMessage = {
|
|
145
|
+
role: 'assistant',
|
|
146
|
+
content: textParts.join('\n'),
|
|
147
|
+
};
|
|
148
|
+
if (toolCalls.length > 0) {
|
|
149
|
+
assistantMessage.tool_calls = toolCalls;
|
|
150
|
+
}
|
|
151
|
+
out.push(assistantMessage);
|
|
152
|
+
continue;
|
|
153
|
+
}
|
|
154
|
+
if (role === 'user' && Array.isArray(content)) {
|
|
155
|
+
const textParts = [];
|
|
156
|
+
const toolResults = [];
|
|
157
|
+
for (const blockRaw of content) {
|
|
158
|
+
if (!blockRaw || typeof blockRaw !== 'object') {
|
|
159
|
+
continue;
|
|
160
|
+
}
|
|
161
|
+
const block = blockRaw;
|
|
162
|
+
const blockType = typeof block.type === 'string' ? block.type : '';
|
|
163
|
+
if (blockType === 'tool_result') {
|
|
164
|
+
const toolCallId = typeof block.tool_use_id === 'string' ? block.tool_use_id : '';
|
|
165
|
+
if (toolCallId.length > 0) {
|
|
166
|
+
toolResults.push({
|
|
167
|
+
role: 'tool',
|
|
168
|
+
tool_call_id: toolCallId,
|
|
169
|
+
content: toStringContent(block.content),
|
|
170
|
+
});
|
|
171
|
+
continue;
|
|
172
|
+
}
|
|
173
|
+
}
|
|
174
|
+
const text = toStringContent(block);
|
|
175
|
+
if (text.length > 0) {
|
|
176
|
+
textParts.push(text);
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
if (textParts.length > 0) {
|
|
180
|
+
out.push({
|
|
181
|
+
role: 'user',
|
|
182
|
+
content: textParts.join('\n'),
|
|
183
|
+
});
|
|
184
|
+
}
|
|
185
|
+
out.push(...toolResults);
|
|
186
|
+
continue;
|
|
187
|
+
}
|
|
188
|
+
out.push({
|
|
189
|
+
role,
|
|
190
|
+
content: toStringContent(content),
|
|
191
|
+
});
|
|
192
|
+
}
|
|
193
|
+
return out;
|
|
194
|
+
}
|
|
195
|
+
function convertAnthropicToolsToOpenAI(toolsRaw) {
|
|
196
|
+
if (!Array.isArray(toolsRaw) || toolsRaw.length === 0) {
|
|
197
|
+
return undefined;
|
|
198
|
+
}
|
|
199
|
+
const out = [];
|
|
200
|
+
for (const toolRaw of toolsRaw) {
|
|
201
|
+
if (!toolRaw || typeof toolRaw !== 'object') {
|
|
202
|
+
continue;
|
|
203
|
+
}
|
|
204
|
+
const tool = toolRaw;
|
|
205
|
+
if (typeof tool.name !== 'string' || tool.name.length === 0) {
|
|
206
|
+
continue;
|
|
207
|
+
}
|
|
208
|
+
out.push({
|
|
209
|
+
type: 'function',
|
|
210
|
+
function: {
|
|
211
|
+
name: tool.name,
|
|
212
|
+
...(typeof tool.description === 'string' && tool.description.length > 0
|
|
213
|
+
? { description: tool.description }
|
|
214
|
+
: {}),
|
|
215
|
+
parameters: tool.input_schema && typeof tool.input_schema === 'object'
|
|
216
|
+
? tool.input_schema
|
|
217
|
+
: { type: 'object', properties: {} },
|
|
218
|
+
},
|
|
219
|
+
});
|
|
220
|
+
}
|
|
221
|
+
return out.length > 0 ? out : undefined;
|
|
222
|
+
}
|
|
223
|
+
function convertAnthropicToolChoiceToOpenAI(toolChoice) {
|
|
224
|
+
if (typeof toolChoice === 'string') {
|
|
225
|
+
if (toolChoice === 'auto' || toolChoice === 'none' || toolChoice === 'required') {
|
|
226
|
+
return toolChoice;
|
|
227
|
+
}
|
|
228
|
+
return undefined;
|
|
229
|
+
}
|
|
230
|
+
if (!toolChoice || typeof toolChoice !== 'object') {
|
|
231
|
+
return undefined;
|
|
232
|
+
}
|
|
233
|
+
const choice = toolChoice;
|
|
234
|
+
const type = typeof choice.type === 'string' ? choice.type : '';
|
|
235
|
+
if (type === 'auto') {
|
|
236
|
+
return 'auto';
|
|
237
|
+
}
|
|
238
|
+
if (type === 'any') {
|
|
239
|
+
return 'required';
|
|
240
|
+
}
|
|
241
|
+
if (type === 'tool' && typeof choice.name === 'string' && choice.name.length > 0) {
|
|
242
|
+
return {
|
|
243
|
+
type: 'function',
|
|
244
|
+
function: {
|
|
245
|
+
name: choice.name,
|
|
246
|
+
},
|
|
247
|
+
};
|
|
248
|
+
}
|
|
249
|
+
return undefined;
|
|
250
|
+
}
|
|
251
|
+
function buildAnthropicStreamFromMessage(message) {
|
|
252
|
+
const chunks = [];
|
|
253
|
+
const pushEvent = (event, data) => {
|
|
254
|
+
chunks.push(`event: ${event}\n`);
|
|
255
|
+
chunks.push(`data: ${JSON.stringify(data)}\n\n`);
|
|
256
|
+
};
|
|
257
|
+
pushEvent('message_start', {
|
|
258
|
+
type: 'message_start',
|
|
259
|
+
message: {
|
|
260
|
+
id: message.id,
|
|
261
|
+
type: 'message',
|
|
262
|
+
role: 'assistant',
|
|
263
|
+
model: message.service,
|
|
264
|
+
content: [],
|
|
265
|
+
stop_reason: null,
|
|
266
|
+
stop_sequence: null,
|
|
267
|
+
usage: {
|
|
268
|
+
input_tokens: message.usage.inputTokens,
|
|
269
|
+
output_tokens: 0,
|
|
270
|
+
},
|
|
271
|
+
},
|
|
272
|
+
});
|
|
273
|
+
message.content.forEach((block, index) => {
|
|
274
|
+
pushEvent('content_block_start', {
|
|
275
|
+
type: 'content_block_start',
|
|
276
|
+
index,
|
|
277
|
+
content_block: block.type === 'text'
|
|
278
|
+
? { type: 'text', text: '' }
|
|
279
|
+
: { type: 'tool_use', id: block.id, name: block.name, input: {} },
|
|
280
|
+
});
|
|
281
|
+
if (block.type === 'text' && block.text.length > 0) {
|
|
282
|
+
pushEvent('content_block_delta', {
|
|
283
|
+
type: 'content_block_delta',
|
|
284
|
+
index,
|
|
285
|
+
delta: {
|
|
286
|
+
type: 'text_delta',
|
|
287
|
+
text: block.text,
|
|
288
|
+
},
|
|
289
|
+
});
|
|
290
|
+
}
|
|
291
|
+
if (block.type === 'tool_use') {
|
|
292
|
+
pushEvent('content_block_delta', {
|
|
293
|
+
type: 'content_block_delta',
|
|
294
|
+
index,
|
|
295
|
+
delta: {
|
|
296
|
+
type: 'input_json_delta',
|
|
297
|
+
partial_json: JSON.stringify(block.input),
|
|
298
|
+
},
|
|
299
|
+
});
|
|
300
|
+
}
|
|
301
|
+
pushEvent('content_block_stop', {
|
|
302
|
+
type: 'content_block_stop',
|
|
303
|
+
index,
|
|
304
|
+
});
|
|
305
|
+
});
|
|
306
|
+
pushEvent('message_delta', {
|
|
307
|
+
type: 'message_delta',
|
|
308
|
+
delta: {
|
|
309
|
+
stop_reason: message.stopReason,
|
|
310
|
+
stop_sequence: null,
|
|
311
|
+
},
|
|
312
|
+
usage: {
|
|
313
|
+
output_tokens: message.usage.outputTokens,
|
|
314
|
+
},
|
|
315
|
+
});
|
|
316
|
+
pushEvent('message_stop', {
|
|
317
|
+
type: 'message_stop',
|
|
318
|
+
});
|
|
319
|
+
return new TextEncoder().encode(chunks.join(''));
|
|
320
|
+
}
|
|
321
|
+
export function detectRequestServiceApiProtocol(request) {
|
|
322
|
+
const normalizedPath = request.path.toLowerCase();
|
|
323
|
+
if (normalizedPath.startsWith('/v1/messages') || normalizedPath.startsWith('/v1/complete')) {
|
|
324
|
+
return 'anthropic-messages';
|
|
325
|
+
}
|
|
326
|
+
if (normalizedPath.startsWith('/v1/chat/completions')) {
|
|
327
|
+
return 'openai-chat-completions';
|
|
328
|
+
}
|
|
329
|
+
if (normalizedPath.startsWith('/v1/completions')) {
|
|
330
|
+
return 'openai-completions';
|
|
331
|
+
}
|
|
332
|
+
if (normalizedPath.startsWith('/v1/responses')) {
|
|
333
|
+
return 'openai-responses';
|
|
334
|
+
}
|
|
335
|
+
const hasAnthropicVersionHeader = Object.keys(request.headers)
|
|
336
|
+
.some((key) => key.toLowerCase() === 'anthropic-version');
|
|
337
|
+
if (hasAnthropicVersionHeader) {
|
|
338
|
+
return 'anthropic-messages';
|
|
339
|
+
}
|
|
340
|
+
return null;
|
|
341
|
+
}
|
|
342
|
+
export function inferProviderDefaultServiceApiProtocols(providerName) {
|
|
343
|
+
const normalized = providerName.trim().toLowerCase();
|
|
344
|
+
if (normalized.length === 0) {
|
|
345
|
+
return [];
|
|
346
|
+
}
|
|
347
|
+
if (ANTHROPIC_PROVIDER_NAMES.has(normalized)) {
|
|
348
|
+
return ['anthropic-messages'];
|
|
349
|
+
}
|
|
350
|
+
if (OPENAI_CHAT_PROVIDER_NAMES.has(normalized)) {
|
|
351
|
+
return ['openai-chat-completions'];
|
|
352
|
+
}
|
|
353
|
+
return [];
|
|
354
|
+
}
|
|
355
|
+
export function selectTargetProtocolForRequest(requestProtocol, supportedProtocols) {
|
|
356
|
+
if (!requestProtocol) {
|
|
357
|
+
return null;
|
|
358
|
+
}
|
|
359
|
+
if (supportedProtocols.includes(requestProtocol)) {
|
|
360
|
+
return { targetProtocol: requestProtocol, requiresTransform: false };
|
|
361
|
+
}
|
|
362
|
+
if (requestProtocol === 'anthropic-messages' && supportedProtocols.includes('openai-chat-completions')) {
|
|
363
|
+
return { targetProtocol: 'openai-chat-completions', requiresTransform: true };
|
|
364
|
+
}
|
|
365
|
+
if (requestProtocol === 'openai-responses' && supportedProtocols.includes('openai-chat-completions')) {
|
|
366
|
+
return { targetProtocol: 'openai-chat-completions', requiresTransform: true };
|
|
367
|
+
}
|
|
368
|
+
return null;
|
|
369
|
+
}
|
|
370
|
+
export function transformAnthropicMessagesRequestToOpenAIChat(request) {
|
|
371
|
+
if (!request.path.toLowerCase().startsWith('/v1/messages')) {
|
|
372
|
+
return null;
|
|
373
|
+
}
|
|
374
|
+
const body = parseJsonObject(request.body);
|
|
375
|
+
if (!body) {
|
|
376
|
+
return null;
|
|
377
|
+
}
|
|
378
|
+
const streamRequested = body.stream === true;
|
|
379
|
+
const requestedModel = typeof body.model === 'string' && body.model.trim().length > 0
|
|
380
|
+
? body.model.trim()
|
|
381
|
+
: null;
|
|
382
|
+
const mappedMessages = convertAnthropicMessagesToOpenAI(body);
|
|
383
|
+
const mappedTools = convertAnthropicToolsToOpenAI(body.tools);
|
|
384
|
+
const mappedToolChoice = convertAnthropicToolChoiceToOpenAI(body.tool_choice);
|
|
385
|
+
const transformedBody = {
|
|
386
|
+
...(requestedModel ? { model: requestedModel } : {}),
|
|
387
|
+
messages: mappedMessages,
|
|
388
|
+
stream: false,
|
|
389
|
+
};
|
|
390
|
+
if (typeof body.max_tokens === 'number') {
|
|
391
|
+
transformedBody.max_tokens = body.max_tokens;
|
|
392
|
+
}
|
|
393
|
+
if (typeof body.temperature === 'number') {
|
|
394
|
+
transformedBody.temperature = body.temperature;
|
|
395
|
+
}
|
|
396
|
+
if (typeof body.top_p === 'number') {
|
|
397
|
+
transformedBody.top_p = body.top_p;
|
|
398
|
+
}
|
|
399
|
+
if (Array.isArray(body.stop_sequences)) {
|
|
400
|
+
transformedBody.stop = body.stop_sequences;
|
|
401
|
+
}
|
|
402
|
+
if (mappedTools) {
|
|
403
|
+
transformedBody.tools = mappedTools;
|
|
404
|
+
}
|
|
405
|
+
if (mappedToolChoice !== undefined) {
|
|
406
|
+
transformedBody.tool_choice = mappedToolChoice;
|
|
407
|
+
}
|
|
408
|
+
if (body.metadata && typeof body.metadata === 'object' && !Array.isArray(body.metadata)) {
|
|
409
|
+
transformedBody.metadata = body.metadata;
|
|
410
|
+
}
|
|
411
|
+
if (typeof body.user === 'string') {
|
|
412
|
+
transformedBody.user = body.user;
|
|
413
|
+
}
|
|
414
|
+
const transformedHeaders = { ...request.headers };
|
|
415
|
+
for (const headerName of Object.keys(transformedHeaders)) {
|
|
416
|
+
const lower = headerName.toLowerCase();
|
|
417
|
+
if (lower === 'anthropic-version' || lower === 'anthropic-beta') {
|
|
418
|
+
delete transformedHeaders[headerName];
|
|
419
|
+
}
|
|
420
|
+
}
|
|
421
|
+
transformedHeaders['content-type'] = 'application/json';
|
|
422
|
+
return {
|
|
423
|
+
request: {
|
|
424
|
+
...request,
|
|
425
|
+
path: '/v1/chat/completions',
|
|
426
|
+
headers: transformedHeaders,
|
|
427
|
+
body: encodeJson(transformedBody),
|
|
428
|
+
},
|
|
429
|
+
streamRequested,
|
|
430
|
+
requestedModel,
|
|
431
|
+
};
|
|
432
|
+
}
|
|
433
|
+
export function transformOpenAIChatResponseToAnthropicMessage(response, options) {
|
|
434
|
+
const parsed = parseJsonObject(response.body);
|
|
435
|
+
if (!parsed) {
|
|
436
|
+
return response;
|
|
437
|
+
}
|
|
438
|
+
if (response.statusCode >= 400) {
|
|
439
|
+
const openaiError = parsed.error && typeof parsed.error === 'object'
|
|
440
|
+
? parsed.error
|
|
441
|
+
: null;
|
|
442
|
+
const message = openaiError && typeof openaiError.message === 'string'
|
|
443
|
+
? openaiError.message
|
|
444
|
+
: 'Upstream error';
|
|
445
|
+
const anthropicError = {
|
|
446
|
+
type: 'error',
|
|
447
|
+
error: {
|
|
448
|
+
type: 'api_error',
|
|
449
|
+
message,
|
|
450
|
+
},
|
|
451
|
+
};
|
|
452
|
+
return {
|
|
453
|
+
...response,
|
|
454
|
+
headers: {
|
|
455
|
+
...response.headers,
|
|
456
|
+
'content-type': options.streamRequested ? 'text/event-stream' : 'application/json',
|
|
457
|
+
},
|
|
458
|
+
body: options.streamRequested
|
|
459
|
+
? new TextEncoder().encode(`event: error\ndata: ${JSON.stringify(anthropicError)}\n\n`)
|
|
460
|
+
: encodeJson(anthropicError),
|
|
461
|
+
};
|
|
462
|
+
}
|
|
463
|
+
const choices = Array.isArray(parsed.choices) ? parsed.choices : [];
|
|
464
|
+
const firstChoice = choices[0] && typeof choices[0] === 'object'
|
|
465
|
+
? choices[0]
|
|
466
|
+
: null;
|
|
467
|
+
const message = firstChoice?.message && typeof firstChoice.message === 'object'
|
|
468
|
+
? firstChoice.message
|
|
469
|
+
: null;
|
|
470
|
+
const finishReason = mapFinishReasonToAnthropicStopReason(firstChoice?.finish_reason);
|
|
471
|
+
const contentBlocks = [];
|
|
472
|
+
const textContent = toStringContent(message?.content);
|
|
473
|
+
if (textContent.length > 0) {
|
|
474
|
+
contentBlocks.push({ type: 'text', text: textContent });
|
|
475
|
+
}
|
|
476
|
+
const toolCalls = Array.isArray(message?.tool_calls) ? message.tool_calls : [];
|
|
477
|
+
for (const [index, toolCallRaw] of toolCalls.entries()) {
|
|
478
|
+
if (!toolCallRaw || typeof toolCallRaw !== 'object') {
|
|
479
|
+
continue;
|
|
480
|
+
}
|
|
481
|
+
const toolCall = toolCallRaw;
|
|
482
|
+
const functionPayload = toolCall.function && typeof toolCall.function === 'object'
|
|
483
|
+
? toolCall.function
|
|
484
|
+
: {};
|
|
485
|
+
const id = typeof toolCall.id === 'string' && toolCall.id.length > 0
|
|
486
|
+
? toolCall.id
|
|
487
|
+
: `toolu_${index + 1}`;
|
|
488
|
+
const name = typeof functionPayload.name === 'string' && functionPayload.name.length > 0
|
|
489
|
+
? functionPayload.name
|
|
490
|
+
: 'tool';
|
|
491
|
+
const argsRaw = typeof functionPayload.arguments === 'string' ? functionPayload.arguments : '{}';
|
|
492
|
+
const parsedArgs = parseJsonSafe(argsRaw);
|
|
493
|
+
contentBlocks.push({
|
|
494
|
+
type: 'tool_use',
|
|
495
|
+
id,
|
|
496
|
+
name,
|
|
497
|
+
input: parsedArgs && typeof parsedArgs === 'object' && !Array.isArray(parsedArgs)
|
|
498
|
+
? parsedArgs
|
|
499
|
+
: { raw: argsRaw },
|
|
500
|
+
});
|
|
501
|
+
}
|
|
502
|
+
const usage = parsed.usage && typeof parsed.usage === 'object'
|
|
503
|
+
? parsed.usage
|
|
504
|
+
: {};
|
|
505
|
+
const inputTokens = toNonNegativeInt(usage.prompt_tokens ?? usage.input_tokens);
|
|
506
|
+
const outputTokens = toNonNegativeInt(usage.completion_tokens ?? usage.output_tokens);
|
|
507
|
+
const id = typeof parsed.id === 'string' && parsed.id.length > 0 ? parsed.id : `msg_${response.requestId}`;
|
|
508
|
+
const service = typeof parsed.model === 'string' && parsed.model.length > 0
|
|
509
|
+
? parsed.model
|
|
510
|
+
: (options.fallbackModel ?? 'unknown');
|
|
511
|
+
const anthropicMessage = {
|
|
512
|
+
id,
|
|
513
|
+
type: 'message',
|
|
514
|
+
role: 'assistant',
|
|
515
|
+
model: service,
|
|
516
|
+
content: contentBlocks,
|
|
517
|
+
stop_reason: finishReason,
|
|
518
|
+
stop_sequence: null,
|
|
519
|
+
usage: {
|
|
520
|
+
input_tokens: inputTokens,
|
|
521
|
+
output_tokens: outputTokens,
|
|
522
|
+
},
|
|
523
|
+
};
|
|
524
|
+
if (options.streamRequested) {
|
|
525
|
+
return {
|
|
526
|
+
...response,
|
|
527
|
+
headers: {
|
|
528
|
+
...response.headers,
|
|
529
|
+
'content-type': 'text/event-stream',
|
|
530
|
+
'cache-control': 'no-cache',
|
|
531
|
+
},
|
|
532
|
+
body: buildAnthropicStreamFromMessage({
|
|
533
|
+
id,
|
|
534
|
+
service,
|
|
535
|
+
content: contentBlocks,
|
|
536
|
+
stopReason: finishReason,
|
|
537
|
+
usage: {
|
|
538
|
+
inputTokens,
|
|
539
|
+
outputTokens,
|
|
540
|
+
},
|
|
541
|
+
}),
|
|
542
|
+
};
|
|
543
|
+
}
|
|
544
|
+
return {
|
|
545
|
+
...response,
|
|
546
|
+
headers: {
|
|
547
|
+
...response.headers,
|
|
548
|
+
'content-type': 'application/json',
|
|
549
|
+
},
|
|
550
|
+
body: encodeJson(anthropicMessage),
|
|
551
|
+
};
|
|
552
|
+
}
|
|
553
|
+
function convertResponsesToolsToChatTools(tools) {
|
|
554
|
+
const out = [];
|
|
555
|
+
for (const toolRaw of tools) {
|
|
556
|
+
if (!toolRaw || typeof toolRaw !== 'object') {
|
|
557
|
+
continue;
|
|
558
|
+
}
|
|
559
|
+
const tool = toolRaw;
|
|
560
|
+
if (typeof tool.name !== 'string' || tool.name.length === 0) {
|
|
561
|
+
continue;
|
|
562
|
+
}
|
|
563
|
+
out.push({
|
|
564
|
+
type: 'function',
|
|
565
|
+
function: {
|
|
566
|
+
name: tool.name,
|
|
567
|
+
...(typeof tool.description === 'string' ? { description: tool.description } : {}),
|
|
568
|
+
...(tool.parameters && typeof tool.parameters === 'object' ? { parameters: tool.parameters } : {}),
|
|
569
|
+
},
|
|
570
|
+
});
|
|
571
|
+
}
|
|
572
|
+
return out.length > 0 ? out : undefined;
|
|
573
|
+
}
|
|
574
|
+
function convertResponsesInputToMessages(body) {
|
|
575
|
+
const out = [];
|
|
576
|
+
// "instructions" maps to a system message
|
|
577
|
+
if (typeof body.instructions === 'string' && body.instructions.length > 0) {
|
|
578
|
+
out.push({ role: 'system', content: body.instructions });
|
|
579
|
+
}
|
|
580
|
+
const input = body.input;
|
|
581
|
+
// Simple string input → single user message
|
|
582
|
+
if (typeof input === 'string') {
|
|
583
|
+
out.push({ role: 'user', content: input });
|
|
584
|
+
return out;
|
|
585
|
+
}
|
|
586
|
+
// Array of message objects
|
|
587
|
+
if (Array.isArray(input)) {
|
|
588
|
+
for (const item of input) {
|
|
589
|
+
if (!item || typeof item !== 'object') {
|
|
590
|
+
continue;
|
|
591
|
+
}
|
|
592
|
+
const msg = item;
|
|
593
|
+
const type = typeof msg.type === 'string' ? msg.type : '';
|
|
594
|
+
// function_call_output → tool role message with tool_call_id
|
|
595
|
+
if (type === 'function_call_output') {
|
|
596
|
+
out.push({
|
|
597
|
+
role: 'tool',
|
|
598
|
+
tool_call_id: typeof msg.call_id === 'string' ? msg.call_id : '',
|
|
599
|
+
content: typeof msg.output === 'string' ? msg.output : toStringContent(msg.output),
|
|
600
|
+
});
|
|
601
|
+
continue;
|
|
602
|
+
}
|
|
603
|
+
// function_call → assistant message with tool_calls
|
|
604
|
+
if (type === 'function_call') {
|
|
605
|
+
const chatCallId = typeof msg.call_id === 'string' && msg.call_id.length > 0
|
|
606
|
+
? msg.call_id
|
|
607
|
+
: (typeof msg.id === 'string' ? msg.id : '');
|
|
608
|
+
out.push({
|
|
609
|
+
role: 'assistant',
|
|
610
|
+
content: null,
|
|
611
|
+
tool_calls: [{
|
|
612
|
+
id: chatCallId,
|
|
613
|
+
type: 'function',
|
|
614
|
+
function: {
|
|
615
|
+
name: typeof msg.name === 'string' ? msg.name : '',
|
|
616
|
+
arguments: typeof msg.arguments === 'string' ? msg.arguments : JSON.stringify(msg.arguments ?? {}),
|
|
617
|
+
},
|
|
618
|
+
}],
|
|
619
|
+
});
|
|
620
|
+
continue;
|
|
621
|
+
}
|
|
622
|
+
const role = typeof msg.role === 'string' ? msg.role : 'user';
|
|
623
|
+
out.push({ role, content: toStringContent(msg.content) });
|
|
624
|
+
}
|
|
625
|
+
return out;
|
|
626
|
+
}
|
|
627
|
+
return out;
|
|
628
|
+
}
|
|
629
|
+
export function transformOpenAIResponsesRequestToOpenAIChat(request) {
|
|
630
|
+
if (!request.path.toLowerCase().startsWith('/v1/responses')) {
|
|
631
|
+
return null;
|
|
632
|
+
}
|
|
633
|
+
const body = parseJsonObject(request.body);
|
|
634
|
+
if (!body) {
|
|
635
|
+
return null;
|
|
636
|
+
}
|
|
637
|
+
const streamRequested = body.stream === true;
|
|
638
|
+
const requestedModel = typeof body.model === 'string' && body.model.trim().length > 0
|
|
639
|
+
? body.model.trim()
|
|
640
|
+
: null;
|
|
641
|
+
const messages = convertResponsesInputToMessages(body);
|
|
642
|
+
const transformedBody = {
|
|
643
|
+
...(requestedModel ? { model: requestedModel } : {}),
|
|
644
|
+
messages,
|
|
645
|
+
stream: false,
|
|
646
|
+
};
|
|
647
|
+
if (typeof body.max_output_tokens === 'number') {
|
|
648
|
+
transformedBody.max_tokens = body.max_output_tokens;
|
|
649
|
+
}
|
|
650
|
+
if (typeof body.temperature === 'number') {
|
|
651
|
+
transformedBody.temperature = body.temperature;
|
|
652
|
+
}
|
|
653
|
+
if (typeof body.top_p === 'number') {
|
|
654
|
+
transformedBody.top_p = body.top_p;
|
|
655
|
+
}
|
|
656
|
+
if (Array.isArray(body.tools)) {
|
|
657
|
+
const chatTools = convertResponsesToolsToChatTools(body.tools);
|
|
658
|
+
if (chatTools) {
|
|
659
|
+
transformedBody.tools = chatTools;
|
|
660
|
+
}
|
|
661
|
+
}
|
|
662
|
+
if (body.tool_choice !== undefined) {
|
|
663
|
+
const tc = body.tool_choice;
|
|
664
|
+
if (tc && typeof tc === 'object' && !Array.isArray(tc)) {
|
|
665
|
+
const tcObj = tc;
|
|
666
|
+
if (tcObj.type === 'function' && typeof tcObj.name === 'string') {
|
|
667
|
+
transformedBody.tool_choice = { type: 'function', function: { name: tcObj.name } };
|
|
668
|
+
}
|
|
669
|
+
else {
|
|
670
|
+
transformedBody.tool_choice = tc;
|
|
671
|
+
}
|
|
672
|
+
}
|
|
673
|
+
else {
|
|
674
|
+
transformedBody.tool_choice = tc;
|
|
675
|
+
}
|
|
676
|
+
}
|
|
677
|
+
if (body.metadata && typeof body.metadata === 'object' && !Array.isArray(body.metadata)) {
|
|
678
|
+
transformedBody.metadata = body.metadata;
|
|
679
|
+
}
|
|
680
|
+
return {
|
|
681
|
+
request: {
|
|
682
|
+
...request,
|
|
683
|
+
path: '/v1/chat/completions',
|
|
684
|
+
headers: { ...request.headers, 'content-type': 'application/json' },
|
|
685
|
+
body: encodeJson(transformedBody),
|
|
686
|
+
},
|
|
687
|
+
streamRequested,
|
|
688
|
+
requestedModel,
|
|
689
|
+
};
|
|
690
|
+
}
|
|
691
|
+
function buildOpenAIResponsesBody(response, parsed, options) {
|
|
692
|
+
const choices = Array.isArray(parsed.choices) ? parsed.choices : [];
|
|
693
|
+
const firstChoice = choices[0] && typeof choices[0] === 'object'
|
|
694
|
+
? choices[0]
|
|
695
|
+
: null;
|
|
696
|
+
const message = firstChoice?.message && typeof firstChoice.message === 'object'
|
|
697
|
+
? firstChoice.message
|
|
698
|
+
: null;
|
|
699
|
+
const outputItems = [];
|
|
700
|
+
const textContent = toStringContent(message?.content);
|
|
701
|
+
if (textContent.length > 0) {
|
|
702
|
+
outputItems.push({
|
|
703
|
+
type: 'message',
|
|
704
|
+
id: `${typeof parsed.id === 'string' && parsed.id.length > 0 ? parsed.id : `resp_${response.requestId}`}_msg_1`,
|
|
705
|
+
role: 'assistant',
|
|
706
|
+
status: 'completed',
|
|
707
|
+
content: [{
|
|
708
|
+
type: 'output_text',
|
|
709
|
+
text: textContent,
|
|
710
|
+
annotations: [],
|
|
711
|
+
}],
|
|
712
|
+
});
|
|
713
|
+
}
|
|
714
|
+
const toolCalls = Array.isArray(message?.tool_calls) ? message.tool_calls : [];
|
|
715
|
+
for (const [index, toolCallRaw] of toolCalls.entries()) {
|
|
716
|
+
if (!toolCallRaw || typeof toolCallRaw !== 'object') {
|
|
717
|
+
continue;
|
|
718
|
+
}
|
|
719
|
+
const toolCall = toolCallRaw;
|
|
720
|
+
const functionPayload = toolCall.function && typeof toolCall.function === 'object'
|
|
721
|
+
? toolCall.function
|
|
722
|
+
: {};
|
|
723
|
+
const callId = typeof toolCall.id === 'string' && toolCall.id.length > 0
|
|
724
|
+
? toolCall.id
|
|
725
|
+
: `call_${index + 1}`;
|
|
726
|
+
outputItems.push({
|
|
727
|
+
type: 'function_call',
|
|
728
|
+
id: callId,
|
|
729
|
+
call_id: callId,
|
|
730
|
+
name: typeof functionPayload.name === 'string' ? functionPayload.name : '',
|
|
731
|
+
arguments: typeof functionPayload.arguments === 'string' ? functionPayload.arguments : '{}',
|
|
732
|
+
status: 'completed',
|
|
733
|
+
});
|
|
734
|
+
}
|
|
735
|
+
const usage = parsed.usage && typeof parsed.usage === 'object'
|
|
736
|
+
? parsed.usage
|
|
737
|
+
: {};
|
|
738
|
+
const inputTokens = toNonNegativeInt(usage.prompt_tokens ?? usage.input_tokens);
|
|
739
|
+
const outputTokens = toNonNegativeInt(usage.completion_tokens ?? usage.output_tokens);
|
|
740
|
+
const id = typeof parsed.id === 'string' && parsed.id.length > 0 ? parsed.id : `resp_${response.requestId}`;
|
|
741
|
+
const service = typeof parsed.model === 'string' && parsed.model.length > 0
|
|
742
|
+
? parsed.model
|
|
743
|
+
: (options.fallbackModel ?? 'unknown');
|
|
744
|
+
return {
|
|
745
|
+
id,
|
|
746
|
+
object: 'response',
|
|
747
|
+
model: service,
|
|
748
|
+
status: 'completed',
|
|
749
|
+
created_at: Math.floor(Date.now() / 1000),
|
|
750
|
+
output: outputItems,
|
|
751
|
+
output_text: textContent,
|
|
752
|
+
usage: {
|
|
753
|
+
input_tokens: inputTokens,
|
|
754
|
+
output_tokens: outputTokens,
|
|
755
|
+
total_tokens: inputTokens + outputTokens,
|
|
756
|
+
},
|
|
757
|
+
};
|
|
758
|
+
}
|
|
759
|
+
function buildOpenAIResponsesStream(body) {
|
|
760
|
+
const sseEvents = [];
|
|
761
|
+
let sequenceNumber = 0;
|
|
762
|
+
const pushEvent = (event, data) => {
|
|
763
|
+
sseEvents.push(`event: ${event}\ndata: ${JSON.stringify({ type: event, sequence_number: sequenceNumber++, ...data })}\n\n`);
|
|
764
|
+
};
|
|
765
|
+
pushEvent('response.created', {
|
|
766
|
+
response: {
|
|
767
|
+
...body,
|
|
768
|
+
status: 'in_progress',
|
|
769
|
+
output: [],
|
|
770
|
+
output_text: '',
|
|
771
|
+
},
|
|
772
|
+
});
|
|
773
|
+
for (const [outputIndex, outputItem] of body.output.entries()) {
|
|
774
|
+
if (outputItem.type === 'message') {
|
|
775
|
+
const pendingItem = {
|
|
776
|
+
...outputItem,
|
|
777
|
+
status: 'in_progress',
|
|
778
|
+
content: outputItem.content.map((part) => ({ ...part, text: '' })),
|
|
779
|
+
};
|
|
780
|
+
pushEvent('response.output_item.added', {
|
|
781
|
+
output_index: outputIndex,
|
|
782
|
+
item: pendingItem,
|
|
783
|
+
});
|
|
784
|
+
for (const [contentIndex, part] of outputItem.content.entries()) {
|
|
785
|
+
const pendingPart = { ...part, text: '' };
|
|
786
|
+
pushEvent('response.content_part.added', {
|
|
787
|
+
output_index: outputIndex,
|
|
788
|
+
item_id: outputItem.id,
|
|
789
|
+
content_index: contentIndex,
|
|
790
|
+
part: pendingPart,
|
|
791
|
+
});
|
|
792
|
+
pushEvent('response.output_text.delta', {
|
|
793
|
+
output_index: outputIndex,
|
|
794
|
+
item_id: outputItem.id,
|
|
795
|
+
content_index: contentIndex,
|
|
796
|
+
delta: part.text,
|
|
797
|
+
logprobs: [],
|
|
798
|
+
});
|
|
799
|
+
pushEvent('response.output_text.done', {
|
|
800
|
+
output_index: outputIndex,
|
|
801
|
+
item_id: outputItem.id,
|
|
802
|
+
content_index: contentIndex,
|
|
803
|
+
text: part.text,
|
|
804
|
+
logprobs: [],
|
|
805
|
+
});
|
|
806
|
+
pushEvent('response.content_part.done', {
|
|
807
|
+
output_index: outputIndex,
|
|
808
|
+
item_id: outputItem.id,
|
|
809
|
+
content_index: contentIndex,
|
|
810
|
+
part,
|
|
811
|
+
});
|
|
812
|
+
}
|
|
813
|
+
pushEvent('response.output_item.done', {
|
|
814
|
+
output_index: outputIndex,
|
|
815
|
+
item: outputItem,
|
|
816
|
+
});
|
|
817
|
+
continue;
|
|
818
|
+
}
|
|
819
|
+
const pendingItem = {
|
|
820
|
+
...outputItem,
|
|
821
|
+
status: 'in_progress',
|
|
822
|
+
arguments: '',
|
|
823
|
+
};
|
|
824
|
+
pushEvent('response.output_item.added', {
|
|
825
|
+
output_index: outputIndex,
|
|
826
|
+
item: pendingItem,
|
|
827
|
+
});
|
|
828
|
+
pushEvent('response.function_call_arguments.delta', {
|
|
829
|
+
output_index: outputIndex,
|
|
830
|
+
item_id: outputItem.id,
|
|
831
|
+
call_id: outputItem.call_id,
|
|
832
|
+
delta: outputItem.arguments,
|
|
833
|
+
});
|
|
834
|
+
pushEvent('response.function_call_arguments.done', {
|
|
835
|
+
output_index: outputIndex,
|
|
836
|
+
item_id: outputItem.id,
|
|
837
|
+
call_id: outputItem.call_id,
|
|
838
|
+
name: outputItem.name,
|
|
839
|
+
arguments: outputItem.arguments,
|
|
840
|
+
});
|
|
841
|
+
pushEvent('response.output_item.done', {
|
|
842
|
+
output_index: outputIndex,
|
|
843
|
+
item: outputItem,
|
|
844
|
+
});
|
|
845
|
+
}
|
|
846
|
+
pushEvent('response.completed', { response: body });
|
|
847
|
+
sseEvents.push('data: [DONE]\n\n');
|
|
848
|
+
return new TextEncoder().encode(sseEvents.join(''));
|
|
849
|
+
}
|
|
850
|
+
export function transformOpenAIChatResponseToOpenAIResponses(response, options) {
|
|
851
|
+
const parsed = parseJsonObject(response.body);
|
|
852
|
+
if (!parsed) {
|
|
853
|
+
return response;
|
|
854
|
+
}
|
|
855
|
+
if (response.statusCode >= 400) {
|
|
856
|
+
const errorPayload = parsed.error && typeof parsed.error === 'object'
|
|
857
|
+
? parsed.error
|
|
858
|
+
: parsed;
|
|
859
|
+
const errorBody = errorPayload === parsed ? parsed : { error: errorPayload };
|
|
860
|
+
if (options.streamRequested) {
|
|
861
|
+
return {
|
|
862
|
+
...response,
|
|
863
|
+
headers: {
|
|
864
|
+
...response.headers,
|
|
865
|
+
'content-type': 'text/event-stream',
|
|
866
|
+
'cache-control': 'no-cache',
|
|
867
|
+
},
|
|
868
|
+
body: new TextEncoder().encode(`event: error\ndata: ${JSON.stringify(errorBody)}\n\n`),
|
|
869
|
+
};
|
|
870
|
+
}
|
|
871
|
+
return {
|
|
872
|
+
...response,
|
|
873
|
+
headers: { ...response.headers, 'content-type': 'application/json' },
|
|
874
|
+
body: encodeJson(errorBody),
|
|
875
|
+
};
|
|
876
|
+
}
|
|
877
|
+
const responsesBody = buildOpenAIResponsesBody(response, parsed, options);
|
|
878
|
+
if (!options.streamRequested) {
|
|
879
|
+
return {
|
|
880
|
+
...response,
|
|
881
|
+
headers: { ...response.headers, 'content-type': 'application/json' },
|
|
882
|
+
body: encodeJson(responsesBody),
|
|
883
|
+
};
|
|
884
|
+
}
|
|
885
|
+
return {
|
|
886
|
+
...response,
|
|
887
|
+
headers: { ...response.headers, 'content-type': 'text/event-stream', 'cache-control': 'no-cache' },
|
|
888
|
+
body: buildOpenAIResponsesStream(responsesBody),
|
|
889
|
+
};
|
|
890
|
+
}
|
|
891
|
+
//# sourceMappingURL=service-api-adapter.js.map
|