@flutchai/flutch-sdk 0.2.20 → 0.2.21

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/dist/index.d.cts CHANGED
@@ -1517,6 +1517,7 @@ declare class EventProcessor {
1517
1517
  private readonly logger;
1518
1518
  createAccumulator(): StreamAccumulator;
1519
1519
  private normalizeContentBlocks;
1520
+ private toolCallChunksToBlocks;
1520
1521
  private extractAttachments;
1521
1522
  private sendDelta;
1522
1523
  private processContentStream;
package/dist/index.d.ts CHANGED
@@ -1517,6 +1517,7 @@ declare class EventProcessor {
1517
1517
  private readonly logger;
1518
1518
  createAccumulator(): StreamAccumulator;
1519
1519
  private normalizeContentBlocks;
1520
+ private toolCallChunksToBlocks;
1520
1521
  private extractAttachments;
1521
1522
  private sendDelta;
1522
1523
  private processContentStream;
package/dist/index.js CHANGED
@@ -4787,6 +4787,36 @@ var EventProcessor = class {
4787
4787
  }
4788
4788
  return [];
4789
4789
  }
4790
+ /**
4791
+ * Convert LangChain unified `tool_call_chunks` (Bedrock / OpenAI streaming
4792
+ * format) into Anthropic-style blocks so the rest of the pipeline can stay
4793
+ * uniform. The first chunk for a tool carries `name` (and usually `id`);
4794
+ * subsequent chunks carry partial `args` strings that need to accumulate.
4795
+ *
4796
+ * NOTE: assumes tool calls arrive sequentially. Parallel tool calls with
4797
+ * interleaved `args` chunks across different `index`es will misroute args
4798
+ * to the most recently opened tool_use block.
4799
+ */
4800
+ toolCallChunksToBlocks(toolCallChunks) {
4801
+ const blocks = [];
4802
+ for (const tcc of toolCallChunks) {
4803
+ if (tcc.name) {
4804
+ blocks.push({
4805
+ type: "tool_use",
4806
+ id: tcc.id,
4807
+ name: tcc.name,
4808
+ input: ""
4809
+ });
4810
+ }
4811
+ if (typeof tcc.args === "string" && tcc.args.length > 0) {
4812
+ blocks.push({
4813
+ type: "input_json_delta",
4814
+ input: tcc.args
4815
+ });
4816
+ }
4817
+ }
4818
+ return blocks;
4819
+ }
4790
4820
  /**
4791
4821
  * Extract attachments from various input formats
4792
4822
  * Handles both array format (IAttachment[]) and object format (Record<string, IGraphAttachment>)
@@ -4950,10 +4980,19 @@ var EventProcessor = class {
4950
4980
  }
4951
4981
  return;
4952
4982
  }
4953
- if (event.event === "on_chat_model_stream" && event.data?.chunk?.content) {
4983
+ if (event.event === "on_chat_model_stream" && event.data?.chunk) {
4954
4984
  const channel = event.metadata?.stream_channel ?? "text" /* TEXT */;
4955
- const blocks = this.normalizeContentBlocks(event.data.chunk.content);
4956
- this.processContentStream(acc, channel, blocks, onPartial);
4985
+ const chunk = event.data.chunk;
4986
+ const blocks = [];
4987
+ if (chunk.content) {
4988
+ blocks.push(...this.normalizeContentBlocks(chunk.content));
4989
+ }
4990
+ if (Array.isArray(chunk.tool_call_chunks) && chunk.tool_call_chunks.length > 0) {
4991
+ blocks.push(...this.toolCallChunksToBlocks(chunk.tool_call_chunks));
4992
+ }
4993
+ if (blocks.length > 0) {
4994
+ this.processContentStream(acc, channel, blocks, onPartial);
4995
+ }
4957
4996
  return;
4958
4997
  }
4959
4998
  if (event.event === "on_tool_start") {
@@ -4966,6 +5005,44 @@ var EventProcessor = class {
4966
5005
  if (idx !== -1) {
4967
5006
  const block = state.pendingToolBlocks.splice(idx, 1)[0];
4968
5007
  state.toolBlocksByRunId.set(event.run_id, block);
5008
+ } else {
5009
+ const toolInput = event.data?.input;
5010
+ let inputString;
5011
+ try {
5012
+ inputString = typeof toolInput === "string" ? toolInput : JSON.stringify(toolInput ?? {});
5013
+ } catch {
5014
+ inputString = "";
5015
+ }
5016
+ const synthesizedBlock = {
5017
+ index: state.contentChain.length + (state.currentBlock ? 1 : 0),
5018
+ type: "tool_use",
5019
+ name: event.name,
5020
+ id: event.run_id,
5021
+ input: inputString,
5022
+ output: ""
5023
+ };
5024
+ if (state.currentBlock) {
5025
+ state.contentChain.push(state.currentBlock);
5026
+ state.currentBlock = null;
5027
+ }
5028
+ state.contentChain.push(synthesizedBlock);
5029
+ state.toolBlocksByRunId.set(event.run_id, synthesizedBlock);
5030
+ this.sendDelta(
5031
+ channel,
5032
+ { type: "step_started", step: synthesizedBlock },
5033
+ onPartial
5034
+ );
5035
+ if (inputString.length > 0) {
5036
+ this.sendDelta(
5037
+ channel,
5038
+ {
5039
+ type: "tool_input_chunk",
5040
+ stepId: synthesizedBlock.id,
5041
+ chunk: inputString
5042
+ },
5043
+ onPartial
5044
+ );
5045
+ }
4969
5046
  }
4970
5047
  }
4971
5048
  this.logger.log("\u{1F527} Tool execution started", {