@copilotkit/aimock 1.16.0 → 1.16.2
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/.claude-plugin/marketplace.json +1 -1
- package/.claude-plugin/plugin.json +1 -1
- package/CHANGELOG.md +31 -0
- package/dist/bedrock-converse.cjs +197 -15
- package/dist/bedrock-converse.cjs.map +1 -1
- package/dist/bedrock-converse.d.cts +2 -1
- package/dist/bedrock-converse.d.cts.map +1 -1
- package/dist/bedrock-converse.d.ts +2 -1
- package/dist/bedrock-converse.d.ts.map +1 -1
- package/dist/bedrock-converse.js +194 -12
- package/dist/bedrock-converse.js.map +1 -1
- package/dist/bedrock.cjs +208 -152
- package/dist/bedrock.cjs.map +1 -1
- package/dist/bedrock.d.cts +2 -1
- package/dist/bedrock.d.cts.map +1 -1
- package/dist/bedrock.d.ts +2 -1
- package/dist/bedrock.d.ts.map +1 -1
- package/dist/bedrock.js +209 -150
- package/dist/bedrock.js.map +1 -1
- package/dist/cohere.cjs +4 -1
- package/dist/cohere.cjs.map +1 -1
- package/dist/cohere.js +4 -1
- package/dist/cohere.js.map +1 -1
- package/dist/config-loader.d.cts.map +1 -1
- package/dist/embeddings.cjs +4 -1
- package/dist/embeddings.cjs.map +1 -1
- package/dist/embeddings.js +4 -1
- package/dist/embeddings.js.map +1 -1
- package/dist/gemini.cjs +2 -0
- package/dist/gemini.cjs.map +1 -1
- package/dist/gemini.js +2 -0
- package/dist/gemini.js.map +1 -1
- package/dist/images.cjs +4 -1
- package/dist/images.cjs.map +1 -1
- package/dist/images.js +4 -1
- package/dist/images.js.map +1 -1
- package/dist/messages.cjs +8 -1
- package/dist/messages.cjs.map +1 -1
- package/dist/messages.js +8 -1
- package/dist/messages.js.map +1 -1
- package/dist/ollama.cjs +8 -2
- package/dist/ollama.cjs.map +1 -1
- package/dist/ollama.d.cts.map +1 -1
- package/dist/ollama.d.ts.map +1 -1
- package/dist/ollama.js +8 -2
- package/dist/ollama.js.map +1 -1
- package/dist/responses.cjs +87 -13
- package/dist/responses.cjs.map +1 -1
- package/dist/responses.d.cts.map +1 -1
- package/dist/responses.d.ts.map +1 -1
- package/dist/responses.js +87 -13
- package/dist/responses.js.map +1 -1
- package/dist/server.cjs +8 -1
- package/dist/server.cjs.map +1 -1
- package/dist/server.d.cts.map +1 -1
- package/dist/server.d.ts.map +1 -1
- package/dist/server.js +8 -1
- package/dist/server.js.map +1 -1
- package/dist/speech.cjs +4 -1
- package/dist/speech.cjs.map +1 -1
- package/dist/speech.js +4 -1
- package/dist/speech.js.map +1 -1
- package/dist/transcription.cjs +4 -1
- package/dist/transcription.cjs.map +1 -1
- package/dist/transcription.js +4 -1
- package/dist/transcription.js.map +1 -1
- package/dist/video.cjs +4 -1
- package/dist/video.cjs.map +1 -1
- package/dist/video.d.cts.map +1 -1
- package/dist/video.d.ts.map +1 -1
- package/dist/video.js +4 -1
- package/dist/video.js.map +1 -1
- package/package.json +1 -1
package/dist/bedrock.js
CHANGED
|
@@ -14,6 +14,15 @@ function bedrockStopReason(overrideFinishReason, defaultReason) {
|
|
|
14
14
|
if (overrideFinishReason === "length") return "max_tokens";
|
|
15
15
|
return overrideFinishReason;
|
|
16
16
|
}
|
|
17
|
+
/**
|
|
18
|
+
* Build a Bedrock-style usage object from optional overrides.
|
|
19
|
+
*
|
|
20
|
+
* When no overrides are provided (the common case for mock fixtures),
|
|
21
|
+
* returns all-zero token counts. This is intentional — aimock does not
|
|
22
|
+
* attempt to estimate token usage from fixture content. Callers that
|
|
23
|
+
* need realistic usage numbers should set `usage` in their fixture's
|
|
24
|
+
* response overrides.
|
|
25
|
+
*/
|
|
17
26
|
function bedrockUsage(overrides) {
|
|
18
27
|
if (!overrides?.usage) return {
|
|
19
28
|
input_tokens: 0,
|
|
@@ -28,7 +37,7 @@ function extractTextContent(content) {
|
|
|
28
37
|
if (typeof content === "string") return content;
|
|
29
38
|
return content.filter((b) => b.type === "text").map((b) => b.text ?? "").join("");
|
|
30
39
|
}
|
|
31
|
-
function bedrockToCompletionRequest(req, modelId) {
|
|
40
|
+
function bedrockToCompletionRequest(req, modelId, logger) {
|
|
32
41
|
const messages = [];
|
|
33
42
|
if (req.system) {
|
|
34
43
|
const systemText = typeof req.system === "string" ? req.system : req.system.filter((b) => b.type === "text").map((b) => b.text ?? "").join("");
|
|
@@ -39,6 +48,11 @@ function bedrockToCompletionRequest(req, modelId) {
|
|
|
39
48
|
}
|
|
40
49
|
for (const msg of req.messages) if (msg.role === "user") {
|
|
41
50
|
if (typeof msg.content !== "string" && Array.isArray(msg.content)) {
|
|
51
|
+
const unsupportedBlocks = msg.content.filter((b) => b.type !== "text" && b.type !== "tool_result");
|
|
52
|
+
if (unsupportedBlocks.length > 0 && logger) {
|
|
53
|
+
const types = [...new Set(unsupportedBlocks.map((b) => b.type))].join(", ");
|
|
54
|
+
logger.warn(`Bedrock user message contains unsupported content block types [${types}] — these will be dropped during conversion`);
|
|
55
|
+
}
|
|
42
56
|
const toolResults = msg.content.filter((b) => b.type === "tool_result");
|
|
43
57
|
const textBlocks = msg.content.filter((b) => b.type === "text");
|
|
44
58
|
if (toolResults.length > 0) {
|
|
@@ -70,24 +84,28 @@ function bedrockToCompletionRequest(req, modelId) {
|
|
|
70
84
|
const textContent = extractTextContent(msg.content);
|
|
71
85
|
if (toolUseBlocks.length > 0) messages.push({
|
|
72
86
|
role: "assistant",
|
|
73
|
-
content: textContent
|
|
74
|
-
tool_calls: toolUseBlocks.map((b) =>
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
87
|
+
content: textContent ?? null,
|
|
88
|
+
tool_calls: toolUseBlocks.map((b, index) => {
|
|
89
|
+
if (!b.id && logger) logger.warn(`Bedrock assistant tool_use block at index ${index} is missing an id — using deterministic fallback "tool_use_${index}"`);
|
|
90
|
+
return {
|
|
91
|
+
id: b.id ?? `tool_use_${index}`,
|
|
92
|
+
type: "function",
|
|
93
|
+
function: {
|
|
94
|
+
name: b.name ?? "",
|
|
95
|
+
arguments: typeof b.input === "string" ? b.input : JSON.stringify(b.input ?? {})
|
|
96
|
+
}
|
|
97
|
+
};
|
|
98
|
+
})
|
|
82
99
|
});
|
|
83
100
|
else messages.push({
|
|
84
101
|
role: "assistant",
|
|
85
|
-
content: textContent
|
|
102
|
+
content: textContent ?? null
|
|
86
103
|
});
|
|
87
104
|
} else messages.push({
|
|
88
105
|
role: "assistant",
|
|
89
106
|
content: null
|
|
90
107
|
});
|
|
108
|
+
else if (logger) logger.warn(`Bedrock message has unexpected role "${msg.role}" — skipping`);
|
|
91
109
|
let tools;
|
|
92
110
|
if (req.tools && req.tools.length > 0) tools = req.tools.map((t) => ({
|
|
93
111
|
type: "function",
|
|
@@ -193,10 +211,12 @@ async function handleBedrock(req, res, raw, modelId, fixtures, journal, defaults
|
|
|
193
211
|
} }));
|
|
194
212
|
return;
|
|
195
213
|
}
|
|
196
|
-
const completionReq = bedrockToCompletionRequest(bedrockReq, modelId);
|
|
214
|
+
const completionReq = bedrockToCompletionRequest(bedrockReq, modelId, logger);
|
|
197
215
|
completionReq._endpointType = "chat";
|
|
198
216
|
const testId = getTestId(req);
|
|
199
217
|
const fixture = matchFixture(fixtures, completionReq, journal.getFixtureMatchCountsForTest(testId), defaults.requestTransform);
|
|
218
|
+
if (fixture) logger.debug(`Fixture matched: ${JSON.stringify(fixture.match).slice(0, 120)}`);
|
|
219
|
+
else logger.debug(`No fixture matched for request`);
|
|
200
220
|
if (fixture) journal.incrementFixtureMatchCount(fixture, fixtures, testId);
|
|
201
221
|
if (applyChaos(res, fixture, defaults.chaos, req.headers, journal, {
|
|
202
222
|
method: req.method ?? "POST",
|
|
@@ -306,6 +326,7 @@ async function handleBedrock(req, res, raw, modelId, fixtures, journal, defaults
|
|
|
306
326
|
return;
|
|
307
327
|
}
|
|
308
328
|
if (isToolCallResponse(response)) {
|
|
329
|
+
if ("webSearches" in response) logger.warn("webSearches in fixture response are not supported for Bedrock API — ignoring");
|
|
309
330
|
const overrides = extractOverrides(response);
|
|
310
331
|
journal.add({
|
|
311
332
|
method: req.method ?? "POST",
|
|
@@ -337,151 +358,198 @@ async function handleBedrock(req, res, raw, modelId, fixtures, journal, defaults
|
|
|
337
358
|
type: "server_error"
|
|
338
359
|
} }));
|
|
339
360
|
}
|
|
340
|
-
|
|
361
|
+
const BEDROCK_INVOKE_STREAM_EVENT_TYPE = "chunk";
|
|
362
|
+
function buildBedrockInvokeMessageStart(model, overrides) {
|
|
363
|
+
return {
|
|
364
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
365
|
+
payload: {
|
|
366
|
+
type: "message_start",
|
|
367
|
+
message: {
|
|
368
|
+
id: overrides?.id ?? generateMessageId(),
|
|
369
|
+
type: "message",
|
|
370
|
+
role: "assistant",
|
|
371
|
+
content: [],
|
|
372
|
+
model: overrides?.model ?? model,
|
|
373
|
+
stop_reason: null,
|
|
374
|
+
stop_sequence: null,
|
|
375
|
+
usage: bedrockUsage(overrides)
|
|
376
|
+
}
|
|
377
|
+
}
|
|
378
|
+
};
|
|
379
|
+
}
|
|
380
|
+
function buildBedrockInvokeMessageDelta(stopReason) {
|
|
381
|
+
return {
|
|
382
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
383
|
+
payload: {
|
|
384
|
+
type: "message_delta",
|
|
385
|
+
delta: {
|
|
386
|
+
stop_reason: stopReason,
|
|
387
|
+
stop_sequence: null
|
|
388
|
+
},
|
|
389
|
+
usage: { output_tokens: 0 }
|
|
390
|
+
}
|
|
391
|
+
};
|
|
392
|
+
}
|
|
393
|
+
function buildBedrockInvokeMessageStop() {
|
|
394
|
+
return {
|
|
395
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
396
|
+
payload: { type: "message_stop" }
|
|
397
|
+
};
|
|
398
|
+
}
|
|
399
|
+
function parseToolArgumentsForStream(toolCall, logger) {
|
|
400
|
+
try {
|
|
401
|
+
const parsed = JSON.parse(toolCall.arguments || "{}");
|
|
402
|
+
return JSON.stringify(parsed);
|
|
403
|
+
} catch {
|
|
404
|
+
logger.warn(`Malformed JSON in fixture tool call arguments for "${toolCall.name}": ${toolCall.arguments}`);
|
|
405
|
+
return "{}";
|
|
406
|
+
}
|
|
407
|
+
}
|
|
408
|
+
function buildBedrockStreamTextEvents(content, model, chunkSize, reasoning, overrides) {
|
|
341
409
|
const events = [];
|
|
342
|
-
events.push(
|
|
343
|
-
eventType: "messageStart",
|
|
344
|
-
payload: { messageStart: { role: "assistant" } }
|
|
345
|
-
});
|
|
410
|
+
events.push(buildBedrockInvokeMessageStart(model, overrides));
|
|
346
411
|
if (reasoning) {
|
|
347
412
|
const blockIndex = 0;
|
|
348
413
|
events.push({
|
|
349
|
-
eventType:
|
|
414
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
350
415
|
payload: {
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
416
|
+
type: "content_block_start",
|
|
417
|
+
index: blockIndex,
|
|
418
|
+
content_block: {
|
|
419
|
+
type: "thinking",
|
|
420
|
+
thinking: ""
|
|
355
421
|
}
|
|
356
422
|
}
|
|
357
423
|
});
|
|
358
424
|
for (let i = 0; i < reasoning.length; i += chunkSize) {
|
|
359
425
|
const slice = reasoning.slice(i, i + chunkSize);
|
|
360
426
|
events.push({
|
|
361
|
-
eventType:
|
|
427
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
362
428
|
payload: {
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
thinking: slice
|
|
369
|
-
}
|
|
429
|
+
type: "content_block_delta",
|
|
430
|
+
index: blockIndex,
|
|
431
|
+
delta: {
|
|
432
|
+
type: "thinking_delta",
|
|
433
|
+
thinking: slice
|
|
370
434
|
}
|
|
371
435
|
}
|
|
372
436
|
});
|
|
373
437
|
}
|
|
374
438
|
events.push({
|
|
375
|
-
eventType:
|
|
376
|
-
payload: {
|
|
439
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
440
|
+
payload: {
|
|
441
|
+
type: "content_block_stop",
|
|
442
|
+
index: blockIndex
|
|
443
|
+
}
|
|
377
444
|
});
|
|
378
445
|
}
|
|
379
446
|
const textBlockIndex = reasoning ? 1 : 0;
|
|
380
447
|
events.push({
|
|
381
|
-
eventType:
|
|
448
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
382
449
|
payload: {
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
450
|
+
type: "content_block_start",
|
|
451
|
+
index: textBlockIndex,
|
|
452
|
+
content_block: {
|
|
453
|
+
type: "text",
|
|
454
|
+
text: ""
|
|
387
455
|
}
|
|
388
456
|
}
|
|
389
457
|
});
|
|
390
458
|
for (let i = 0; i < content.length; i += chunkSize) {
|
|
391
459
|
const slice = content.slice(i, i + chunkSize);
|
|
392
460
|
events.push({
|
|
393
|
-
eventType:
|
|
461
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
394
462
|
payload: {
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
text: slice
|
|
401
|
-
}
|
|
463
|
+
type: "content_block_delta",
|
|
464
|
+
index: textBlockIndex,
|
|
465
|
+
delta: {
|
|
466
|
+
type: "text_delta",
|
|
467
|
+
text: slice
|
|
402
468
|
}
|
|
403
469
|
}
|
|
404
470
|
});
|
|
405
471
|
}
|
|
406
472
|
events.push({
|
|
407
|
-
eventType:
|
|
408
|
-
payload: {
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
payload: { stopReason: bedrockStopReason(overrides?.finishReason, "end_turn") }
|
|
473
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
474
|
+
payload: {
|
|
475
|
+
type: "content_block_stop",
|
|
476
|
+
index: textBlockIndex
|
|
477
|
+
}
|
|
413
478
|
});
|
|
479
|
+
events.push(buildBedrockInvokeMessageDelta(bedrockStopReason(overrides?.finishReason, "end_turn")));
|
|
480
|
+
events.push(buildBedrockInvokeMessageStop());
|
|
414
481
|
return events;
|
|
415
482
|
}
|
|
416
|
-
function buildBedrockStreamContentWithToolCallsEvents(content, toolCalls, chunkSize, logger, reasoning, overrides) {
|
|
483
|
+
function buildBedrockStreamContentWithToolCallsEvents(content, toolCalls, model, chunkSize, logger, reasoning, overrides) {
|
|
417
484
|
const events = [];
|
|
418
|
-
events.push(
|
|
419
|
-
eventType: "messageStart",
|
|
420
|
-
payload: { messageStart: { role: "assistant" } }
|
|
421
|
-
});
|
|
485
|
+
events.push(buildBedrockInvokeMessageStart(model, overrides));
|
|
422
486
|
let blockIndex = 0;
|
|
423
487
|
if (reasoning) {
|
|
424
488
|
events.push({
|
|
425
|
-
eventType:
|
|
489
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
426
490
|
payload: {
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
|
|
430
|
-
|
|
491
|
+
type: "content_block_start",
|
|
492
|
+
index: blockIndex,
|
|
493
|
+
content_block: {
|
|
494
|
+
type: "thinking",
|
|
495
|
+
thinking: ""
|
|
431
496
|
}
|
|
432
497
|
}
|
|
433
498
|
});
|
|
434
499
|
for (let i = 0; i < reasoning.length; i += chunkSize) {
|
|
435
500
|
const slice = reasoning.slice(i, i + chunkSize);
|
|
436
501
|
events.push({
|
|
437
|
-
eventType:
|
|
502
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
438
503
|
payload: {
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
thinking: slice
|
|
445
|
-
}
|
|
504
|
+
type: "content_block_delta",
|
|
505
|
+
index: blockIndex,
|
|
506
|
+
delta: {
|
|
507
|
+
type: "thinking_delta",
|
|
508
|
+
thinking: slice
|
|
446
509
|
}
|
|
447
510
|
}
|
|
448
511
|
});
|
|
449
512
|
}
|
|
450
513
|
events.push({
|
|
451
|
-
eventType:
|
|
452
|
-
payload: {
|
|
514
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
515
|
+
payload: {
|
|
516
|
+
type: "content_block_stop",
|
|
517
|
+
index: blockIndex
|
|
518
|
+
}
|
|
453
519
|
});
|
|
454
520
|
blockIndex++;
|
|
455
521
|
}
|
|
456
522
|
events.push({
|
|
457
|
-
eventType:
|
|
523
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
458
524
|
payload: {
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
525
|
+
type: "content_block_start",
|
|
526
|
+
index: blockIndex,
|
|
527
|
+
content_block: {
|
|
528
|
+
type: "text",
|
|
529
|
+
text: ""
|
|
463
530
|
}
|
|
464
531
|
}
|
|
465
532
|
});
|
|
466
533
|
for (let i = 0; i < content.length; i += chunkSize) {
|
|
467
534
|
const slice = content.slice(i, i + chunkSize);
|
|
468
535
|
events.push({
|
|
469
|
-
eventType:
|
|
536
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
470
537
|
payload: {
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
text: slice
|
|
477
|
-
}
|
|
538
|
+
type: "content_block_delta",
|
|
539
|
+
index: blockIndex,
|
|
540
|
+
delta: {
|
|
541
|
+
type: "text_delta",
|
|
542
|
+
text: slice
|
|
478
543
|
}
|
|
479
544
|
}
|
|
480
545
|
});
|
|
481
546
|
}
|
|
482
547
|
events.push({
|
|
483
|
-
eventType:
|
|
484
|
-
payload: {
|
|
548
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
549
|
+
payload: {
|
|
550
|
+
type: "content_block_stop",
|
|
551
|
+
index: blockIndex
|
|
552
|
+
}
|
|
485
553
|
});
|
|
486
554
|
blockIndex++;
|
|
487
555
|
for (let tcIdx = 0; tcIdx < toolCalls.length; tcIdx++) {
|
|
@@ -489,102 +557,89 @@ function buildBedrockStreamContentWithToolCallsEvents(content, toolCalls, chunkS
|
|
|
489
557
|
const toolUseId = tc.id || generateToolUseId();
|
|
490
558
|
const currentBlock = blockIndex + tcIdx;
|
|
491
559
|
events.push({
|
|
492
|
-
eventType:
|
|
560
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
493
561
|
payload: {
|
|
494
|
-
|
|
495
|
-
|
|
496
|
-
|
|
497
|
-
|
|
498
|
-
|
|
499
|
-
|
|
500
|
-
|
|
562
|
+
type: "content_block_start",
|
|
563
|
+
index: currentBlock,
|
|
564
|
+
content_block: {
|
|
565
|
+
type: "tool_use",
|
|
566
|
+
id: toolUseId,
|
|
567
|
+
name: tc.name,
|
|
568
|
+
input: {}
|
|
501
569
|
}
|
|
502
570
|
}
|
|
503
571
|
});
|
|
504
|
-
|
|
505
|
-
try {
|
|
506
|
-
const parsed = JSON.parse(tc.arguments || "{}");
|
|
507
|
-
argsStr = JSON.stringify(parsed);
|
|
508
|
-
} catch {
|
|
509
|
-
logger.warn(`Malformed JSON in fixture tool call arguments for "${tc.name}": ${tc.arguments}`);
|
|
510
|
-
argsStr = "{}";
|
|
511
|
-
}
|
|
572
|
+
const argsStr = parseToolArgumentsForStream(tc, logger);
|
|
512
573
|
for (let i = 0; i < argsStr.length; i += chunkSize) {
|
|
513
574
|
const slice = argsStr.slice(i, i + chunkSize);
|
|
514
575
|
events.push({
|
|
515
|
-
eventType:
|
|
576
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
516
577
|
payload: {
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
|
|
520
|
-
|
|
578
|
+
type: "content_block_delta",
|
|
579
|
+
index: currentBlock,
|
|
580
|
+
delta: {
|
|
581
|
+
type: "input_json_delta",
|
|
582
|
+
partial_json: slice
|
|
521
583
|
}
|
|
522
584
|
}
|
|
523
585
|
});
|
|
524
586
|
}
|
|
525
587
|
events.push({
|
|
526
|
-
eventType:
|
|
527
|
-
payload: {
|
|
588
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
589
|
+
payload: {
|
|
590
|
+
type: "content_block_stop",
|
|
591
|
+
index: currentBlock
|
|
592
|
+
}
|
|
528
593
|
});
|
|
529
594
|
}
|
|
530
|
-
events.push(
|
|
531
|
-
|
|
532
|
-
payload: { stopReason: bedrockStopReason(overrides?.finishReason, "tool_use") }
|
|
533
|
-
});
|
|
595
|
+
events.push(buildBedrockInvokeMessageDelta(bedrockStopReason(overrides?.finishReason, "tool_use")));
|
|
596
|
+
events.push(buildBedrockInvokeMessageStop());
|
|
534
597
|
return events;
|
|
535
598
|
}
|
|
536
|
-
function buildBedrockStreamToolCallEvents(toolCalls, chunkSize, logger, overrides) {
|
|
599
|
+
function buildBedrockStreamToolCallEvents(toolCalls, model, chunkSize, logger, overrides) {
|
|
537
600
|
const events = [];
|
|
538
|
-
events.push(
|
|
539
|
-
eventType: "messageStart",
|
|
540
|
-
payload: { messageStart: { role: "assistant" } }
|
|
541
|
-
});
|
|
601
|
+
events.push(buildBedrockInvokeMessageStart(model, overrides));
|
|
542
602
|
for (let tcIdx = 0; tcIdx < toolCalls.length; tcIdx++) {
|
|
543
603
|
const tc = toolCalls[tcIdx];
|
|
544
604
|
const toolUseId = tc.id || generateToolUseId();
|
|
545
605
|
events.push({
|
|
546
|
-
eventType:
|
|
606
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
547
607
|
payload: {
|
|
548
|
-
|
|
549
|
-
|
|
550
|
-
|
|
551
|
-
|
|
552
|
-
|
|
553
|
-
|
|
554
|
-
|
|
608
|
+
type: "content_block_start",
|
|
609
|
+
index: tcIdx,
|
|
610
|
+
content_block: {
|
|
611
|
+
type: "tool_use",
|
|
612
|
+
id: toolUseId,
|
|
613
|
+
name: tc.name,
|
|
614
|
+
input: {}
|
|
555
615
|
}
|
|
556
616
|
}
|
|
557
617
|
});
|
|
558
|
-
|
|
559
|
-
try {
|
|
560
|
-
const parsed = JSON.parse(tc.arguments || "{}");
|
|
561
|
-
argsStr = JSON.stringify(parsed);
|
|
562
|
-
} catch {
|
|
563
|
-
logger.warn(`Malformed JSON in fixture tool call arguments for "${tc.name}": ${tc.arguments}`);
|
|
564
|
-
argsStr = "{}";
|
|
565
|
-
}
|
|
618
|
+
const argsStr = parseToolArgumentsForStream(tc, logger);
|
|
566
619
|
for (let i = 0; i < argsStr.length; i += chunkSize) {
|
|
567
620
|
const slice = argsStr.slice(i, i + chunkSize);
|
|
568
621
|
events.push({
|
|
569
|
-
eventType:
|
|
622
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
570
623
|
payload: {
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
624
|
+
type: "content_block_delta",
|
|
625
|
+
index: tcIdx,
|
|
626
|
+
delta: {
|
|
627
|
+
type: "input_json_delta",
|
|
628
|
+
partial_json: slice
|
|
575
629
|
}
|
|
576
630
|
}
|
|
577
631
|
});
|
|
578
632
|
}
|
|
579
633
|
events.push({
|
|
580
|
-
eventType:
|
|
581
|
-
payload: {
|
|
634
|
+
eventType: BEDROCK_INVOKE_STREAM_EVENT_TYPE,
|
|
635
|
+
payload: {
|
|
636
|
+
type: "content_block_stop",
|
|
637
|
+
index: tcIdx
|
|
638
|
+
}
|
|
582
639
|
});
|
|
583
640
|
}
|
|
584
|
-
events.push(
|
|
585
|
-
|
|
586
|
-
payload: { stopReason: bedrockStopReason(overrides?.finishReason, "tool_use") }
|
|
587
|
-
});
|
|
641
|
+
events.push(buildBedrockInvokeMessageDelta(bedrockStopReason(overrides?.finishReason, "tool_use")));
|
|
642
|
+
events.push(buildBedrockInvokeMessageStop());
|
|
588
643
|
return events;
|
|
589
644
|
}
|
|
590
645
|
async function handleBedrockStream(req, res, raw, modelId, fixtures, journal, defaults, setCorsHeaders) {
|
|
@@ -628,10 +683,13 @@ async function handleBedrockStream(req, res, raw, modelId, fixtures, journal, de
|
|
|
628
683
|
} }));
|
|
629
684
|
return;
|
|
630
685
|
}
|
|
631
|
-
const completionReq = bedrockToCompletionRequest(bedrockReq, modelId);
|
|
686
|
+
const completionReq = bedrockToCompletionRequest(bedrockReq, modelId, logger);
|
|
687
|
+
completionReq.stream = true;
|
|
632
688
|
completionReq._endpointType = "chat";
|
|
633
689
|
const testId = getTestId(req);
|
|
634
690
|
const fixture = matchFixture(fixtures, completionReq, journal.getFixtureMatchCountsForTest(testId), defaults.requestTransform);
|
|
691
|
+
if (fixture) logger.debug(`Fixture matched: ${JSON.stringify(fixture.match).slice(0, 120)}`);
|
|
692
|
+
else logger.debug(`No fixture matched for request`);
|
|
635
693
|
if (fixture) journal.incrementFixtureMatchCount(fixture, fixtures, testId);
|
|
636
694
|
if (applyChaos(res, fixture, defaults.chaos, req.headers, journal, {
|
|
637
695
|
method: req.method ?? "POST",
|
|
@@ -713,7 +771,7 @@ async function handleBedrockStream(req, res, raw, modelId, fixtures, journal, de
|
|
|
713
771
|
fixture
|
|
714
772
|
}
|
|
715
773
|
});
|
|
716
|
-
const events = buildBedrockStreamContentWithToolCallsEvents(response.content, response.toolCalls, chunkSize, logger, response.reasoning, overrides);
|
|
774
|
+
const events = buildBedrockStreamContentWithToolCallsEvents(response.content, response.toolCalls, completionReq.model, chunkSize, logger, response.reasoning, overrides);
|
|
717
775
|
const interruption = createInterruptionSignal(fixture);
|
|
718
776
|
if (!await writeEventStream(res, events, {
|
|
719
777
|
latency,
|
|
@@ -741,7 +799,7 @@ async function handleBedrockStream(req, res, raw, modelId, fixtures, journal, de
|
|
|
741
799
|
fixture
|
|
742
800
|
}
|
|
743
801
|
});
|
|
744
|
-
const events = buildBedrockStreamTextEvents(response.content, chunkSize, response.reasoning, overrides);
|
|
802
|
+
const events = buildBedrockStreamTextEvents(response.content, completionReq.model, chunkSize, response.reasoning, overrides);
|
|
745
803
|
const interruption = createInterruptionSignal(fixture);
|
|
746
804
|
if (!await writeEventStream(res, events, {
|
|
747
805
|
latency,
|
|
@@ -757,6 +815,7 @@ async function handleBedrockStream(req, res, raw, modelId, fixtures, journal, de
|
|
|
757
815
|
return;
|
|
758
816
|
}
|
|
759
817
|
if (isToolCallResponse(response)) {
|
|
818
|
+
if ("webSearches" in response) logger.warn("webSearches in fixture response are not supported for Bedrock API — ignoring");
|
|
760
819
|
const overrides = extractOverrides(response);
|
|
761
820
|
const journalEntry = journal.add({
|
|
762
821
|
method: req.method ?? "POST",
|
|
@@ -768,7 +827,7 @@ async function handleBedrockStream(req, res, raw, modelId, fixtures, journal, de
|
|
|
768
827
|
fixture
|
|
769
828
|
}
|
|
770
829
|
});
|
|
771
|
-
const events = buildBedrockStreamToolCallEvents(response.toolCalls, chunkSize, logger, overrides);
|
|
830
|
+
const events = buildBedrockStreamToolCallEvents(response.toolCalls, completionReq.model, chunkSize, logger, overrides);
|
|
772
831
|
const interruption = createInterruptionSignal(fixture);
|
|
773
832
|
if (!await writeEventStream(res, events, {
|
|
774
833
|
latency,
|
|
@@ -800,5 +859,5 @@ async function handleBedrockStream(req, res, raw, modelId, fixtures, journal, de
|
|
|
800
859
|
}
|
|
801
860
|
|
|
802
861
|
//#endregion
|
|
803
|
-
export { bedrockToCompletionRequest,
|
|
862
|
+
export { bedrockToCompletionRequest, handleBedrock, handleBedrockStream };
|
|
804
863
|
//# sourceMappingURL=bedrock.js.map
|