@ai-sdk/react 1.1.18 → 1.1.20

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/CHANGELOG.md CHANGED
@@ -1,5 +1,17 @@
1
1
  # @ai-sdk/react
2
2
 
3
+ ## 1.1.20
4
+
5
+ ### Patch Changes
6
+
7
+ - 6255fbc: fix (ai/react): update messages when initialMessages changes
8
+
9
+ ## 1.1.19
10
+
11
+ ### Patch Changes
12
+
13
+ - da5c734: fix (react): infinite re-render caused by fillMessageParts
14
+
3
15
  ## 1.1.18
4
16
 
5
17
  ### Patch Changes
package/dist/index.js CHANGED
@@ -205,8 +205,8 @@ function useAssistant({
205
205
  }
206
206
 
207
207
  // src/use-chat.ts
208
- var import_ui_utils2 = require("@ai-sdk/ui-utils");
209
- var import_react2 = require("react");
208
+ var import_ui_utils3 = require("@ai-sdk/ui-utils");
209
+ var import_react3 = require("react");
210
210
  var import_swr = __toESM(require("swr"));
211
211
 
212
212
  // src/throttle.ts
@@ -215,6 +215,19 @@ function throttle(fn, waitMs) {
215
215
  return waitMs != null ? (0, import_throttleit.default)(fn, waitMs) : fn;
216
216
  }
217
217
 
218
+ // src/util/use-stable-value.ts
219
+ var import_ui_utils2 = require("@ai-sdk/ui-utils");
220
+ var import_react2 = require("react");
221
+ function useStableValue(latestValue) {
222
+ const [value, setValue] = (0, import_react2.useState)(latestValue);
223
+ (0, import_react2.useEffect)(() => {
224
+ if (!(0, import_ui_utils2.isDeepEqualData)(latestValue, value)) {
225
+ setValue(latestValue);
226
+ }
227
+ }, [latestValue, value]);
228
+ return value;
229
+ }
230
+
218
231
  // src/use-chat.ts
219
232
  function useChat({
220
233
  api = "/api/chat",
@@ -232,54 +245,56 @@ function useChat({
232
245
  credentials,
233
246
  headers,
234
247
  body,
235
- generateId: generateId2 = import_ui_utils2.generateId,
248
+ generateId: generateId2 = import_ui_utils3.generateId,
236
249
  fetch: fetch2,
237
250
  keepLastMessageOnError = true,
238
251
  experimental_throttle: throttleWaitMs
239
252
  } = {}) {
240
- const [hookId] = (0, import_react2.useState)(generateId2);
253
+ const [hookId] = (0, import_react3.useState)(generateId2);
241
254
  const chatId = id != null ? id : hookId;
242
255
  const chatKey = typeof api === "string" ? [api, chatId] : chatId;
243
- const [initialMessagesFallback] = (0, import_react2.useState)([]);
256
+ const stableInitialMessages = useStableValue(initialMessages != null ? initialMessages : []);
257
+ const processedInitialMessages = (0, import_react3.useMemo)(
258
+ () => (0, import_ui_utils3.fillMessageParts)(stableInitialMessages),
259
+ [stableInitialMessages]
260
+ );
244
261
  const { data: messages, mutate } = (0, import_swr.default)(
245
262
  [chatKey, "messages"],
246
263
  null,
247
- {
248
- fallbackData: initialMessages != null ? (0, import_ui_utils2.fillMessageParts)(initialMessages) : initialMessagesFallback
249
- }
264
+ { fallbackData: processedInitialMessages }
250
265
  );
251
- const messagesRef = (0, import_react2.useRef)(messages || []);
252
- (0, import_react2.useEffect)(() => {
266
+ const messagesRef = (0, import_react3.useRef)(messages || []);
267
+ (0, import_react3.useEffect)(() => {
253
268
  messagesRef.current = messages || [];
254
269
  }, [messages]);
255
270
  const { data: streamData, mutate: mutateStreamData } = (0, import_swr.default)([chatKey, "streamData"], null);
256
- const streamDataRef = (0, import_react2.useRef)(streamData);
257
- (0, import_react2.useEffect)(() => {
271
+ const streamDataRef = (0, import_react3.useRef)(streamData);
272
+ (0, import_react3.useEffect)(() => {
258
273
  streamDataRef.current = streamData;
259
274
  }, [streamData]);
260
275
  const { data: status = "ready", mutate: mutateStatus } = (0, import_swr.default)([chatKey, "status"], null);
261
276
  const { data: error = void 0, mutate: setError } = (0, import_swr.default)([chatKey, "error"], null);
262
- const abortControllerRef = (0, import_react2.useRef)(null);
263
- const extraMetadataRef = (0, import_react2.useRef)({
277
+ const abortControllerRef = (0, import_react3.useRef)(null);
278
+ const extraMetadataRef = (0, import_react3.useRef)({
264
279
  credentials,
265
280
  headers,
266
281
  body
267
282
  });
268
- (0, import_react2.useEffect)(() => {
283
+ (0, import_react3.useEffect)(() => {
269
284
  extraMetadataRef.current = {
270
285
  credentials,
271
286
  headers,
272
287
  body
273
288
  };
274
289
  }, [credentials, headers, body]);
275
- const triggerRequest = (0, import_react2.useCallback)(
290
+ const triggerRequest = (0, import_react3.useCallback)(
276
291
  async (chatRequest) => {
277
292
  var _a, _b;
278
293
  mutateStatus("submitted");
279
294
  setError(void 0);
280
- const chatMessages = (0, import_ui_utils2.fillMessageParts)(chatRequest.messages);
295
+ const chatMessages = (0, import_ui_utils3.fillMessageParts)(chatRequest.messages);
281
296
  const messageCount = chatMessages.length;
282
- const maxStep = (0, import_ui_utils2.extractMaxToolInvocationStep)(
297
+ const maxStep = (0, import_ui_utils3.extractMaxToolInvocationStep)(
283
298
  (_a = chatMessages[chatMessages.length - 1]) == null ? void 0 : _a.toolInvocations
284
299
  );
285
300
  try {
@@ -314,7 +329,7 @@ function useChat({
314
329
  })
315
330
  );
316
331
  const existingData = streamDataRef.current;
317
- await (0, import_ui_utils2.callChatApi)({
332
+ await (0, import_ui_utils3.callChatApi)({
318
333
  api,
319
334
  body: (_b = experimental_prepareRequestBody == null ? void 0 : experimental_prepareRequestBody({
320
335
  id: chatId,
@@ -378,7 +393,7 @@ function useChat({
378
393
  mutateStatus("error");
379
394
  }
380
395
  const messages2 = messagesRef.current;
381
- if ((0, import_ui_utils2.shouldResubmitMessages)({
396
+ if ((0, import_ui_utils3.shouldResubmitMessages)({
382
397
  originalMaxToolInvocationStep: maxStep,
383
398
  originalMessageCount: messageCount,
384
399
  maxSteps,
@@ -412,7 +427,7 @@ function useChat({
412
427
  chatId
413
428
  ]
414
429
  );
415
- const append = (0, import_react2.useCallback)(
430
+ const append = (0, import_react3.useCallback)(
416
431
  async (message, {
417
432
  data,
418
433
  headers: headers2,
@@ -420,7 +435,7 @@ function useChat({
420
435
  experimental_attachments
421
436
  } = {}) => {
422
437
  var _a, _b;
423
- const attachmentsForRequest = await (0, import_ui_utils2.prepareAttachmentsForRequest)(
438
+ const attachmentsForRequest = await (0, import_ui_utils3.prepareAttachmentsForRequest)(
424
439
  experimental_attachments
425
440
  );
426
441
  const messages2 = messagesRef.current.concat({
@@ -428,13 +443,13 @@ function useChat({
428
443
  id: (_a = message.id) != null ? _a : generateId2(),
429
444
  createdAt: (_b = message.createdAt) != null ? _b : /* @__PURE__ */ new Date(),
430
445
  experimental_attachments: attachmentsForRequest.length > 0 ? attachmentsForRequest : void 0,
431
- parts: (0, import_ui_utils2.getMessageParts)(message)
446
+ parts: (0, import_ui_utils3.getMessageParts)(message)
432
447
  });
433
448
  return triggerRequest({ messages: messages2, headers: headers2, body: body2, data });
434
449
  },
435
450
  [triggerRequest, generateId2]
436
451
  );
437
- const reload = (0, import_react2.useCallback)(
452
+ const reload = (0, import_react3.useCallback)(
438
453
  async ({ data, headers: headers2, body: body2 } = {}) => {
439
454
  const messages2 = messagesRef.current;
440
455
  if (messages2.length === 0) {
@@ -450,24 +465,24 @@ function useChat({
450
465
  },
451
466
  [triggerRequest]
452
467
  );
453
- const stop = (0, import_react2.useCallback)(() => {
468
+ const stop = (0, import_react3.useCallback)(() => {
454
469
  if (abortControllerRef.current) {
455
470
  abortControllerRef.current.abort();
456
471
  abortControllerRef.current = null;
457
472
  }
458
473
  }, []);
459
- const setMessages = (0, import_react2.useCallback)(
474
+ const setMessages = (0, import_react3.useCallback)(
460
475
  (messages2) => {
461
476
  if (typeof messages2 === "function") {
462
477
  messages2 = messages2(messagesRef.current);
463
478
  }
464
- const messagesWithParts = (0, import_ui_utils2.fillMessageParts)(messages2);
479
+ const messagesWithParts = (0, import_ui_utils3.fillMessageParts)(messages2);
465
480
  mutate(messagesWithParts, false);
466
481
  messagesRef.current = messagesWithParts;
467
482
  },
468
483
  [mutate]
469
484
  );
470
- const setData = (0, import_react2.useCallback)(
485
+ const setData = (0, import_react3.useCallback)(
471
486
  (data) => {
472
487
  if (typeof data === "function") {
473
488
  data = data(streamDataRef.current);
@@ -477,8 +492,8 @@ function useChat({
477
492
  },
478
493
  [mutateStreamData]
479
494
  );
480
- const [input, setInput] = (0, import_react2.useState)(initialInput);
481
- const handleSubmit = (0, import_react2.useCallback)(
495
+ const [input, setInput] = (0, import_react3.useState)(initialInput);
496
+ const handleSubmit = (0, import_react3.useCallback)(
482
497
  async (event, options = {}, metadata) => {
483
498
  var _a;
484
499
  (_a = event == null ? void 0 : event.preventDefault) == null ? void 0 : _a.call(event);
@@ -490,7 +505,7 @@ function useChat({
490
505
  ...metadata
491
506
  };
492
507
  }
493
- const attachmentsForRequest = await (0, import_ui_utils2.prepareAttachmentsForRequest)(
508
+ const attachmentsForRequest = await (0, import_ui_utils3.prepareAttachmentsForRequest)(
494
509
  options.experimental_attachments
495
510
  );
496
511
  const messages2 = messagesRef.current.concat({
@@ -515,17 +530,17 @@ function useChat({
515
530
  const handleInputChange = (e) => {
516
531
  setInput(e.target.value);
517
532
  };
518
- const addToolResult = (0, import_react2.useCallback)(
533
+ const addToolResult = (0, import_react3.useCallback)(
519
534
  ({ toolCallId, result }) => {
520
535
  const currentMessages = messagesRef.current;
521
- (0, import_ui_utils2.updateToolCallResult)({
536
+ (0, import_ui_utils3.updateToolCallResult)({
522
537
  messages: currentMessages,
523
538
  toolCallId,
524
539
  toolResult: result
525
540
  });
526
541
  mutate(currentMessages, false);
527
542
  const lastMessage = currentMessages[currentMessages.length - 1];
528
- if ((0, import_ui_utils2.isAssistantMessageWithCompletedToolCalls)(lastMessage)) {
543
+ if ((0, import_ui_utils3.isAssistantMessageWithCompletedToolCalls)(lastMessage)) {
529
544
  triggerRequest({ messages: currentMessages });
530
545
  }
531
546
  },
@@ -552,8 +567,8 @@ function useChat({
552
567
  }
553
568
 
554
569
  // src/use-completion.ts
555
- var import_ui_utils3 = require("@ai-sdk/ui-utils");
556
- var import_react3 = require("react");
570
+ var import_ui_utils4 = require("@ai-sdk/ui-utils");
571
+ var import_react4 = require("react");
557
572
  var import_swr2 = __toESM(require("swr"));
558
573
  function useCompletion({
559
574
  api = "/api/completion",
@@ -570,7 +585,7 @@ function useCompletion({
570
585
  onError,
571
586
  experimental_throttle: throttleWaitMs
572
587
  } = {}) {
573
- const hookId = (0, import_react3.useId)();
588
+ const hookId = (0, import_react4.useId)();
574
589
  const completionId = id || hookId;
575
590
  const { data, mutate } = (0, import_swr2.default)([api, completionId], null, {
576
591
  fallbackData: initialCompletion
@@ -580,23 +595,23 @@ function useCompletion({
580
595
  null
581
596
  );
582
597
  const { data: streamData, mutate: mutateStreamData } = (0, import_swr2.default)([completionId, "streamData"], null);
583
- const [error, setError] = (0, import_react3.useState)(void 0);
598
+ const [error, setError] = (0, import_react4.useState)(void 0);
584
599
  const completion = data;
585
- const [abortController, setAbortController] = (0, import_react3.useState)(null);
586
- const extraMetadataRef = (0, import_react3.useRef)({
600
+ const [abortController, setAbortController] = (0, import_react4.useState)(null);
601
+ const extraMetadataRef = (0, import_react4.useRef)({
587
602
  credentials,
588
603
  headers,
589
604
  body
590
605
  });
591
- (0, import_react3.useEffect)(() => {
606
+ (0, import_react4.useEffect)(() => {
592
607
  extraMetadataRef.current = {
593
608
  credentials,
594
609
  headers,
595
610
  body
596
611
  };
597
612
  }, [credentials, headers, body]);
598
- const triggerRequest = (0, import_react3.useCallback)(
599
- async (prompt, options) => (0, import_ui_utils3.callCompletionApi)({
613
+ const triggerRequest = (0, import_react4.useCallback)(
614
+ async (prompt, options) => (0, import_ui_utils4.callCompletionApi)({
600
615
  api,
601
616
  prompt,
602
617
  credentials: extraMetadataRef.current.credentials,
@@ -640,26 +655,26 @@ function useCompletion({
640
655
  throttleWaitMs
641
656
  ]
642
657
  );
643
- const stop = (0, import_react3.useCallback)(() => {
658
+ const stop = (0, import_react4.useCallback)(() => {
644
659
  if (abortController) {
645
660
  abortController.abort();
646
661
  setAbortController(null);
647
662
  }
648
663
  }, [abortController]);
649
- const setCompletion = (0, import_react3.useCallback)(
664
+ const setCompletion = (0, import_react4.useCallback)(
650
665
  (completion2) => {
651
666
  mutate(completion2, false);
652
667
  },
653
668
  [mutate]
654
669
  );
655
- const complete = (0, import_react3.useCallback)(
670
+ const complete = (0, import_react4.useCallback)(
656
671
  async (prompt, options) => {
657
672
  return triggerRequest(prompt, options);
658
673
  },
659
674
  [triggerRequest]
660
675
  );
661
- const [input, setInput] = (0, import_react3.useState)(initialInput);
662
- const handleSubmit = (0, import_react3.useCallback)(
676
+ const [input, setInput] = (0, import_react4.useState)(initialInput);
677
+ const handleSubmit = (0, import_react4.useCallback)(
663
678
  (event) => {
664
679
  var _a;
665
680
  (_a = event == null ? void 0 : event.preventDefault) == null ? void 0 : _a.call(event);
@@ -667,7 +682,7 @@ function useCompletion({
667
682
  },
668
683
  [input, complete]
669
684
  );
670
- const handleInputChange = (0, import_react3.useCallback)(
685
+ const handleInputChange = (0, import_react4.useCallback)(
671
686
  (e) => {
672
687
  setInput(e.target.value);
673
688
  },
@@ -690,8 +705,8 @@ function useCompletion({
690
705
 
691
706
  // src/use-object.ts
692
707
  var import_provider_utils2 = require("@ai-sdk/provider-utils");
693
- var import_ui_utils4 = require("@ai-sdk/ui-utils");
694
- var import_react4 = require("react");
708
+ var import_ui_utils5 = require("@ai-sdk/ui-utils");
709
+ var import_react5 = require("react");
695
710
  var import_swr3 = __toESM(require("swr"));
696
711
  var getOriginalFetch2 = () => fetch;
697
712
  function useObject({
@@ -705,17 +720,17 @@ function useObject({
705
720
  onFinish,
706
721
  headers
707
722
  }) {
708
- const hookId = (0, import_react4.useId)();
723
+ const hookId = (0, import_react5.useId)();
709
724
  const completionId = id != null ? id : hookId;
710
725
  const { data, mutate } = (0, import_swr3.default)(
711
726
  [api, completionId],
712
727
  null,
713
728
  { fallbackData: initialValue }
714
729
  );
715
- const [error, setError] = (0, import_react4.useState)(void 0);
716
- const [isLoading, setIsLoading] = (0, import_react4.useState)(false);
717
- const abortControllerRef = (0, import_react4.useRef)(null);
718
- const stop = (0, import_react4.useCallback)(() => {
730
+ const [error, setError] = (0, import_react5.useState)(void 0);
731
+ const [isLoading, setIsLoading] = (0, import_react5.useState)(false);
732
+ const abortControllerRef = (0, import_react5.useRef)(null);
733
+ const stop = (0, import_react5.useCallback)(() => {
719
734
  var _a;
720
735
  try {
721
736
  (_a = abortControllerRef.current) == null ? void 0 : _a.abort();
@@ -757,9 +772,9 @@ function useObject({
757
772
  new WritableStream({
758
773
  write(chunk) {
759
774
  accumulatedText += chunk;
760
- const { value } = (0, import_ui_utils4.parsePartialJson)(accumulatedText);
775
+ const { value } = (0, import_ui_utils5.parsePartialJson)(accumulatedText);
761
776
  const currentObject = value;
762
- if (!(0, import_ui_utils4.isDeepEqualData)(latestObject, currentObject)) {
777
+ if (!(0, import_ui_utils5.isDeepEqualData)(latestObject, currentObject)) {
763
778
  latestObject = currentObject;
764
779
  mutate(currentObject);
765
780
  }
@@ -770,7 +785,7 @@ function useObject({
770
785
  if (onFinish != null) {
771
786
  const validationResult = (0, import_provider_utils2.safeValidateTypes)({
772
787
  value: latestObject,
773
- schema: (0, import_ui_utils4.asSchema)(schema)
788
+ schema: (0, import_ui_utils5.asSchema)(schema)
774
789
  });
775
790
  onFinish(
776
791
  validationResult.success ? { object: validationResult.value, error: void 0 } : { object: void 0, error: validationResult.error }
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/index.ts","../src/use-assistant.ts","../src/use-chat.ts","../src/throttle.ts","../src/use-completion.ts","../src/use-object.ts"],"sourcesContent":["export * from './use-assistant';\nexport * from './use-chat';\nexport * from './use-completion';\nexport * from './use-object';\n","import { isAbortError } from '@ai-sdk/provider-utils';\nimport {\n AssistantStatus,\n CreateMessage,\n Message,\n UseAssistantOptions,\n generateId,\n processAssistantStream,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useRef, useState } from 'react';\n\n// use function to allow for mocking in tests:\nconst getOriginalFetch = () => fetch;\n\nexport type UseAssistantHelpers = {\n /**\n * The current array of chat messages.\n */\n messages: Message[];\n\n /**\n * Update the message store with a new array of messages.\n */\n setMessages: React.Dispatch<React.SetStateAction<Message[]>>;\n\n /**\n * The current thread ID.\n */\n threadId: string | undefined;\n\n /**\n * Set the current thread ID. Specifying a thread ID will switch to that thread, if it exists. If set to 'undefined', a new thread will be created. For both cases, `threadId` will be updated with the new value and `messages` will be cleared.\n */\n setThreadId: (threadId: string | undefined) => void;\n\n /**\n * The current value of the input field.\n */\n input: string;\n\n /**\n * Append a user message to the chat list. This triggers the API call to fetch\n * the assistant's response.\n * @param message The message to append\n * @param requestOptions Additional options to pass to the API call\n */\n append: (\n message: Message | CreateMessage,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => Promise<void>;\n\n /**\nAbort the current request immediately, keep the generated tokens if any.\n */\n stop: () => void;\n\n /**\n * setState-powered method to update the input value.\n */\n setInput: React.Dispatch<React.SetStateAction<string>>;\n\n /**\n * Handler for the `onChange` event of the input field to control the input's value.\n */\n handleInputChange: (\n event:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => void;\n\n /**\n * Form submission handler that automatically resets the input field and appends a user message.\n */\n submitMessage: (\n event?: React.FormEvent<HTMLFormElement>,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => Promise<void>;\n\n /**\n * The current status of the assistant. This can be used to show a loading indicator.\n */\n status: AssistantStatus;\n\n /**\n * The error thrown during the assistant message processing, if any.\n */\n error: undefined | Error;\n};\n\nexport function useAssistant({\n api,\n threadId: threadIdParam,\n credentials,\n headers,\n body,\n onError,\n fetch,\n}: UseAssistantOptions): UseAssistantHelpers {\n const [messages, setMessages] = useState<Message[]>([]);\n const [input, setInput] = useState('');\n const [currentThreadId, setCurrentThreadId] = useState<string | undefined>(\n undefined,\n );\n const [status, setStatus] = useState<AssistantStatus>('awaiting_message');\n const [error, setError] = useState<undefined | Error>(undefined);\n\n const handleInputChange = (\n event:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => {\n setInput(event.target.value);\n };\n\n // Abort controller to cancel the current API call.\n const abortControllerRef = useRef<AbortController | null>(null);\n\n const stop = useCallback(() => {\n if (abortControllerRef.current) {\n abortControllerRef.current.abort();\n abortControllerRef.current = null;\n }\n }, []);\n\n const append = async (\n message: Message | CreateMessage,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => {\n setStatus('in_progress');\n\n setMessages(messages => [\n ...messages,\n {\n ...message,\n id: message.id ?? generateId(),\n },\n ]);\n\n setInput('');\n\n const abortController = new AbortController();\n\n try {\n abortControllerRef.current = abortController;\n\n const actualFetch = fetch ?? getOriginalFetch();\n const response = await actualFetch(api, {\n method: 'POST',\n credentials,\n signal: abortController.signal,\n headers: { 'Content-Type': 'application/json', ...headers },\n body: JSON.stringify({\n ...body,\n // always use user-provided threadId when available:\n threadId: threadIdParam ?? currentThreadId ?? null,\n message: message.content,\n\n // optional request data:\n data: requestOptions?.data,\n }),\n });\n\n if (!response.ok) {\n throw new Error(\n (await response.text()) ?? 'Failed to fetch the assistant response.',\n );\n }\n\n if (response.body == null) {\n throw new Error('The response body is empty.');\n }\n\n await processAssistantStream({\n stream: response.body,\n onAssistantMessagePart(value) {\n setMessages(messages => [\n ...messages,\n {\n id: value.id,\n role: value.role,\n content: value.content[0].text.value,\n parts: [],\n },\n ]);\n },\n onTextPart(value) {\n // text delta - add to last message:\n setMessages(messages => {\n const lastMessage = messages[messages.length - 1];\n return [\n ...messages.slice(0, messages.length - 1),\n {\n id: lastMessage.id,\n role: lastMessage.role,\n content: lastMessage.content + value,\n parts: lastMessage.parts,\n },\n ];\n });\n },\n onAssistantControlDataPart(value) {\n setCurrentThreadId(value.threadId);\n\n // set id of last message:\n setMessages(messages => {\n const lastMessage = messages[messages.length - 1];\n lastMessage.id = value.messageId;\n return [...messages.slice(0, messages.length - 1), lastMessage];\n });\n },\n onDataMessagePart(value) {\n setMessages(messages => [\n ...messages,\n {\n id: value.id ?? generateId(),\n role: 'data',\n content: '',\n data: value.data,\n parts: [],\n },\n ]);\n },\n onErrorPart(value) {\n setError(new Error(value));\n },\n });\n } catch (error) {\n // Ignore abort errors as they are expected when the user cancels the request:\n if (isAbortError(error) && abortController.signal.aborted) {\n abortControllerRef.current = null;\n return;\n }\n\n if (onError && error instanceof Error) {\n onError(error);\n }\n\n setError(error as Error);\n } finally {\n abortControllerRef.current = null;\n setStatus('awaiting_message');\n }\n };\n\n const submitMessage = async (\n event?: React.FormEvent<HTMLFormElement>,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => {\n event?.preventDefault?.();\n\n if (input === '') {\n return;\n }\n\n append({ role: 'user', content: input, parts: [] }, requestOptions);\n };\n\n const setThreadId = (threadId: string | undefined) => {\n setCurrentThreadId(threadId);\n setMessages([]);\n };\n\n return {\n append,\n messages,\n setMessages,\n threadId: currentThreadId,\n setThreadId,\n input,\n setInput,\n handleInputChange,\n submitMessage,\n status,\n error,\n stop,\n };\n}\n","import type {\n ChatRequest,\n ChatRequestOptions,\n CreateMessage,\n JSONValue,\n Message,\n UIMessage,\n UseChatOptions,\n} from '@ai-sdk/ui-utils';\nimport {\n callChatApi,\n extractMaxToolInvocationStep,\n fillMessageParts,\n generateId as generateIdFunc,\n getMessageParts,\n isAssistantMessageWithCompletedToolCalls,\n prepareAttachmentsForRequest,\n shouldResubmitMessages,\n updateToolCallResult,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useEffect, useRef, useState } from 'react';\nimport useSWR from 'swr';\nimport { throttle } from './throttle';\n\nexport type { CreateMessage, Message, UseChatOptions };\n\nexport type UseChatHelpers = {\n /** Current messages in the chat */\n messages: UIMessage[];\n /** The error object of the API request */\n error: undefined | Error;\n /**\n * Append a user message to the chat list. This triggers the API call to fetch\n * the assistant's response.\n * @param message The message to append\n * @param options Additional options to pass to the API call\n */\n append: (\n message: Message | CreateMessage,\n chatRequestOptions?: ChatRequestOptions,\n ) => Promise<string | null | undefined>;\n /**\n * Reload the last AI chat response for the given chat history. If the last\n * message isn't from the assistant, it will request the API to generate a\n * new response.\n */\n reload: (\n chatRequestOptions?: ChatRequestOptions,\n ) => Promise<string | null | undefined>;\n /**\n * Abort the current request immediately, keep the generated tokens if any.\n */\n stop: () => void;\n /**\n * Update the `messages` state locally. This is useful when you want to\n * edit the messages on the client, and then trigger the `reload` method\n * manually to regenerate the AI response.\n */\n setMessages: (\n messages: Message[] | ((messages: Message[]) => Message[]),\n ) => void;\n /** The current value of the input */\n input: string;\n /** setState-powered method to update the input value */\n setInput: React.Dispatch<React.SetStateAction<string>>;\n /** An input/textarea-ready onChange handler to control the value of the input */\n handleInputChange: (\n e:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => void;\n /** Form submission handler to automatically reset input and append a user message */\n handleSubmit: (\n event?: { preventDefault?: () => void },\n chatRequestOptions?: ChatRequestOptions,\n ) => void;\n metadata?: Object;\n\n /**\n * Whether the API request is in progress\n *\n * @deprecated use `status` instead\n */\n isLoading: boolean;\n\n /**\n * Hook status:\n *\n * - `submitted`: The message has been sent to the API and we're awaiting the start of the response stream.\n * - `streaming`: The response is actively streaming in from the API, receiving chunks of data.\n * - `ready`: The full response has been received and processed; a new user message can be submitted.\n * - `error`: An error occurred during the API request, preventing successful completion.\n */\n status: 'submitted' | 'streaming' | 'ready' | 'error';\n\n /** Additional data added on the server via StreamData. */\n data?: JSONValue[];\n\n /** Set the data of the chat. You can use this to transform or clear the chat data. */\n setData: (\n data:\n | JSONValue[]\n | undefined\n | ((data: JSONValue[] | undefined) => JSONValue[] | undefined),\n ) => void;\n\n /** The id of the chat */\n id: string;\n};\n\nexport function useChat({\n api = '/api/chat',\n id,\n initialMessages,\n initialInput = '',\n sendExtraMessageFields,\n onToolCall,\n experimental_prepareRequestBody,\n maxSteps = 1,\n streamProtocol = 'data',\n onResponse,\n onFinish,\n onError,\n credentials,\n headers,\n body,\n generateId = generateIdFunc,\n fetch,\n keepLastMessageOnError = true,\n experimental_throttle: throttleWaitMs,\n}: UseChatOptions & {\n key?: string;\n\n /**\n * Experimental (React only). When a function is provided, it will be used\n * to prepare the request body for the chat API. This can be useful for\n * customizing the request body based on the messages and data in the chat.\n *\n * @param messages The current messages in the chat.\n * @param requestData The data object passed in the chat request.\n * @param requestBody The request body object passed in the chat request.\n */\n experimental_prepareRequestBody?: (options: {\n id: string;\n messages: UIMessage[];\n requestData?: JSONValue;\n requestBody?: object;\n }) => unknown;\n\n /**\nCustom throttle wait in ms for the chat messages and data updates.\nDefault is undefined, which disables throttling.\n */\n experimental_throttle?: number;\n\n /**\nMaximum number of sequential LLM calls (steps), e.g. when you use tool calls.\nMust be at least 1.\n\nA maximum number is required to prevent infinite loops in the case of misconfigured tools.\n\nBy default, it's set to 1, which means that only a single LLM call is made.\n */\n maxSteps?: number;\n} = {}): UseChatHelpers & {\n addToolResult: ({\n toolCallId,\n result,\n }: {\n toolCallId: string;\n result: any;\n }) => void;\n} {\n // Generate ID once, store in state for stability across re-renders\n const [hookId] = useState(generateId);\n\n // Use the caller-supplied ID if available; otherwise, fall back to our stable ID\n const chatId = id ?? hookId;\n const chatKey = typeof api === 'string' ? [api, chatId] : chatId;\n\n // Store a empty array as the initial messages\n // (instead of using a default parameter value that gets re-created each time)\n // to avoid re-renders:\n const [initialMessagesFallback] = useState([]);\n\n // Store the chat state in SWR, using the chatId as the key to share states.\n const { data: messages, mutate } = useSWR<UIMessage[]>(\n [chatKey, 'messages'],\n null,\n {\n fallbackData:\n initialMessages != null\n ? fillMessageParts(initialMessages)\n : initialMessagesFallback,\n },\n );\n\n // Keep the latest messages in a ref.\n const messagesRef = useRef<UIMessage[]>(messages || []);\n useEffect(() => {\n messagesRef.current = messages || [];\n }, [messages]);\n\n // stream data\n const { data: streamData, mutate: mutateStreamData } = useSWR<\n JSONValue[] | undefined\n >([chatKey, 'streamData'], null);\n\n // keep the latest stream data in a ref\n const streamDataRef = useRef<JSONValue[] | undefined>(streamData);\n useEffect(() => {\n streamDataRef.current = streamData;\n }, [streamData]);\n\n const { data: status = 'ready', mutate: mutateStatus } = useSWR<\n 'submitted' | 'streaming' | 'ready' | 'error'\n >([chatKey, 'status'], null);\n\n const { data: error = undefined, mutate: setError } = useSWR<\n undefined | Error\n >([chatKey, 'error'], null);\n\n // Abort controller to cancel the current API call.\n const abortControllerRef = useRef<AbortController | null>(null);\n\n const extraMetadataRef = useRef({\n credentials,\n headers,\n body,\n });\n\n useEffect(() => {\n extraMetadataRef.current = {\n credentials,\n headers,\n body,\n };\n }, [credentials, headers, body]);\n\n const triggerRequest = useCallback(\n async (chatRequest: ChatRequest) => {\n mutateStatus('submitted');\n setError(undefined);\n\n const chatMessages = fillMessageParts(chatRequest.messages);\n\n const messageCount = chatMessages.length;\n const maxStep = extractMaxToolInvocationStep(\n chatMessages[chatMessages.length - 1]?.toolInvocations,\n );\n\n try {\n const abortController = new AbortController();\n abortControllerRef.current = abortController;\n\n const throttledMutate = throttle(mutate, throttleWaitMs);\n const throttledMutateStreamData = throttle(\n mutateStreamData,\n throttleWaitMs,\n );\n\n // Do an optimistic update to the chat state to show the updated messages immediately:\n const previousMessages = messagesRef.current;\n throttledMutate(chatMessages, false);\n\n const constructedMessagesPayload = sendExtraMessageFields\n ? chatMessages\n : chatMessages.map(\n ({\n role,\n content,\n experimental_attachments,\n data,\n annotations,\n toolInvocations,\n parts,\n }) => ({\n role,\n content,\n ...(experimental_attachments !== undefined && {\n experimental_attachments,\n }),\n ...(data !== undefined && { data }),\n ...(annotations !== undefined && { annotations }),\n ...(toolInvocations !== undefined && { toolInvocations }),\n ...(parts !== undefined && { parts }),\n }),\n );\n\n const existingData = streamDataRef.current;\n\n await callChatApi({\n api,\n body: experimental_prepareRequestBody?.({\n id: chatId,\n messages: chatMessages,\n requestData: chatRequest.data,\n requestBody: chatRequest.body,\n }) ?? {\n id: chatId,\n messages: constructedMessagesPayload,\n data: chatRequest.data,\n ...extraMetadataRef.current.body,\n ...chatRequest.body,\n },\n streamProtocol,\n credentials: extraMetadataRef.current.credentials,\n headers: {\n ...extraMetadataRef.current.headers,\n ...chatRequest.headers,\n },\n abortController: () => abortControllerRef.current,\n restoreMessagesOnFailure() {\n if (!keepLastMessageOnError) {\n throttledMutate(previousMessages, false);\n }\n },\n onResponse,\n onUpdate({ message, data, replaceLastMessage }) {\n mutateStatus('streaming');\n\n throttledMutate(\n [\n ...(replaceLastMessage\n ? chatMessages.slice(0, chatMessages.length - 1)\n : chatMessages),\n message,\n ],\n false,\n );\n\n if (data?.length) {\n throttledMutateStreamData(\n [...(existingData ?? []), ...data],\n false,\n );\n }\n },\n onToolCall,\n onFinish,\n generateId,\n fetch,\n lastMessage: chatMessages[chatMessages.length - 1],\n });\n\n abortControllerRef.current = null;\n\n mutateStatus('ready');\n } catch (err) {\n // Ignore abort errors as they are expected.\n if ((err as any).name === 'AbortError') {\n abortControllerRef.current = null;\n mutateStatus('ready');\n return null;\n }\n\n if (onError && err instanceof Error) {\n onError(err);\n }\n\n setError(err as Error);\n mutateStatus('error');\n }\n\n // auto-submit when all tool calls in the last assistant message have results\n // and assistant has not answered yet\n const messages = messagesRef.current;\n if (\n shouldResubmitMessages({\n originalMaxToolInvocationStep: maxStep,\n originalMessageCount: messageCount,\n maxSteps,\n messages,\n })\n ) {\n await triggerRequest({ messages });\n }\n },\n [\n mutate,\n mutateStatus,\n api,\n extraMetadataRef,\n onResponse,\n onFinish,\n onError,\n setError,\n mutateStreamData,\n streamDataRef,\n streamProtocol,\n sendExtraMessageFields,\n experimental_prepareRequestBody,\n onToolCall,\n maxSteps,\n messagesRef,\n abortControllerRef,\n generateId,\n fetch,\n keepLastMessageOnError,\n throttleWaitMs,\n chatId,\n ],\n );\n\n const append = useCallback(\n async (\n message: Message | CreateMessage,\n {\n data,\n headers,\n body,\n experimental_attachments,\n }: ChatRequestOptions = {},\n ) => {\n const attachmentsForRequest = await prepareAttachmentsForRequest(\n experimental_attachments,\n );\n\n const messages = messagesRef.current.concat({\n ...message,\n id: message.id ?? generateId(),\n createdAt: message.createdAt ?? new Date(),\n experimental_attachments:\n attachmentsForRequest.length > 0 ? attachmentsForRequest : undefined,\n parts: getMessageParts(message),\n });\n\n return triggerRequest({ messages, headers, body, data });\n },\n [triggerRequest, generateId],\n );\n\n const reload = useCallback(\n async ({ data, headers, body }: ChatRequestOptions = {}) => {\n const messages = messagesRef.current;\n\n if (messages.length === 0) {\n return null;\n }\n\n // Remove last assistant message and retry last user message.\n const lastMessage = messages[messages.length - 1];\n return triggerRequest({\n messages:\n lastMessage.role === 'assistant' ? messages.slice(0, -1) : messages,\n headers,\n body,\n data,\n });\n },\n [triggerRequest],\n );\n\n const stop = useCallback(() => {\n if (abortControllerRef.current) {\n abortControllerRef.current.abort();\n abortControllerRef.current = null;\n }\n }, []);\n\n const setMessages = useCallback(\n (messages: Message[] | ((messages: Message[]) => Message[])) => {\n if (typeof messages === 'function') {\n messages = messages(messagesRef.current);\n }\n\n const messagesWithParts = fillMessageParts(messages);\n mutate(messagesWithParts, false);\n messagesRef.current = messagesWithParts;\n },\n [mutate],\n );\n\n const setData = useCallback(\n (\n data:\n | JSONValue[]\n | undefined\n | ((data: JSONValue[] | undefined) => JSONValue[] | undefined),\n ) => {\n if (typeof data === 'function') {\n data = data(streamDataRef.current);\n }\n\n mutateStreamData(data, false);\n streamDataRef.current = data;\n },\n [mutateStreamData],\n );\n\n // Input state and handlers.\n const [input, setInput] = useState(initialInput);\n\n const handleSubmit = useCallback(\n async (\n event?: { preventDefault?: () => void },\n options: ChatRequestOptions = {},\n metadata?: Object,\n ) => {\n event?.preventDefault?.();\n\n if (!input && !options.allowEmptySubmit) return;\n\n if (metadata) {\n extraMetadataRef.current = {\n ...extraMetadataRef.current,\n ...metadata,\n };\n }\n\n const attachmentsForRequest = await prepareAttachmentsForRequest(\n options.experimental_attachments,\n );\n\n const messages = messagesRef.current.concat({\n id: generateId(),\n createdAt: new Date(),\n role: 'user',\n content: input,\n experimental_attachments:\n attachmentsForRequest.length > 0 ? attachmentsForRequest : undefined,\n parts: [{ type: 'text', text: input }],\n });\n\n const chatRequest: ChatRequest = {\n messages,\n headers: options.headers,\n body: options.body,\n data: options.data,\n };\n\n triggerRequest(chatRequest);\n\n setInput('');\n },\n [input, generateId, triggerRequest],\n );\n\n const handleInputChange = (e: any) => {\n setInput(e.target.value);\n };\n\n const addToolResult = useCallback(\n ({ toolCallId, result }: { toolCallId: string; result: unknown }) => {\n const currentMessages = messagesRef.current;\n\n updateToolCallResult({\n messages: currentMessages,\n toolCallId,\n toolResult: result,\n });\n\n mutate(currentMessages, false);\n\n // auto-submit when all tool calls in the last assistant message have results:\n const lastMessage = currentMessages[currentMessages.length - 1];\n if (isAssistantMessageWithCompletedToolCalls(lastMessage)) {\n triggerRequest({ messages: currentMessages });\n }\n },\n [mutate, triggerRequest],\n );\n\n return {\n messages: messages ?? [],\n id: chatId,\n setMessages,\n data: streamData,\n setData,\n error,\n append,\n reload,\n stop,\n input,\n setInput,\n handleInputChange,\n handleSubmit,\n isLoading: status === 'submitted' || status === 'streaming',\n status,\n addToolResult,\n };\n}\n","import throttleFunction from 'throttleit';\n\nexport function throttle<T extends (...args: any[]) => any>(\n fn: T,\n waitMs: number | undefined,\n): T {\n return waitMs != null ? throttleFunction(fn, waitMs) : fn;\n}\n","import {\n JSONValue,\n RequestOptions,\n UseCompletionOptions,\n callCompletionApi,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useEffect, useId, useRef, useState } from 'react';\nimport useSWR from 'swr';\nimport { throttle } from './throttle';\n\nexport type { UseCompletionOptions };\n\nexport type UseCompletionHelpers = {\n /** The current completion result */\n completion: string;\n /**\n * Send a new prompt to the API endpoint and update the completion state.\n */\n complete: (\n prompt: string,\n options?: RequestOptions,\n ) => Promise<string | null | undefined>;\n /** The error object of the API request */\n error: undefined | Error;\n /**\n * Abort the current API request but keep the generated tokens.\n */\n stop: () => void;\n /**\n * Update the `completion` state locally.\n */\n setCompletion: (completion: string) => void;\n /** The current value of the input */\n input: string;\n /** setState-powered method to update the input value */\n setInput: React.Dispatch<React.SetStateAction<string>>;\n /**\n * An input/textarea-ready onChange handler to control the value of the input\n * @example\n * ```jsx\n * <input onChange={handleInputChange} value={input} />\n * ```\n */\n handleInputChange: (\n event:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => void;\n\n /**\n * Form submission handler to automatically reset input and append a user message\n * @example\n * ```jsx\n * <form onSubmit={handleSubmit}>\n * <input onChange={handleInputChange} value={input} />\n * </form>\n * ```\n */\n handleSubmit: (event?: { preventDefault?: () => void }) => void;\n\n /** Whether the API request is in progress */\n isLoading: boolean;\n /** Additional data added on the server via StreamData */\n data?: JSONValue[];\n};\n\nexport function useCompletion({\n api = '/api/completion',\n id,\n initialCompletion = '',\n initialInput = '',\n credentials,\n headers,\n body,\n streamProtocol = 'data',\n fetch,\n onResponse,\n onFinish,\n onError,\n experimental_throttle: throttleWaitMs,\n}: UseCompletionOptions & {\n /**\n * Custom throttle wait in ms for the completion and data updates.\n * Default is undefined, which disables throttling.\n */\n experimental_throttle?: number;\n} = {}): UseCompletionHelpers {\n // Generate an unique id for the completion if not provided.\n const hookId = useId();\n const completionId = id || hookId;\n\n // Store the completion state in SWR, using the completionId as the key to share states.\n const { data, mutate } = useSWR<string>([api, completionId], null, {\n fallbackData: initialCompletion,\n });\n\n const { data: isLoading = false, mutate: mutateLoading } = useSWR<boolean>(\n [completionId, 'loading'],\n null,\n );\n\n const { data: streamData, mutate: mutateStreamData } = useSWR<\n JSONValue[] | undefined\n >([completionId, 'streamData'], null);\n\n const [error, setError] = useState<undefined | Error>(undefined);\n const completion = data!;\n\n // Abort controller to cancel the current API call.\n const [abortController, setAbortController] =\n useState<AbortController | null>(null);\n\n const extraMetadataRef = useRef({\n credentials,\n headers,\n body,\n });\n\n useEffect(() => {\n extraMetadataRef.current = {\n credentials,\n headers,\n body,\n };\n }, [credentials, headers, body]);\n\n const triggerRequest = useCallback(\n async (prompt: string, options?: RequestOptions) =>\n callCompletionApi({\n api,\n prompt,\n credentials: extraMetadataRef.current.credentials,\n headers: { ...extraMetadataRef.current.headers, ...options?.headers },\n body: {\n ...extraMetadataRef.current.body,\n ...options?.body,\n },\n streamProtocol,\n fetch,\n // throttle streamed ui updates:\n setCompletion: throttle(\n (completion: string) => mutate(completion, false),\n throttleWaitMs,\n ),\n onData: throttle(\n (data: JSONValue[]) =>\n mutateStreamData([...(streamData ?? []), ...(data ?? [])], false),\n throttleWaitMs,\n ),\n setLoading: mutateLoading,\n setError,\n setAbortController,\n onResponse,\n onFinish,\n onError,\n }),\n [\n mutate,\n mutateLoading,\n api,\n extraMetadataRef,\n setAbortController,\n onResponse,\n onFinish,\n onError,\n setError,\n streamData,\n streamProtocol,\n fetch,\n mutateStreamData,\n throttleWaitMs,\n ],\n );\n\n const stop = useCallback(() => {\n if (abortController) {\n abortController.abort();\n setAbortController(null);\n }\n }, [abortController]);\n\n const setCompletion = useCallback(\n (completion: string) => {\n mutate(completion, false);\n },\n [mutate],\n );\n\n const complete = useCallback<UseCompletionHelpers['complete']>(\n async (prompt, options) => {\n return triggerRequest(prompt, options);\n },\n [triggerRequest],\n );\n\n const [input, setInput] = useState(initialInput);\n\n const handleSubmit = useCallback(\n (event?: { preventDefault?: () => void }) => {\n event?.preventDefault?.();\n return input ? complete(input) : undefined;\n },\n [input, complete],\n );\n\n const handleInputChange = useCallback(\n (e: any) => {\n setInput(e.target.value);\n },\n [setInput],\n );\n\n return {\n completion,\n complete,\n error,\n setCompletion,\n stop,\n input,\n setInput,\n handleInputChange,\n handleSubmit,\n isLoading,\n data: streamData,\n };\n}\n","import {\n FetchFunction,\n isAbortError,\n safeValidateTypes,\n} from '@ai-sdk/provider-utils';\nimport {\n asSchema,\n DeepPartial,\n isDeepEqualData,\n parsePartialJson,\n Schema,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useId, useRef, useState } from 'react';\nimport useSWR from 'swr';\nimport z from 'zod';\n\n// use function to allow for mocking in tests:\nconst getOriginalFetch = () => fetch;\n\nexport type Experimental_UseObjectOptions<RESULT> = {\n /**\n * The API endpoint. It should stream JSON that matches the schema as chunked text.\n */\n api: string;\n\n /**\n * A Zod schema that defines the shape of the complete object.\n */\n schema: z.Schema<RESULT, z.ZodTypeDef, any> | Schema<RESULT>;\n\n /**\n * An unique identifier. If not provided, a random one will be\n * generated. When provided, the `useObject` hook with the same `id` will\n * have shared states across components.\n */\n id?: string;\n\n /**\n * An optional value for the initial object.\n */\n initialValue?: DeepPartial<RESULT>;\n\n /**\nCustom fetch implementation. You can use it as a middleware to intercept requests,\nor to provide a custom fetch implementation for e.g. testing.\n */\n fetch?: FetchFunction;\n\n /**\nCallback that is called when the stream has finished.\n */\n onFinish?: (event: {\n /**\nThe generated object (typed according to the schema).\nCan be undefined if the final object does not match the schema.\n */\n object: RESULT | undefined;\n\n /**\nOptional error object. This is e.g. a TypeValidationError when the final object does not match the schema.\n */\n error: Error | undefined;\n }) => Promise<void> | void;\n\n /**\n * Callback function to be called when an error is encountered.\n */\n onError?: (error: Error) => void;\n\n /**\n * Additional HTTP headers to be included in the request.\n */\n headers?: Record<string, string> | Headers;\n};\n\nexport type Experimental_UseObjectHelpers<RESULT, INPUT> = {\n /**\n * Calls the API with the provided input as JSON body.\n */\n submit: (input: INPUT) => void;\n\n /**\n * The current value for the generated object. Updated as the API streams JSON chunks.\n */\n object: DeepPartial<RESULT> | undefined;\n\n /**\n * The error object of the API request if any.\n */\n error: Error | undefined;\n\n /**\n * Flag that indicates whether an API request is in progress.\n */\n isLoading: boolean;\n\n /**\n * Abort the current request immediately, keep the current partial object if any.\n */\n stop: () => void;\n};\n\nfunction useObject<RESULT, INPUT = any>({\n api,\n id,\n schema, // required, in the future we will use it for validation\n initialValue,\n fetch,\n onError,\n onFinish,\n headers,\n}: Experimental_UseObjectOptions<RESULT>): Experimental_UseObjectHelpers<\n RESULT,\n INPUT\n> {\n // Generate an unique id if not provided.\n const hookId = useId();\n const completionId = id ?? hookId;\n\n // Store the completion state in SWR, using the completionId as the key to share states.\n const { data, mutate } = useSWR<DeepPartial<RESULT>>(\n [api, completionId],\n null,\n { fallbackData: initialValue },\n );\n\n const [error, setError] = useState<undefined | Error>(undefined);\n const [isLoading, setIsLoading] = useState(false);\n\n // Abort controller to cancel the current API call.\n const abortControllerRef = useRef<AbortController | null>(null);\n\n const stop = useCallback(() => {\n try {\n abortControllerRef.current?.abort();\n } catch (ignored) {\n } finally {\n setIsLoading(false);\n abortControllerRef.current = null;\n }\n }, []);\n\n const submit = async (input: INPUT) => {\n try {\n mutate(undefined); // reset the data\n setIsLoading(true);\n setError(undefined);\n\n const abortController = new AbortController();\n abortControllerRef.current = abortController;\n\n const actualFetch = fetch ?? getOriginalFetch();\n const response = await actualFetch(api, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n ...headers,\n },\n signal: abortController.signal,\n body: JSON.stringify(input),\n });\n\n if (!response.ok) {\n throw new Error(\n (await response.text()) ?? 'Failed to fetch the response.',\n );\n }\n\n if (response.body == null) {\n throw new Error('The response body is empty.');\n }\n\n let accumulatedText = '';\n let latestObject: DeepPartial<RESULT> | undefined = undefined;\n\n await response.body.pipeThrough(new TextDecoderStream()).pipeTo(\n new WritableStream<string>({\n write(chunk) {\n accumulatedText += chunk;\n\n const { value } = parsePartialJson(accumulatedText);\n const currentObject = value as DeepPartial<RESULT>;\n\n if (!isDeepEqualData(latestObject, currentObject)) {\n latestObject = currentObject;\n\n mutate(currentObject);\n }\n },\n\n close() {\n setIsLoading(false);\n abortControllerRef.current = null;\n\n if (onFinish != null) {\n const validationResult = safeValidateTypes({\n value: latestObject,\n schema: asSchema(schema),\n });\n\n onFinish(\n validationResult.success\n ? { object: validationResult.value, error: undefined }\n : { object: undefined, error: validationResult.error },\n );\n }\n },\n }),\n );\n } catch (error) {\n if (isAbortError(error)) {\n return;\n }\n\n if (onError && error instanceof Error) {\n onError(error);\n }\n\n setIsLoading(false);\n setError(error instanceof Error ? error : new Error(String(error)));\n }\n };\n\n return {\n submit,\n object: data,\n error,\n isLoading,\n stop,\n };\n}\n\nexport const experimental_useObject = useObject;\n"],"mappings":"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","names":["fetch","messages","_a","error","import_ui_utils","import_react","throttleFunction","generateId","generateIdFunc","fetch","useSWR","messages","headers","body","import_ui_utils","import_react","import_swr","fetch","useSWR","completion","data","import_provider_utils","import_ui_utils","import_react","import_swr","getOriginalFetch","fetch","useSWR","error"]}
1
+ {"version":3,"sources":["../src/index.ts","../src/use-assistant.ts","../src/use-chat.ts","../src/throttle.ts","../src/util/use-stable-value.ts","../src/use-completion.ts","../src/use-object.ts"],"sourcesContent":["export * from './use-assistant';\nexport * from './use-chat';\nexport * from './use-completion';\nexport * from './use-object';\n","import { isAbortError } from '@ai-sdk/provider-utils';\nimport {\n AssistantStatus,\n CreateMessage,\n Message,\n UseAssistantOptions,\n generateId,\n processAssistantStream,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useRef, useState } from 'react';\n\n// use function to allow for mocking in tests:\nconst getOriginalFetch = () => fetch;\n\nexport type UseAssistantHelpers = {\n /**\n * The current array of chat messages.\n */\n messages: Message[];\n\n /**\n * Update the message store with a new array of messages.\n */\n setMessages: React.Dispatch<React.SetStateAction<Message[]>>;\n\n /**\n * The current thread ID.\n */\n threadId: string | undefined;\n\n /**\n * Set the current thread ID. Specifying a thread ID will switch to that thread, if it exists. If set to 'undefined', a new thread will be created. For both cases, `threadId` will be updated with the new value and `messages` will be cleared.\n */\n setThreadId: (threadId: string | undefined) => void;\n\n /**\n * The current value of the input field.\n */\n input: string;\n\n /**\n * Append a user message to the chat list. This triggers the API call to fetch\n * the assistant's response.\n * @param message The message to append\n * @param requestOptions Additional options to pass to the API call\n */\n append: (\n message: Message | CreateMessage,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => Promise<void>;\n\n /**\nAbort the current request immediately, keep the generated tokens if any.\n */\n stop: () => void;\n\n /**\n * setState-powered method to update the input value.\n */\n setInput: React.Dispatch<React.SetStateAction<string>>;\n\n /**\n * Handler for the `onChange` event of the input field to control the input's value.\n */\n handleInputChange: (\n event:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => void;\n\n /**\n * Form submission handler that automatically resets the input field and appends a user message.\n */\n submitMessage: (\n event?: React.FormEvent<HTMLFormElement>,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => Promise<void>;\n\n /**\n * The current status of the assistant. This can be used to show a loading indicator.\n */\n status: AssistantStatus;\n\n /**\n * The error thrown during the assistant message processing, if any.\n */\n error: undefined | Error;\n};\n\nexport function useAssistant({\n api,\n threadId: threadIdParam,\n credentials,\n headers,\n body,\n onError,\n fetch,\n}: UseAssistantOptions): UseAssistantHelpers {\n const [messages, setMessages] = useState<Message[]>([]);\n const [input, setInput] = useState('');\n const [currentThreadId, setCurrentThreadId] = useState<string | undefined>(\n undefined,\n );\n const [status, setStatus] = useState<AssistantStatus>('awaiting_message');\n const [error, setError] = useState<undefined | Error>(undefined);\n\n const handleInputChange = (\n event:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => {\n setInput(event.target.value);\n };\n\n // Abort controller to cancel the current API call.\n const abortControllerRef = useRef<AbortController | null>(null);\n\n const stop = useCallback(() => {\n if (abortControllerRef.current) {\n abortControllerRef.current.abort();\n abortControllerRef.current = null;\n }\n }, []);\n\n const append = async (\n message: Message | CreateMessage,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => {\n setStatus('in_progress');\n\n setMessages(messages => [\n ...messages,\n {\n ...message,\n id: message.id ?? generateId(),\n },\n ]);\n\n setInput('');\n\n const abortController = new AbortController();\n\n try {\n abortControllerRef.current = abortController;\n\n const actualFetch = fetch ?? getOriginalFetch();\n const response = await actualFetch(api, {\n method: 'POST',\n credentials,\n signal: abortController.signal,\n headers: { 'Content-Type': 'application/json', ...headers },\n body: JSON.stringify({\n ...body,\n // always use user-provided threadId when available:\n threadId: threadIdParam ?? currentThreadId ?? null,\n message: message.content,\n\n // optional request data:\n data: requestOptions?.data,\n }),\n });\n\n if (!response.ok) {\n throw new Error(\n (await response.text()) ?? 'Failed to fetch the assistant response.',\n );\n }\n\n if (response.body == null) {\n throw new Error('The response body is empty.');\n }\n\n await processAssistantStream({\n stream: response.body,\n onAssistantMessagePart(value) {\n setMessages(messages => [\n ...messages,\n {\n id: value.id,\n role: value.role,\n content: value.content[0].text.value,\n parts: [],\n },\n ]);\n },\n onTextPart(value) {\n // text delta - add to last message:\n setMessages(messages => {\n const lastMessage = messages[messages.length - 1];\n return [\n ...messages.slice(0, messages.length - 1),\n {\n id: lastMessage.id,\n role: lastMessage.role,\n content: lastMessage.content + value,\n parts: lastMessage.parts,\n },\n ];\n });\n },\n onAssistantControlDataPart(value) {\n setCurrentThreadId(value.threadId);\n\n // set id of last message:\n setMessages(messages => {\n const lastMessage = messages[messages.length - 1];\n lastMessage.id = value.messageId;\n return [...messages.slice(0, messages.length - 1), lastMessage];\n });\n },\n onDataMessagePart(value) {\n setMessages(messages => [\n ...messages,\n {\n id: value.id ?? generateId(),\n role: 'data',\n content: '',\n data: value.data,\n parts: [],\n },\n ]);\n },\n onErrorPart(value) {\n setError(new Error(value));\n },\n });\n } catch (error) {\n // Ignore abort errors as they are expected when the user cancels the request:\n if (isAbortError(error) && abortController.signal.aborted) {\n abortControllerRef.current = null;\n return;\n }\n\n if (onError && error instanceof Error) {\n onError(error);\n }\n\n setError(error as Error);\n } finally {\n abortControllerRef.current = null;\n setStatus('awaiting_message');\n }\n };\n\n const submitMessage = async (\n event?: React.FormEvent<HTMLFormElement>,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => {\n event?.preventDefault?.();\n\n if (input === '') {\n return;\n }\n\n append({ role: 'user', content: input, parts: [] }, requestOptions);\n };\n\n const setThreadId = (threadId: string | undefined) => {\n setCurrentThreadId(threadId);\n setMessages([]);\n };\n\n return {\n append,\n messages,\n setMessages,\n threadId: currentThreadId,\n setThreadId,\n input,\n setInput,\n handleInputChange,\n submitMessage,\n status,\n error,\n stop,\n };\n}\n","import type {\n ChatRequest,\n ChatRequestOptions,\n CreateMessage,\n JSONValue,\n Message,\n UIMessage,\n UseChatOptions,\n} from '@ai-sdk/ui-utils';\nimport {\n callChatApi,\n extractMaxToolInvocationStep,\n fillMessageParts,\n generateId as generateIdFunc,\n getMessageParts,\n isAssistantMessageWithCompletedToolCalls,\n prepareAttachmentsForRequest,\n shouldResubmitMessages,\n updateToolCallResult,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useEffect, useMemo, useRef, useState } from 'react';\nimport useSWR from 'swr';\nimport { throttle } from './throttle';\nimport { useStableValue } from './util/use-stable-value';\n\nexport type { CreateMessage, Message, UseChatOptions };\n\nexport type UseChatHelpers = {\n /** Current messages in the chat */\n messages: UIMessage[];\n /** The error object of the API request */\n error: undefined | Error;\n /**\n * Append a user message to the chat list. This triggers the API call to fetch\n * the assistant's response.\n * @param message The message to append\n * @param options Additional options to pass to the API call\n */\n append: (\n message: Message | CreateMessage,\n chatRequestOptions?: ChatRequestOptions,\n ) => Promise<string | null | undefined>;\n /**\n * Reload the last AI chat response for the given chat history. If the last\n * message isn't from the assistant, it will request the API to generate a\n * new response.\n */\n reload: (\n chatRequestOptions?: ChatRequestOptions,\n ) => Promise<string | null | undefined>;\n /**\n * Abort the current request immediately, keep the generated tokens if any.\n */\n stop: () => void;\n /**\n * Update the `messages` state locally. This is useful when you want to\n * edit the messages on the client, and then trigger the `reload` method\n * manually to regenerate the AI response.\n */\n setMessages: (\n messages: Message[] | ((messages: Message[]) => Message[]),\n ) => void;\n /** The current value of the input */\n input: string;\n /** setState-powered method to update the input value */\n setInput: React.Dispatch<React.SetStateAction<string>>;\n /** An input/textarea-ready onChange handler to control the value of the input */\n handleInputChange: (\n e:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => void;\n /** Form submission handler to automatically reset input and append a user message */\n handleSubmit: (\n event?: { preventDefault?: () => void },\n chatRequestOptions?: ChatRequestOptions,\n ) => void;\n metadata?: Object;\n\n /**\n * Whether the API request is in progress\n *\n * @deprecated use `status` instead\n */\n isLoading: boolean;\n\n /**\n * Hook status:\n *\n * - `submitted`: The message has been sent to the API and we're awaiting the start of the response stream.\n * - `streaming`: The response is actively streaming in from the API, receiving chunks of data.\n * - `ready`: The full response has been received and processed; a new user message can be submitted.\n * - `error`: An error occurred during the API request, preventing successful completion.\n */\n status: 'submitted' | 'streaming' | 'ready' | 'error';\n\n /** Additional data added on the server via StreamData. */\n data?: JSONValue[];\n\n /** Set the data of the chat. You can use this to transform or clear the chat data. */\n setData: (\n data:\n | JSONValue[]\n | undefined\n | ((data: JSONValue[] | undefined) => JSONValue[] | undefined),\n ) => void;\n\n /** The id of the chat */\n id: string;\n};\n\nexport function useChat({\n api = '/api/chat',\n id,\n initialMessages,\n initialInput = '',\n sendExtraMessageFields,\n onToolCall,\n experimental_prepareRequestBody,\n maxSteps = 1,\n streamProtocol = 'data',\n onResponse,\n onFinish,\n onError,\n credentials,\n headers,\n body,\n generateId = generateIdFunc,\n fetch,\n keepLastMessageOnError = true,\n experimental_throttle: throttleWaitMs,\n}: UseChatOptions & {\n key?: string;\n\n /**\n * Experimental (React only). When a function is provided, it will be used\n * to prepare the request body for the chat API. This can be useful for\n * customizing the request body based on the messages and data in the chat.\n *\n * @param messages The current messages in the chat.\n * @param requestData The data object passed in the chat request.\n * @param requestBody The request body object passed in the chat request.\n */\n experimental_prepareRequestBody?: (options: {\n id: string;\n messages: UIMessage[];\n requestData?: JSONValue;\n requestBody?: object;\n }) => unknown;\n\n /**\nCustom throttle wait in ms for the chat messages and data updates.\nDefault is undefined, which disables throttling.\n */\n experimental_throttle?: number;\n\n /**\nMaximum number of sequential LLM calls (steps), e.g. when you use tool calls.\nMust be at least 1.\n\nA maximum number is required to prevent infinite loops in the case of misconfigured tools.\n\nBy default, it's set to 1, which means that only a single LLM call is made.\n */\n maxSteps?: number;\n} = {}): UseChatHelpers & {\n addToolResult: ({\n toolCallId,\n result,\n }: {\n toolCallId: string;\n result: any;\n }) => void;\n} {\n // Generate ID once, store in state for stability across re-renders\n const [hookId] = useState(generateId);\n\n // Use the caller-supplied ID if available; otherwise, fall back to our stable ID\n const chatId = id ?? hookId;\n const chatKey = typeof api === 'string' ? [api, chatId] : chatId;\n\n // Store array of the processed initial messages to avoid re-renders:\n const stableInitialMessages = useStableValue(initialMessages ?? []);\n const processedInitialMessages = useMemo(\n () => fillMessageParts(stableInitialMessages),\n [stableInitialMessages],\n );\n\n // Store the chat state in SWR, using the chatId as the key to share states.\n const { data: messages, mutate } = useSWR<UIMessage[]>(\n [chatKey, 'messages'],\n null,\n { fallbackData: processedInitialMessages },\n );\n\n // Keep the latest messages in a ref.\n const messagesRef = useRef<UIMessage[]>(messages || []);\n useEffect(() => {\n messagesRef.current = messages || [];\n }, [messages]);\n\n // stream data\n const { data: streamData, mutate: mutateStreamData } = useSWR<\n JSONValue[] | undefined\n >([chatKey, 'streamData'], null);\n\n // keep the latest stream data in a ref\n const streamDataRef = useRef<JSONValue[] | undefined>(streamData);\n useEffect(() => {\n streamDataRef.current = streamData;\n }, [streamData]);\n\n const { data: status = 'ready', mutate: mutateStatus } = useSWR<\n 'submitted' | 'streaming' | 'ready' | 'error'\n >([chatKey, 'status'], null);\n\n const { data: error = undefined, mutate: setError } = useSWR<\n undefined | Error\n >([chatKey, 'error'], null);\n\n // Abort controller to cancel the current API call.\n const abortControllerRef = useRef<AbortController | null>(null);\n\n const extraMetadataRef = useRef({\n credentials,\n headers,\n body,\n });\n\n useEffect(() => {\n extraMetadataRef.current = {\n credentials,\n headers,\n body,\n };\n }, [credentials, headers, body]);\n\n const triggerRequest = useCallback(\n async (chatRequest: ChatRequest) => {\n mutateStatus('submitted');\n setError(undefined);\n\n const chatMessages = fillMessageParts(chatRequest.messages);\n\n const messageCount = chatMessages.length;\n const maxStep = extractMaxToolInvocationStep(\n chatMessages[chatMessages.length - 1]?.toolInvocations,\n );\n\n try {\n const abortController = new AbortController();\n abortControllerRef.current = abortController;\n\n const throttledMutate = throttle(mutate, throttleWaitMs);\n const throttledMutateStreamData = throttle(\n mutateStreamData,\n throttleWaitMs,\n );\n\n // Do an optimistic update to the chat state to show the updated messages immediately:\n const previousMessages = messagesRef.current;\n throttledMutate(chatMessages, false);\n\n const constructedMessagesPayload = sendExtraMessageFields\n ? chatMessages\n : chatMessages.map(\n ({\n role,\n content,\n experimental_attachments,\n data,\n annotations,\n toolInvocations,\n parts,\n }) => ({\n role,\n content,\n ...(experimental_attachments !== undefined && {\n experimental_attachments,\n }),\n ...(data !== undefined && { data }),\n ...(annotations !== undefined && { annotations }),\n ...(toolInvocations !== undefined && { toolInvocations }),\n ...(parts !== undefined && { parts }),\n }),\n );\n\n const existingData = streamDataRef.current;\n\n await callChatApi({\n api,\n body: experimental_prepareRequestBody?.({\n id: chatId,\n messages: chatMessages,\n requestData: chatRequest.data,\n requestBody: chatRequest.body,\n }) ?? {\n id: chatId,\n messages: constructedMessagesPayload,\n data: chatRequest.data,\n ...extraMetadataRef.current.body,\n ...chatRequest.body,\n },\n streamProtocol,\n credentials: extraMetadataRef.current.credentials,\n headers: {\n ...extraMetadataRef.current.headers,\n ...chatRequest.headers,\n },\n abortController: () => abortControllerRef.current,\n restoreMessagesOnFailure() {\n if (!keepLastMessageOnError) {\n throttledMutate(previousMessages, false);\n }\n },\n onResponse,\n onUpdate({ message, data, replaceLastMessage }) {\n mutateStatus('streaming');\n\n throttledMutate(\n [\n ...(replaceLastMessage\n ? chatMessages.slice(0, chatMessages.length - 1)\n : chatMessages),\n message,\n ],\n false,\n );\n\n if (data?.length) {\n throttledMutateStreamData(\n [...(existingData ?? []), ...data],\n false,\n );\n }\n },\n onToolCall,\n onFinish,\n generateId,\n fetch,\n lastMessage: chatMessages[chatMessages.length - 1],\n });\n\n abortControllerRef.current = null;\n\n mutateStatus('ready');\n } catch (err) {\n // Ignore abort errors as they are expected.\n if ((err as any).name === 'AbortError') {\n abortControllerRef.current = null;\n mutateStatus('ready');\n return null;\n }\n\n if (onError && err instanceof Error) {\n onError(err);\n }\n\n setError(err as Error);\n mutateStatus('error');\n }\n\n // auto-submit when all tool calls in the last assistant message have results\n // and assistant has not answered yet\n const messages = messagesRef.current;\n if (\n shouldResubmitMessages({\n originalMaxToolInvocationStep: maxStep,\n originalMessageCount: messageCount,\n maxSteps,\n messages,\n })\n ) {\n await triggerRequest({ messages });\n }\n },\n [\n mutate,\n mutateStatus,\n api,\n extraMetadataRef,\n onResponse,\n onFinish,\n onError,\n setError,\n mutateStreamData,\n streamDataRef,\n streamProtocol,\n sendExtraMessageFields,\n experimental_prepareRequestBody,\n onToolCall,\n maxSteps,\n messagesRef,\n abortControllerRef,\n generateId,\n fetch,\n keepLastMessageOnError,\n throttleWaitMs,\n chatId,\n ],\n );\n\n const append = useCallback(\n async (\n message: Message | CreateMessage,\n {\n data,\n headers,\n body,\n experimental_attachments,\n }: ChatRequestOptions = {},\n ) => {\n const attachmentsForRequest = await prepareAttachmentsForRequest(\n experimental_attachments,\n );\n\n const messages = messagesRef.current.concat({\n ...message,\n id: message.id ?? generateId(),\n createdAt: message.createdAt ?? new Date(),\n experimental_attachments:\n attachmentsForRequest.length > 0 ? attachmentsForRequest : undefined,\n parts: getMessageParts(message),\n });\n\n return triggerRequest({ messages, headers, body, data });\n },\n [triggerRequest, generateId],\n );\n\n const reload = useCallback(\n async ({ data, headers, body }: ChatRequestOptions = {}) => {\n const messages = messagesRef.current;\n\n if (messages.length === 0) {\n return null;\n }\n\n // Remove last assistant message and retry last user message.\n const lastMessage = messages[messages.length - 1];\n return triggerRequest({\n messages:\n lastMessage.role === 'assistant' ? messages.slice(0, -1) : messages,\n headers,\n body,\n data,\n });\n },\n [triggerRequest],\n );\n\n const stop = useCallback(() => {\n if (abortControllerRef.current) {\n abortControllerRef.current.abort();\n abortControllerRef.current = null;\n }\n }, []);\n\n const setMessages = useCallback(\n (messages: Message[] | ((messages: Message[]) => Message[])) => {\n if (typeof messages === 'function') {\n messages = messages(messagesRef.current);\n }\n\n const messagesWithParts = fillMessageParts(messages);\n mutate(messagesWithParts, false);\n messagesRef.current = messagesWithParts;\n },\n [mutate],\n );\n\n const setData = useCallback(\n (\n data:\n | JSONValue[]\n | undefined\n | ((data: JSONValue[] | undefined) => JSONValue[] | undefined),\n ) => {\n if (typeof data === 'function') {\n data = data(streamDataRef.current);\n }\n\n mutateStreamData(data, false);\n streamDataRef.current = data;\n },\n [mutateStreamData],\n );\n\n // Input state and handlers.\n const [input, setInput] = useState(initialInput);\n\n const handleSubmit = useCallback(\n async (\n event?: { preventDefault?: () => void },\n options: ChatRequestOptions = {},\n metadata?: Object,\n ) => {\n event?.preventDefault?.();\n\n if (!input && !options.allowEmptySubmit) return;\n\n if (metadata) {\n extraMetadataRef.current = {\n ...extraMetadataRef.current,\n ...metadata,\n };\n }\n\n const attachmentsForRequest = await prepareAttachmentsForRequest(\n options.experimental_attachments,\n );\n\n const messages = messagesRef.current.concat({\n id: generateId(),\n createdAt: new Date(),\n role: 'user',\n content: input,\n experimental_attachments:\n attachmentsForRequest.length > 0 ? attachmentsForRequest : undefined,\n parts: [{ type: 'text', text: input }],\n });\n\n const chatRequest: ChatRequest = {\n messages,\n headers: options.headers,\n body: options.body,\n data: options.data,\n };\n\n triggerRequest(chatRequest);\n\n setInput('');\n },\n [input, generateId, triggerRequest],\n );\n\n const handleInputChange = (e: any) => {\n setInput(e.target.value);\n };\n\n const addToolResult = useCallback(\n ({ toolCallId, result }: { toolCallId: string; result: unknown }) => {\n const currentMessages = messagesRef.current;\n\n updateToolCallResult({\n messages: currentMessages,\n toolCallId,\n toolResult: result,\n });\n\n mutate(currentMessages, false);\n\n // auto-submit when all tool calls in the last assistant message have results:\n const lastMessage = currentMessages[currentMessages.length - 1];\n if (isAssistantMessageWithCompletedToolCalls(lastMessage)) {\n triggerRequest({ messages: currentMessages });\n }\n },\n [mutate, triggerRequest],\n );\n\n return {\n messages: messages ?? [],\n id: chatId,\n setMessages,\n data: streamData,\n setData,\n error,\n append,\n reload,\n stop,\n input,\n setInput,\n handleInputChange,\n handleSubmit,\n isLoading: status === 'submitted' || status === 'streaming',\n status,\n addToolResult,\n };\n}\n","import throttleFunction from 'throttleit';\n\nexport function throttle<T extends (...args: any[]) => any>(\n fn: T,\n waitMs: number | undefined,\n): T {\n return waitMs != null ? throttleFunction(fn, waitMs) : fn;\n}\n","import { isDeepEqualData } from '@ai-sdk/ui-utils';\nimport { useEffect, useState } from 'react';\n\n/**\n * Returns a stable value that only updates the stored value (and triggers a re-render)\n * when the value's contents differ by deep-compare.\n */\nexport function useStableValue<T>(latestValue: T): T {\n const [value, setValue] = useState<T>(latestValue);\n\n useEffect(() => {\n if (!isDeepEqualData(latestValue, value)) {\n setValue(latestValue);\n }\n }, [latestValue, value]);\n\n return value;\n}\n","import {\n JSONValue,\n RequestOptions,\n UseCompletionOptions,\n callCompletionApi,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useEffect, useId, useRef, useState } from 'react';\nimport useSWR from 'swr';\nimport { throttle } from './throttle';\n\nexport type { UseCompletionOptions };\n\nexport type UseCompletionHelpers = {\n /** The current completion result */\n completion: string;\n /**\n * Send a new prompt to the API endpoint and update the completion state.\n */\n complete: (\n prompt: string,\n options?: RequestOptions,\n ) => Promise<string | null | undefined>;\n /** The error object of the API request */\n error: undefined | Error;\n /**\n * Abort the current API request but keep the generated tokens.\n */\n stop: () => void;\n /**\n * Update the `completion` state locally.\n */\n setCompletion: (completion: string) => void;\n /** The current value of the input */\n input: string;\n /** setState-powered method to update the input value */\n setInput: React.Dispatch<React.SetStateAction<string>>;\n /**\n * An input/textarea-ready onChange handler to control the value of the input\n * @example\n * ```jsx\n * <input onChange={handleInputChange} value={input} />\n * ```\n */\n handleInputChange: (\n event:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => void;\n\n /**\n * Form submission handler to automatically reset input and append a user message\n * @example\n * ```jsx\n * <form onSubmit={handleSubmit}>\n * <input onChange={handleInputChange} value={input} />\n * </form>\n * ```\n */\n handleSubmit: (event?: { preventDefault?: () => void }) => void;\n\n /** Whether the API request is in progress */\n isLoading: boolean;\n /** Additional data added on the server via StreamData */\n data?: JSONValue[];\n};\n\nexport function useCompletion({\n api = '/api/completion',\n id,\n initialCompletion = '',\n initialInput = '',\n credentials,\n headers,\n body,\n streamProtocol = 'data',\n fetch,\n onResponse,\n onFinish,\n onError,\n experimental_throttle: throttleWaitMs,\n}: UseCompletionOptions & {\n /**\n * Custom throttle wait in ms for the completion and data updates.\n * Default is undefined, which disables throttling.\n */\n experimental_throttle?: number;\n} = {}): UseCompletionHelpers {\n // Generate an unique id for the completion if not provided.\n const hookId = useId();\n const completionId = id || hookId;\n\n // Store the completion state in SWR, using the completionId as the key to share states.\n const { data, mutate } = useSWR<string>([api, completionId], null, {\n fallbackData: initialCompletion,\n });\n\n const { data: isLoading = false, mutate: mutateLoading } = useSWR<boolean>(\n [completionId, 'loading'],\n null,\n );\n\n const { data: streamData, mutate: mutateStreamData } = useSWR<\n JSONValue[] | undefined\n >([completionId, 'streamData'], null);\n\n const [error, setError] = useState<undefined | Error>(undefined);\n const completion = data!;\n\n // Abort controller to cancel the current API call.\n const [abortController, setAbortController] =\n useState<AbortController | null>(null);\n\n const extraMetadataRef = useRef({\n credentials,\n headers,\n body,\n });\n\n useEffect(() => {\n extraMetadataRef.current = {\n credentials,\n headers,\n body,\n };\n }, [credentials, headers, body]);\n\n const triggerRequest = useCallback(\n async (prompt: string, options?: RequestOptions) =>\n callCompletionApi({\n api,\n prompt,\n credentials: extraMetadataRef.current.credentials,\n headers: { ...extraMetadataRef.current.headers, ...options?.headers },\n body: {\n ...extraMetadataRef.current.body,\n ...options?.body,\n },\n streamProtocol,\n fetch,\n // throttle streamed ui updates:\n setCompletion: throttle(\n (completion: string) => mutate(completion, false),\n throttleWaitMs,\n ),\n onData: throttle(\n (data: JSONValue[]) =>\n mutateStreamData([...(streamData ?? []), ...(data ?? [])], false),\n throttleWaitMs,\n ),\n setLoading: mutateLoading,\n setError,\n setAbortController,\n onResponse,\n onFinish,\n onError,\n }),\n [\n mutate,\n mutateLoading,\n api,\n extraMetadataRef,\n setAbortController,\n onResponse,\n onFinish,\n onError,\n setError,\n streamData,\n streamProtocol,\n fetch,\n mutateStreamData,\n throttleWaitMs,\n ],\n );\n\n const stop = useCallback(() => {\n if (abortController) {\n abortController.abort();\n setAbortController(null);\n }\n }, [abortController]);\n\n const setCompletion = useCallback(\n (completion: string) => {\n mutate(completion, false);\n },\n [mutate],\n );\n\n const complete = useCallback<UseCompletionHelpers['complete']>(\n async (prompt, options) => {\n return triggerRequest(prompt, options);\n },\n [triggerRequest],\n );\n\n const [input, setInput] = useState(initialInput);\n\n const handleSubmit = useCallback(\n (event?: { preventDefault?: () => void }) => {\n event?.preventDefault?.();\n return input ? complete(input) : undefined;\n },\n [input, complete],\n );\n\n const handleInputChange = useCallback(\n (e: any) => {\n setInput(e.target.value);\n },\n [setInput],\n );\n\n return {\n completion,\n complete,\n error,\n setCompletion,\n stop,\n input,\n setInput,\n handleInputChange,\n handleSubmit,\n isLoading,\n data: streamData,\n };\n}\n","import {\n FetchFunction,\n isAbortError,\n safeValidateTypes,\n} from '@ai-sdk/provider-utils';\nimport {\n asSchema,\n DeepPartial,\n isDeepEqualData,\n parsePartialJson,\n Schema,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useId, useRef, useState } from 'react';\nimport useSWR from 'swr';\nimport z from 'zod';\n\n// use function to allow for mocking in tests:\nconst getOriginalFetch = () => fetch;\n\nexport type Experimental_UseObjectOptions<RESULT> = {\n /**\n * The API endpoint. It should stream JSON that matches the schema as chunked text.\n */\n api: string;\n\n /**\n * A Zod schema that defines the shape of the complete object.\n */\n schema: z.Schema<RESULT, z.ZodTypeDef, any> | Schema<RESULT>;\n\n /**\n * An unique identifier. If not provided, a random one will be\n * generated. When provided, the `useObject` hook with the same `id` will\n * have shared states across components.\n */\n id?: string;\n\n /**\n * An optional value for the initial object.\n */\n initialValue?: DeepPartial<RESULT>;\n\n /**\nCustom fetch implementation. You can use it as a middleware to intercept requests,\nor to provide a custom fetch implementation for e.g. testing.\n */\n fetch?: FetchFunction;\n\n /**\nCallback that is called when the stream has finished.\n */\n onFinish?: (event: {\n /**\nThe generated object (typed according to the schema).\nCan be undefined if the final object does not match the schema.\n */\n object: RESULT | undefined;\n\n /**\nOptional error object. This is e.g. a TypeValidationError when the final object does not match the schema.\n */\n error: Error | undefined;\n }) => Promise<void> | void;\n\n /**\n * Callback function to be called when an error is encountered.\n */\n onError?: (error: Error) => void;\n\n /**\n * Additional HTTP headers to be included in the request.\n */\n headers?: Record<string, string> | Headers;\n};\n\nexport type Experimental_UseObjectHelpers<RESULT, INPUT> = {\n /**\n * Calls the API with the provided input as JSON body.\n */\n submit: (input: INPUT) => void;\n\n /**\n * The current value for the generated object. Updated as the API streams JSON chunks.\n */\n object: DeepPartial<RESULT> | undefined;\n\n /**\n * The error object of the API request if any.\n */\n error: Error | undefined;\n\n /**\n * Flag that indicates whether an API request is in progress.\n */\n isLoading: boolean;\n\n /**\n * Abort the current request immediately, keep the current partial object if any.\n */\n stop: () => void;\n};\n\nfunction useObject<RESULT, INPUT = any>({\n api,\n id,\n schema, // required, in the future we will use it for validation\n initialValue,\n fetch,\n onError,\n onFinish,\n headers,\n}: Experimental_UseObjectOptions<RESULT>): Experimental_UseObjectHelpers<\n RESULT,\n INPUT\n> {\n // Generate an unique id if not provided.\n const hookId = useId();\n const completionId = id ?? hookId;\n\n // Store the completion state in SWR, using the completionId as the key to share states.\n const { data, mutate } = useSWR<DeepPartial<RESULT>>(\n [api, completionId],\n null,\n { fallbackData: initialValue },\n );\n\n const [error, setError] = useState<undefined | Error>(undefined);\n const [isLoading, setIsLoading] = useState(false);\n\n // Abort controller to cancel the current API call.\n const abortControllerRef = useRef<AbortController | null>(null);\n\n const stop = useCallback(() => {\n try {\n abortControllerRef.current?.abort();\n } catch (ignored) {\n } finally {\n setIsLoading(false);\n abortControllerRef.current = null;\n }\n }, []);\n\n const submit = async (input: INPUT) => {\n try {\n mutate(undefined); // reset the data\n setIsLoading(true);\n setError(undefined);\n\n const abortController = new AbortController();\n abortControllerRef.current = abortController;\n\n const actualFetch = fetch ?? getOriginalFetch();\n const response = await actualFetch(api, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n ...headers,\n },\n signal: abortController.signal,\n body: JSON.stringify(input),\n });\n\n if (!response.ok) {\n throw new Error(\n (await response.text()) ?? 'Failed to fetch the response.',\n );\n }\n\n if (response.body == null) {\n throw new Error('The response body is empty.');\n }\n\n let accumulatedText = '';\n let latestObject: DeepPartial<RESULT> | undefined = undefined;\n\n await response.body.pipeThrough(new TextDecoderStream()).pipeTo(\n new WritableStream<string>({\n write(chunk) {\n accumulatedText += chunk;\n\n const { value } = parsePartialJson(accumulatedText);\n const currentObject = value as DeepPartial<RESULT>;\n\n if (!isDeepEqualData(latestObject, currentObject)) {\n latestObject = currentObject;\n\n mutate(currentObject);\n }\n },\n\n close() {\n setIsLoading(false);\n abortControllerRef.current = null;\n\n if (onFinish != null) {\n const validationResult = safeValidateTypes({\n value: latestObject,\n schema: asSchema(schema),\n });\n\n onFinish(\n validationResult.success\n ? { object: validationResult.value, error: undefined }\n : { object: undefined, error: validationResult.error },\n );\n }\n },\n }),\n );\n } catch (error) {\n if (isAbortError(error)) {\n return;\n }\n\n if (onError && error instanceof Error) {\n onError(error);\n }\n\n setIsLoading(false);\n setError(error instanceof Error ? error : new Error(String(error)));\n }\n };\n\n return {\n submit,\n object: data,\n error,\n isLoading,\n stop,\n };\n}\n\nexport const experimental_useObject = useObject;\n"],"mappings":"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","names":["fetch","messages","_a","error","import_ui_utils","import_react","throttleFunction","import_ui_utils","import_react","generateId","generateIdFunc","fetch","useSWR","messages","headers","body","import_ui_utils","import_react","import_swr","fetch","useSWR","completion","data","import_provider_utils","import_ui_utils","import_react","import_swr","getOriginalFetch","fetch","useSWR","error"]}
package/dist/index.mjs CHANGED
@@ -180,7 +180,7 @@ import {
180
180
  shouldResubmitMessages,
181
181
  updateToolCallResult
182
182
  } from "@ai-sdk/ui-utils";
183
- import { useCallback as useCallback2, useEffect, useRef as useRef2, useState as useState2 } from "react";
183
+ import { useCallback as useCallback2, useEffect as useEffect2, useMemo, useRef as useRef2, useState as useState3 } from "react";
184
184
  import useSWR from "swr";
185
185
 
186
186
  // src/throttle.ts
@@ -189,6 +189,19 @@ function throttle(fn, waitMs) {
189
189
  return waitMs != null ? throttleFunction(fn, waitMs) : fn;
190
190
  }
191
191
 
192
+ // src/util/use-stable-value.ts
193
+ import { isDeepEqualData } from "@ai-sdk/ui-utils";
194
+ import { useEffect, useState as useState2 } from "react";
195
+ function useStableValue(latestValue) {
196
+ const [value, setValue] = useState2(latestValue);
197
+ useEffect(() => {
198
+ if (!isDeepEqualData(latestValue, value)) {
199
+ setValue(latestValue);
200
+ }
201
+ }, [latestValue, value]);
202
+ return value;
203
+ }
204
+
192
205
  // src/use-chat.ts
193
206
  function useChat({
194
207
  api = "/api/chat",
@@ -211,24 +224,26 @@ function useChat({
211
224
  keepLastMessageOnError = true,
212
225
  experimental_throttle: throttleWaitMs
213
226
  } = {}) {
214
- const [hookId] = useState2(generateId2);
227
+ const [hookId] = useState3(generateId2);
215
228
  const chatId = id != null ? id : hookId;
216
229
  const chatKey = typeof api === "string" ? [api, chatId] : chatId;
217
- const [initialMessagesFallback] = useState2([]);
230
+ const stableInitialMessages = useStableValue(initialMessages != null ? initialMessages : []);
231
+ const processedInitialMessages = useMemo(
232
+ () => fillMessageParts(stableInitialMessages),
233
+ [stableInitialMessages]
234
+ );
218
235
  const { data: messages, mutate } = useSWR(
219
236
  [chatKey, "messages"],
220
237
  null,
221
- {
222
- fallbackData: initialMessages != null ? fillMessageParts(initialMessages) : initialMessagesFallback
223
- }
238
+ { fallbackData: processedInitialMessages }
224
239
  );
225
240
  const messagesRef = useRef2(messages || []);
226
- useEffect(() => {
241
+ useEffect2(() => {
227
242
  messagesRef.current = messages || [];
228
243
  }, [messages]);
229
244
  const { data: streamData, mutate: mutateStreamData } = useSWR([chatKey, "streamData"], null);
230
245
  const streamDataRef = useRef2(streamData);
231
- useEffect(() => {
246
+ useEffect2(() => {
232
247
  streamDataRef.current = streamData;
233
248
  }, [streamData]);
234
249
  const { data: status = "ready", mutate: mutateStatus } = useSWR([chatKey, "status"], null);
@@ -239,7 +254,7 @@ function useChat({
239
254
  headers,
240
255
  body
241
256
  });
242
- useEffect(() => {
257
+ useEffect2(() => {
243
258
  extraMetadataRef.current = {
244
259
  credentials,
245
260
  headers,
@@ -451,7 +466,7 @@ function useChat({
451
466
  },
452
467
  [mutateStreamData]
453
468
  );
454
- const [input, setInput] = useState2(initialInput);
469
+ const [input, setInput] = useState3(initialInput);
455
470
  const handleSubmit = useCallback2(
456
471
  async (event, options = {}, metadata) => {
457
472
  var _a;
@@ -529,7 +544,7 @@ function useChat({
529
544
  import {
530
545
  callCompletionApi
531
546
  } from "@ai-sdk/ui-utils";
532
- import { useCallback as useCallback3, useEffect as useEffect2, useId, useRef as useRef3, useState as useState3 } from "react";
547
+ import { useCallback as useCallback3, useEffect as useEffect3, useId, useRef as useRef3, useState as useState4 } from "react";
533
548
  import useSWR2 from "swr";
534
549
  function useCompletion({
535
550
  api = "/api/completion",
@@ -556,15 +571,15 @@ function useCompletion({
556
571
  null
557
572
  );
558
573
  const { data: streamData, mutate: mutateStreamData } = useSWR2([completionId, "streamData"], null);
559
- const [error, setError] = useState3(void 0);
574
+ const [error, setError] = useState4(void 0);
560
575
  const completion = data;
561
- const [abortController, setAbortController] = useState3(null);
576
+ const [abortController, setAbortController] = useState4(null);
562
577
  const extraMetadataRef = useRef3({
563
578
  credentials,
564
579
  headers,
565
580
  body
566
581
  });
567
- useEffect2(() => {
582
+ useEffect3(() => {
568
583
  extraMetadataRef.current = {
569
584
  credentials,
570
585
  headers,
@@ -634,7 +649,7 @@ function useCompletion({
634
649
  },
635
650
  [triggerRequest]
636
651
  );
637
- const [input, setInput] = useState3(initialInput);
652
+ const [input, setInput] = useState4(initialInput);
638
653
  const handleSubmit = useCallback3(
639
654
  (event) => {
640
655
  var _a;
@@ -671,10 +686,10 @@ import {
671
686
  } from "@ai-sdk/provider-utils";
672
687
  import {
673
688
  asSchema,
674
- isDeepEqualData,
689
+ isDeepEqualData as isDeepEqualData2,
675
690
  parsePartialJson
676
691
  } from "@ai-sdk/ui-utils";
677
- import { useCallback as useCallback4, useId as useId2, useRef as useRef4, useState as useState4 } from "react";
692
+ import { useCallback as useCallback4, useId as useId2, useRef as useRef4, useState as useState5 } from "react";
678
693
  import useSWR3 from "swr";
679
694
  var getOriginalFetch2 = () => fetch;
680
695
  function useObject({
@@ -695,8 +710,8 @@ function useObject({
695
710
  null,
696
711
  { fallbackData: initialValue }
697
712
  );
698
- const [error, setError] = useState4(void 0);
699
- const [isLoading, setIsLoading] = useState4(false);
713
+ const [error, setError] = useState5(void 0);
714
+ const [isLoading, setIsLoading] = useState5(false);
700
715
  const abortControllerRef = useRef4(null);
701
716
  const stop = useCallback4(() => {
702
717
  var _a;
@@ -742,7 +757,7 @@ function useObject({
742
757
  accumulatedText += chunk;
743
758
  const { value } = parsePartialJson(accumulatedText);
744
759
  const currentObject = value;
745
- if (!isDeepEqualData(latestObject, currentObject)) {
760
+ if (!isDeepEqualData2(latestObject, currentObject)) {
746
761
  latestObject = currentObject;
747
762
  mutate(currentObject);
748
763
  }
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/use-assistant.ts","../src/use-chat.ts","../src/throttle.ts","../src/use-completion.ts","../src/use-object.ts"],"sourcesContent":["import { isAbortError } from '@ai-sdk/provider-utils';\nimport {\n AssistantStatus,\n CreateMessage,\n Message,\n UseAssistantOptions,\n generateId,\n processAssistantStream,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useRef, useState } from 'react';\n\n// use function to allow for mocking in tests:\nconst getOriginalFetch = () => fetch;\n\nexport type UseAssistantHelpers = {\n /**\n * The current array of chat messages.\n */\n messages: Message[];\n\n /**\n * Update the message store with a new array of messages.\n */\n setMessages: React.Dispatch<React.SetStateAction<Message[]>>;\n\n /**\n * The current thread ID.\n */\n threadId: string | undefined;\n\n /**\n * Set the current thread ID. Specifying a thread ID will switch to that thread, if it exists. If set to 'undefined', a new thread will be created. For both cases, `threadId` will be updated with the new value and `messages` will be cleared.\n */\n setThreadId: (threadId: string | undefined) => void;\n\n /**\n * The current value of the input field.\n */\n input: string;\n\n /**\n * Append a user message to the chat list. This triggers the API call to fetch\n * the assistant's response.\n * @param message The message to append\n * @param requestOptions Additional options to pass to the API call\n */\n append: (\n message: Message | CreateMessage,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => Promise<void>;\n\n /**\nAbort the current request immediately, keep the generated tokens if any.\n */\n stop: () => void;\n\n /**\n * setState-powered method to update the input value.\n */\n setInput: React.Dispatch<React.SetStateAction<string>>;\n\n /**\n * Handler for the `onChange` event of the input field to control the input's value.\n */\n handleInputChange: (\n event:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => void;\n\n /**\n * Form submission handler that automatically resets the input field and appends a user message.\n */\n submitMessage: (\n event?: React.FormEvent<HTMLFormElement>,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => Promise<void>;\n\n /**\n * The current status of the assistant. This can be used to show a loading indicator.\n */\n status: AssistantStatus;\n\n /**\n * The error thrown during the assistant message processing, if any.\n */\n error: undefined | Error;\n};\n\nexport function useAssistant({\n api,\n threadId: threadIdParam,\n credentials,\n headers,\n body,\n onError,\n fetch,\n}: UseAssistantOptions): UseAssistantHelpers {\n const [messages, setMessages] = useState<Message[]>([]);\n const [input, setInput] = useState('');\n const [currentThreadId, setCurrentThreadId] = useState<string | undefined>(\n undefined,\n );\n const [status, setStatus] = useState<AssistantStatus>('awaiting_message');\n const [error, setError] = useState<undefined | Error>(undefined);\n\n const handleInputChange = (\n event:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => {\n setInput(event.target.value);\n };\n\n // Abort controller to cancel the current API call.\n const abortControllerRef = useRef<AbortController | null>(null);\n\n const stop = useCallback(() => {\n if (abortControllerRef.current) {\n abortControllerRef.current.abort();\n abortControllerRef.current = null;\n }\n }, []);\n\n const append = async (\n message: Message | CreateMessage,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => {\n setStatus('in_progress');\n\n setMessages(messages => [\n ...messages,\n {\n ...message,\n id: message.id ?? generateId(),\n },\n ]);\n\n setInput('');\n\n const abortController = new AbortController();\n\n try {\n abortControllerRef.current = abortController;\n\n const actualFetch = fetch ?? getOriginalFetch();\n const response = await actualFetch(api, {\n method: 'POST',\n credentials,\n signal: abortController.signal,\n headers: { 'Content-Type': 'application/json', ...headers },\n body: JSON.stringify({\n ...body,\n // always use user-provided threadId when available:\n threadId: threadIdParam ?? currentThreadId ?? null,\n message: message.content,\n\n // optional request data:\n data: requestOptions?.data,\n }),\n });\n\n if (!response.ok) {\n throw new Error(\n (await response.text()) ?? 'Failed to fetch the assistant response.',\n );\n }\n\n if (response.body == null) {\n throw new Error('The response body is empty.');\n }\n\n await processAssistantStream({\n stream: response.body,\n onAssistantMessagePart(value) {\n setMessages(messages => [\n ...messages,\n {\n id: value.id,\n role: value.role,\n content: value.content[0].text.value,\n parts: [],\n },\n ]);\n },\n onTextPart(value) {\n // text delta - add to last message:\n setMessages(messages => {\n const lastMessage = messages[messages.length - 1];\n return [\n ...messages.slice(0, messages.length - 1),\n {\n id: lastMessage.id,\n role: lastMessage.role,\n content: lastMessage.content + value,\n parts: lastMessage.parts,\n },\n ];\n });\n },\n onAssistantControlDataPart(value) {\n setCurrentThreadId(value.threadId);\n\n // set id of last message:\n setMessages(messages => {\n const lastMessage = messages[messages.length - 1];\n lastMessage.id = value.messageId;\n return [...messages.slice(0, messages.length - 1), lastMessage];\n });\n },\n onDataMessagePart(value) {\n setMessages(messages => [\n ...messages,\n {\n id: value.id ?? generateId(),\n role: 'data',\n content: '',\n data: value.data,\n parts: [],\n },\n ]);\n },\n onErrorPart(value) {\n setError(new Error(value));\n },\n });\n } catch (error) {\n // Ignore abort errors as they are expected when the user cancels the request:\n if (isAbortError(error) && abortController.signal.aborted) {\n abortControllerRef.current = null;\n return;\n }\n\n if (onError && error instanceof Error) {\n onError(error);\n }\n\n setError(error as Error);\n } finally {\n abortControllerRef.current = null;\n setStatus('awaiting_message');\n }\n };\n\n const submitMessage = async (\n event?: React.FormEvent<HTMLFormElement>,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => {\n event?.preventDefault?.();\n\n if (input === '') {\n return;\n }\n\n append({ role: 'user', content: input, parts: [] }, requestOptions);\n };\n\n const setThreadId = (threadId: string | undefined) => {\n setCurrentThreadId(threadId);\n setMessages([]);\n };\n\n return {\n append,\n messages,\n setMessages,\n threadId: currentThreadId,\n setThreadId,\n input,\n setInput,\n handleInputChange,\n submitMessage,\n status,\n error,\n stop,\n };\n}\n","import type {\n ChatRequest,\n ChatRequestOptions,\n CreateMessage,\n JSONValue,\n Message,\n UIMessage,\n UseChatOptions,\n} from '@ai-sdk/ui-utils';\nimport {\n callChatApi,\n extractMaxToolInvocationStep,\n fillMessageParts,\n generateId as generateIdFunc,\n getMessageParts,\n isAssistantMessageWithCompletedToolCalls,\n prepareAttachmentsForRequest,\n shouldResubmitMessages,\n updateToolCallResult,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useEffect, useRef, useState } from 'react';\nimport useSWR from 'swr';\nimport { throttle } from './throttle';\n\nexport type { CreateMessage, Message, UseChatOptions };\n\nexport type UseChatHelpers = {\n /** Current messages in the chat */\n messages: UIMessage[];\n /** The error object of the API request */\n error: undefined | Error;\n /**\n * Append a user message to the chat list. This triggers the API call to fetch\n * the assistant's response.\n * @param message The message to append\n * @param options Additional options to pass to the API call\n */\n append: (\n message: Message | CreateMessage,\n chatRequestOptions?: ChatRequestOptions,\n ) => Promise<string | null | undefined>;\n /**\n * Reload the last AI chat response for the given chat history. If the last\n * message isn't from the assistant, it will request the API to generate a\n * new response.\n */\n reload: (\n chatRequestOptions?: ChatRequestOptions,\n ) => Promise<string | null | undefined>;\n /**\n * Abort the current request immediately, keep the generated tokens if any.\n */\n stop: () => void;\n /**\n * Update the `messages` state locally. This is useful when you want to\n * edit the messages on the client, and then trigger the `reload` method\n * manually to regenerate the AI response.\n */\n setMessages: (\n messages: Message[] | ((messages: Message[]) => Message[]),\n ) => void;\n /** The current value of the input */\n input: string;\n /** setState-powered method to update the input value */\n setInput: React.Dispatch<React.SetStateAction<string>>;\n /** An input/textarea-ready onChange handler to control the value of the input */\n handleInputChange: (\n e:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => void;\n /** Form submission handler to automatically reset input and append a user message */\n handleSubmit: (\n event?: { preventDefault?: () => void },\n chatRequestOptions?: ChatRequestOptions,\n ) => void;\n metadata?: Object;\n\n /**\n * Whether the API request is in progress\n *\n * @deprecated use `status` instead\n */\n isLoading: boolean;\n\n /**\n * Hook status:\n *\n * - `submitted`: The message has been sent to the API and we're awaiting the start of the response stream.\n * - `streaming`: The response is actively streaming in from the API, receiving chunks of data.\n * - `ready`: The full response has been received and processed; a new user message can be submitted.\n * - `error`: An error occurred during the API request, preventing successful completion.\n */\n status: 'submitted' | 'streaming' | 'ready' | 'error';\n\n /** Additional data added on the server via StreamData. */\n data?: JSONValue[];\n\n /** Set the data of the chat. You can use this to transform or clear the chat data. */\n setData: (\n data:\n | JSONValue[]\n | undefined\n | ((data: JSONValue[] | undefined) => JSONValue[] | undefined),\n ) => void;\n\n /** The id of the chat */\n id: string;\n};\n\nexport function useChat({\n api = '/api/chat',\n id,\n initialMessages,\n initialInput = '',\n sendExtraMessageFields,\n onToolCall,\n experimental_prepareRequestBody,\n maxSteps = 1,\n streamProtocol = 'data',\n onResponse,\n onFinish,\n onError,\n credentials,\n headers,\n body,\n generateId = generateIdFunc,\n fetch,\n keepLastMessageOnError = true,\n experimental_throttle: throttleWaitMs,\n}: UseChatOptions & {\n key?: string;\n\n /**\n * Experimental (React only). When a function is provided, it will be used\n * to prepare the request body for the chat API. This can be useful for\n * customizing the request body based on the messages and data in the chat.\n *\n * @param messages The current messages in the chat.\n * @param requestData The data object passed in the chat request.\n * @param requestBody The request body object passed in the chat request.\n */\n experimental_prepareRequestBody?: (options: {\n id: string;\n messages: UIMessage[];\n requestData?: JSONValue;\n requestBody?: object;\n }) => unknown;\n\n /**\nCustom throttle wait in ms for the chat messages and data updates.\nDefault is undefined, which disables throttling.\n */\n experimental_throttle?: number;\n\n /**\nMaximum number of sequential LLM calls (steps), e.g. when you use tool calls.\nMust be at least 1.\n\nA maximum number is required to prevent infinite loops in the case of misconfigured tools.\n\nBy default, it's set to 1, which means that only a single LLM call is made.\n */\n maxSteps?: number;\n} = {}): UseChatHelpers & {\n addToolResult: ({\n toolCallId,\n result,\n }: {\n toolCallId: string;\n result: any;\n }) => void;\n} {\n // Generate ID once, store in state for stability across re-renders\n const [hookId] = useState(generateId);\n\n // Use the caller-supplied ID if available; otherwise, fall back to our stable ID\n const chatId = id ?? hookId;\n const chatKey = typeof api === 'string' ? [api, chatId] : chatId;\n\n // Store a empty array as the initial messages\n // (instead of using a default parameter value that gets re-created each time)\n // to avoid re-renders:\n const [initialMessagesFallback] = useState([]);\n\n // Store the chat state in SWR, using the chatId as the key to share states.\n const { data: messages, mutate } = useSWR<UIMessage[]>(\n [chatKey, 'messages'],\n null,\n {\n fallbackData:\n initialMessages != null\n ? fillMessageParts(initialMessages)\n : initialMessagesFallback,\n },\n );\n\n // Keep the latest messages in a ref.\n const messagesRef = useRef<UIMessage[]>(messages || []);\n useEffect(() => {\n messagesRef.current = messages || [];\n }, [messages]);\n\n // stream data\n const { data: streamData, mutate: mutateStreamData } = useSWR<\n JSONValue[] | undefined\n >([chatKey, 'streamData'], null);\n\n // keep the latest stream data in a ref\n const streamDataRef = useRef<JSONValue[] | undefined>(streamData);\n useEffect(() => {\n streamDataRef.current = streamData;\n }, [streamData]);\n\n const { data: status = 'ready', mutate: mutateStatus } = useSWR<\n 'submitted' | 'streaming' | 'ready' | 'error'\n >([chatKey, 'status'], null);\n\n const { data: error = undefined, mutate: setError } = useSWR<\n undefined | Error\n >([chatKey, 'error'], null);\n\n // Abort controller to cancel the current API call.\n const abortControllerRef = useRef<AbortController | null>(null);\n\n const extraMetadataRef = useRef({\n credentials,\n headers,\n body,\n });\n\n useEffect(() => {\n extraMetadataRef.current = {\n credentials,\n headers,\n body,\n };\n }, [credentials, headers, body]);\n\n const triggerRequest = useCallback(\n async (chatRequest: ChatRequest) => {\n mutateStatus('submitted');\n setError(undefined);\n\n const chatMessages = fillMessageParts(chatRequest.messages);\n\n const messageCount = chatMessages.length;\n const maxStep = extractMaxToolInvocationStep(\n chatMessages[chatMessages.length - 1]?.toolInvocations,\n );\n\n try {\n const abortController = new AbortController();\n abortControllerRef.current = abortController;\n\n const throttledMutate = throttle(mutate, throttleWaitMs);\n const throttledMutateStreamData = throttle(\n mutateStreamData,\n throttleWaitMs,\n );\n\n // Do an optimistic update to the chat state to show the updated messages immediately:\n const previousMessages = messagesRef.current;\n throttledMutate(chatMessages, false);\n\n const constructedMessagesPayload = sendExtraMessageFields\n ? chatMessages\n : chatMessages.map(\n ({\n role,\n content,\n experimental_attachments,\n data,\n annotations,\n toolInvocations,\n parts,\n }) => ({\n role,\n content,\n ...(experimental_attachments !== undefined && {\n experimental_attachments,\n }),\n ...(data !== undefined && { data }),\n ...(annotations !== undefined && { annotations }),\n ...(toolInvocations !== undefined && { toolInvocations }),\n ...(parts !== undefined && { parts }),\n }),\n );\n\n const existingData = streamDataRef.current;\n\n await callChatApi({\n api,\n body: experimental_prepareRequestBody?.({\n id: chatId,\n messages: chatMessages,\n requestData: chatRequest.data,\n requestBody: chatRequest.body,\n }) ?? {\n id: chatId,\n messages: constructedMessagesPayload,\n data: chatRequest.data,\n ...extraMetadataRef.current.body,\n ...chatRequest.body,\n },\n streamProtocol,\n credentials: extraMetadataRef.current.credentials,\n headers: {\n ...extraMetadataRef.current.headers,\n ...chatRequest.headers,\n },\n abortController: () => abortControllerRef.current,\n restoreMessagesOnFailure() {\n if (!keepLastMessageOnError) {\n throttledMutate(previousMessages, false);\n }\n },\n onResponse,\n onUpdate({ message, data, replaceLastMessage }) {\n mutateStatus('streaming');\n\n throttledMutate(\n [\n ...(replaceLastMessage\n ? chatMessages.slice(0, chatMessages.length - 1)\n : chatMessages),\n message,\n ],\n false,\n );\n\n if (data?.length) {\n throttledMutateStreamData(\n [...(existingData ?? []), ...data],\n false,\n );\n }\n },\n onToolCall,\n onFinish,\n generateId,\n fetch,\n lastMessage: chatMessages[chatMessages.length - 1],\n });\n\n abortControllerRef.current = null;\n\n mutateStatus('ready');\n } catch (err) {\n // Ignore abort errors as they are expected.\n if ((err as any).name === 'AbortError') {\n abortControllerRef.current = null;\n mutateStatus('ready');\n return null;\n }\n\n if (onError && err instanceof Error) {\n onError(err);\n }\n\n setError(err as Error);\n mutateStatus('error');\n }\n\n // auto-submit when all tool calls in the last assistant message have results\n // and assistant has not answered yet\n const messages = messagesRef.current;\n if (\n shouldResubmitMessages({\n originalMaxToolInvocationStep: maxStep,\n originalMessageCount: messageCount,\n maxSteps,\n messages,\n })\n ) {\n await triggerRequest({ messages });\n }\n },\n [\n mutate,\n mutateStatus,\n api,\n extraMetadataRef,\n onResponse,\n onFinish,\n onError,\n setError,\n mutateStreamData,\n streamDataRef,\n streamProtocol,\n sendExtraMessageFields,\n experimental_prepareRequestBody,\n onToolCall,\n maxSteps,\n messagesRef,\n abortControllerRef,\n generateId,\n fetch,\n keepLastMessageOnError,\n throttleWaitMs,\n chatId,\n ],\n );\n\n const append = useCallback(\n async (\n message: Message | CreateMessage,\n {\n data,\n headers,\n body,\n experimental_attachments,\n }: ChatRequestOptions = {},\n ) => {\n const attachmentsForRequest = await prepareAttachmentsForRequest(\n experimental_attachments,\n );\n\n const messages = messagesRef.current.concat({\n ...message,\n id: message.id ?? generateId(),\n createdAt: message.createdAt ?? new Date(),\n experimental_attachments:\n attachmentsForRequest.length > 0 ? attachmentsForRequest : undefined,\n parts: getMessageParts(message),\n });\n\n return triggerRequest({ messages, headers, body, data });\n },\n [triggerRequest, generateId],\n );\n\n const reload = useCallback(\n async ({ data, headers, body }: ChatRequestOptions = {}) => {\n const messages = messagesRef.current;\n\n if (messages.length === 0) {\n return null;\n }\n\n // Remove last assistant message and retry last user message.\n const lastMessage = messages[messages.length - 1];\n return triggerRequest({\n messages:\n lastMessage.role === 'assistant' ? messages.slice(0, -1) : messages,\n headers,\n body,\n data,\n });\n },\n [triggerRequest],\n );\n\n const stop = useCallback(() => {\n if (abortControllerRef.current) {\n abortControllerRef.current.abort();\n abortControllerRef.current = null;\n }\n }, []);\n\n const setMessages = useCallback(\n (messages: Message[] | ((messages: Message[]) => Message[])) => {\n if (typeof messages === 'function') {\n messages = messages(messagesRef.current);\n }\n\n const messagesWithParts = fillMessageParts(messages);\n mutate(messagesWithParts, false);\n messagesRef.current = messagesWithParts;\n },\n [mutate],\n );\n\n const setData = useCallback(\n (\n data:\n | JSONValue[]\n | undefined\n | ((data: JSONValue[] | undefined) => JSONValue[] | undefined),\n ) => {\n if (typeof data === 'function') {\n data = data(streamDataRef.current);\n }\n\n mutateStreamData(data, false);\n streamDataRef.current = data;\n },\n [mutateStreamData],\n );\n\n // Input state and handlers.\n const [input, setInput] = useState(initialInput);\n\n const handleSubmit = useCallback(\n async (\n event?: { preventDefault?: () => void },\n options: ChatRequestOptions = {},\n metadata?: Object,\n ) => {\n event?.preventDefault?.();\n\n if (!input && !options.allowEmptySubmit) return;\n\n if (metadata) {\n extraMetadataRef.current = {\n ...extraMetadataRef.current,\n ...metadata,\n };\n }\n\n const attachmentsForRequest = await prepareAttachmentsForRequest(\n options.experimental_attachments,\n );\n\n const messages = messagesRef.current.concat({\n id: generateId(),\n createdAt: new Date(),\n role: 'user',\n content: input,\n experimental_attachments:\n attachmentsForRequest.length > 0 ? attachmentsForRequest : undefined,\n parts: [{ type: 'text', text: input }],\n });\n\n const chatRequest: ChatRequest = {\n messages,\n headers: options.headers,\n body: options.body,\n data: options.data,\n };\n\n triggerRequest(chatRequest);\n\n setInput('');\n },\n [input, generateId, triggerRequest],\n );\n\n const handleInputChange = (e: any) => {\n setInput(e.target.value);\n };\n\n const addToolResult = useCallback(\n ({ toolCallId, result }: { toolCallId: string; result: unknown }) => {\n const currentMessages = messagesRef.current;\n\n updateToolCallResult({\n messages: currentMessages,\n toolCallId,\n toolResult: result,\n });\n\n mutate(currentMessages, false);\n\n // auto-submit when all tool calls in the last assistant message have results:\n const lastMessage = currentMessages[currentMessages.length - 1];\n if (isAssistantMessageWithCompletedToolCalls(lastMessage)) {\n triggerRequest({ messages: currentMessages });\n }\n },\n [mutate, triggerRequest],\n );\n\n return {\n messages: messages ?? [],\n id: chatId,\n setMessages,\n data: streamData,\n setData,\n error,\n append,\n reload,\n stop,\n input,\n setInput,\n handleInputChange,\n handleSubmit,\n isLoading: status === 'submitted' || status === 'streaming',\n status,\n addToolResult,\n };\n}\n","import throttleFunction from 'throttleit';\n\nexport function throttle<T extends (...args: any[]) => any>(\n fn: T,\n waitMs: number | undefined,\n): T {\n return waitMs != null ? throttleFunction(fn, waitMs) : fn;\n}\n","import {\n JSONValue,\n RequestOptions,\n UseCompletionOptions,\n callCompletionApi,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useEffect, useId, useRef, useState } from 'react';\nimport useSWR from 'swr';\nimport { throttle } from './throttle';\n\nexport type { UseCompletionOptions };\n\nexport type UseCompletionHelpers = {\n /** The current completion result */\n completion: string;\n /**\n * Send a new prompt to the API endpoint and update the completion state.\n */\n complete: (\n prompt: string,\n options?: RequestOptions,\n ) => Promise<string | null | undefined>;\n /** The error object of the API request */\n error: undefined | Error;\n /**\n * Abort the current API request but keep the generated tokens.\n */\n stop: () => void;\n /**\n * Update the `completion` state locally.\n */\n setCompletion: (completion: string) => void;\n /** The current value of the input */\n input: string;\n /** setState-powered method to update the input value */\n setInput: React.Dispatch<React.SetStateAction<string>>;\n /**\n * An input/textarea-ready onChange handler to control the value of the input\n * @example\n * ```jsx\n * <input onChange={handleInputChange} value={input} />\n * ```\n */\n handleInputChange: (\n event:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => void;\n\n /**\n * Form submission handler to automatically reset input and append a user message\n * @example\n * ```jsx\n * <form onSubmit={handleSubmit}>\n * <input onChange={handleInputChange} value={input} />\n * </form>\n * ```\n */\n handleSubmit: (event?: { preventDefault?: () => void }) => void;\n\n /** Whether the API request is in progress */\n isLoading: boolean;\n /** Additional data added on the server via StreamData */\n data?: JSONValue[];\n};\n\nexport function useCompletion({\n api = '/api/completion',\n id,\n initialCompletion = '',\n initialInput = '',\n credentials,\n headers,\n body,\n streamProtocol = 'data',\n fetch,\n onResponse,\n onFinish,\n onError,\n experimental_throttle: throttleWaitMs,\n}: UseCompletionOptions & {\n /**\n * Custom throttle wait in ms for the completion and data updates.\n * Default is undefined, which disables throttling.\n */\n experimental_throttle?: number;\n} = {}): UseCompletionHelpers {\n // Generate an unique id for the completion if not provided.\n const hookId = useId();\n const completionId = id || hookId;\n\n // Store the completion state in SWR, using the completionId as the key to share states.\n const { data, mutate } = useSWR<string>([api, completionId], null, {\n fallbackData: initialCompletion,\n });\n\n const { data: isLoading = false, mutate: mutateLoading } = useSWR<boolean>(\n [completionId, 'loading'],\n null,\n );\n\n const { data: streamData, mutate: mutateStreamData } = useSWR<\n JSONValue[] | undefined\n >([completionId, 'streamData'], null);\n\n const [error, setError] = useState<undefined | Error>(undefined);\n const completion = data!;\n\n // Abort controller to cancel the current API call.\n const [abortController, setAbortController] =\n useState<AbortController | null>(null);\n\n const extraMetadataRef = useRef({\n credentials,\n headers,\n body,\n });\n\n useEffect(() => {\n extraMetadataRef.current = {\n credentials,\n headers,\n body,\n };\n }, [credentials, headers, body]);\n\n const triggerRequest = useCallback(\n async (prompt: string, options?: RequestOptions) =>\n callCompletionApi({\n api,\n prompt,\n credentials: extraMetadataRef.current.credentials,\n headers: { ...extraMetadataRef.current.headers, ...options?.headers },\n body: {\n ...extraMetadataRef.current.body,\n ...options?.body,\n },\n streamProtocol,\n fetch,\n // throttle streamed ui updates:\n setCompletion: throttle(\n (completion: string) => mutate(completion, false),\n throttleWaitMs,\n ),\n onData: throttle(\n (data: JSONValue[]) =>\n mutateStreamData([...(streamData ?? []), ...(data ?? [])], false),\n throttleWaitMs,\n ),\n setLoading: mutateLoading,\n setError,\n setAbortController,\n onResponse,\n onFinish,\n onError,\n }),\n [\n mutate,\n mutateLoading,\n api,\n extraMetadataRef,\n setAbortController,\n onResponse,\n onFinish,\n onError,\n setError,\n streamData,\n streamProtocol,\n fetch,\n mutateStreamData,\n throttleWaitMs,\n ],\n );\n\n const stop = useCallback(() => {\n if (abortController) {\n abortController.abort();\n setAbortController(null);\n }\n }, [abortController]);\n\n const setCompletion = useCallback(\n (completion: string) => {\n mutate(completion, false);\n },\n [mutate],\n );\n\n const complete = useCallback<UseCompletionHelpers['complete']>(\n async (prompt, options) => {\n return triggerRequest(prompt, options);\n },\n [triggerRequest],\n );\n\n const [input, setInput] = useState(initialInput);\n\n const handleSubmit = useCallback(\n (event?: { preventDefault?: () => void }) => {\n event?.preventDefault?.();\n return input ? complete(input) : undefined;\n },\n [input, complete],\n );\n\n const handleInputChange = useCallback(\n (e: any) => {\n setInput(e.target.value);\n },\n [setInput],\n );\n\n return {\n completion,\n complete,\n error,\n setCompletion,\n stop,\n input,\n setInput,\n handleInputChange,\n handleSubmit,\n isLoading,\n data: streamData,\n };\n}\n","import {\n FetchFunction,\n isAbortError,\n safeValidateTypes,\n} from '@ai-sdk/provider-utils';\nimport {\n asSchema,\n DeepPartial,\n isDeepEqualData,\n parsePartialJson,\n Schema,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useId, useRef, useState } from 'react';\nimport useSWR from 'swr';\nimport z from 'zod';\n\n// use function to allow for mocking in tests:\nconst getOriginalFetch = () => fetch;\n\nexport type Experimental_UseObjectOptions<RESULT> = {\n /**\n * The API endpoint. It should stream JSON that matches the schema as chunked text.\n */\n api: string;\n\n /**\n * A Zod schema that defines the shape of the complete object.\n */\n schema: z.Schema<RESULT, z.ZodTypeDef, any> | Schema<RESULT>;\n\n /**\n * An unique identifier. If not provided, a random one will be\n * generated. When provided, the `useObject` hook with the same `id` will\n * have shared states across components.\n */\n id?: string;\n\n /**\n * An optional value for the initial object.\n */\n initialValue?: DeepPartial<RESULT>;\n\n /**\nCustom fetch implementation. You can use it as a middleware to intercept requests,\nor to provide a custom fetch implementation for e.g. testing.\n */\n fetch?: FetchFunction;\n\n /**\nCallback that is called when the stream has finished.\n */\n onFinish?: (event: {\n /**\nThe generated object (typed according to the schema).\nCan be undefined if the final object does not match the schema.\n */\n object: RESULT | undefined;\n\n /**\nOptional error object. This is e.g. a TypeValidationError when the final object does not match the schema.\n */\n error: Error | undefined;\n }) => Promise<void> | void;\n\n /**\n * Callback function to be called when an error is encountered.\n */\n onError?: (error: Error) => void;\n\n /**\n * Additional HTTP headers to be included in the request.\n */\n headers?: Record<string, string> | Headers;\n};\n\nexport type Experimental_UseObjectHelpers<RESULT, INPUT> = {\n /**\n * Calls the API with the provided input as JSON body.\n */\n submit: (input: INPUT) => void;\n\n /**\n * The current value for the generated object. Updated as the API streams JSON chunks.\n */\n object: DeepPartial<RESULT> | undefined;\n\n /**\n * The error object of the API request if any.\n */\n error: Error | undefined;\n\n /**\n * Flag that indicates whether an API request is in progress.\n */\n isLoading: boolean;\n\n /**\n * Abort the current request immediately, keep the current partial object if any.\n */\n stop: () => void;\n};\n\nfunction useObject<RESULT, INPUT = any>({\n api,\n id,\n schema, // required, in the future we will use it for validation\n initialValue,\n fetch,\n onError,\n onFinish,\n headers,\n}: Experimental_UseObjectOptions<RESULT>): Experimental_UseObjectHelpers<\n RESULT,\n INPUT\n> {\n // Generate an unique id if not provided.\n const hookId = useId();\n const completionId = id ?? hookId;\n\n // Store the completion state in SWR, using the completionId as the key to share states.\n const { data, mutate } = useSWR<DeepPartial<RESULT>>(\n [api, completionId],\n null,\n { fallbackData: initialValue },\n );\n\n const [error, setError] = useState<undefined | Error>(undefined);\n const [isLoading, setIsLoading] = useState(false);\n\n // Abort controller to cancel the current API call.\n const abortControllerRef = useRef<AbortController | null>(null);\n\n const stop = useCallback(() => {\n try {\n abortControllerRef.current?.abort();\n } catch (ignored) {\n } finally {\n setIsLoading(false);\n abortControllerRef.current = null;\n }\n }, []);\n\n const submit = async (input: INPUT) => {\n try {\n mutate(undefined); // reset the data\n setIsLoading(true);\n setError(undefined);\n\n const abortController = new AbortController();\n abortControllerRef.current = abortController;\n\n const actualFetch = fetch ?? getOriginalFetch();\n const response = await actualFetch(api, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n ...headers,\n },\n signal: abortController.signal,\n body: JSON.stringify(input),\n });\n\n if (!response.ok) {\n throw new Error(\n (await response.text()) ?? 'Failed to fetch the response.',\n );\n }\n\n if (response.body == null) {\n throw new Error('The response body is empty.');\n }\n\n let accumulatedText = '';\n let latestObject: DeepPartial<RESULT> | undefined = undefined;\n\n await response.body.pipeThrough(new TextDecoderStream()).pipeTo(\n new WritableStream<string>({\n write(chunk) {\n accumulatedText += chunk;\n\n const { value } = parsePartialJson(accumulatedText);\n const currentObject = value as DeepPartial<RESULT>;\n\n if (!isDeepEqualData(latestObject, currentObject)) {\n latestObject = currentObject;\n\n mutate(currentObject);\n }\n },\n\n close() {\n setIsLoading(false);\n abortControllerRef.current = null;\n\n if (onFinish != null) {\n const validationResult = safeValidateTypes({\n value: latestObject,\n schema: asSchema(schema),\n });\n\n onFinish(\n validationResult.success\n ? { object: validationResult.value, error: undefined }\n : { object: undefined, error: validationResult.error },\n );\n }\n },\n }),\n );\n } catch (error) {\n if (isAbortError(error)) {\n return;\n }\n\n if (onError && error instanceof Error) {\n onError(error);\n }\n\n setIsLoading(false);\n setError(error instanceof Error ? error : new Error(String(error)));\n }\n };\n\n return {\n submit,\n object: data,\n error,\n isLoading,\n stop,\n };\n}\n\nexport const experimental_useObject = useObject;\n"],"mappings":"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","names":["fetch","messages","_a","error","useCallback","useRef","useState","generateId","fetch","useState","useRef","useCallback","messages","headers","body","useCallback","useEffect","useRef","useState","useSWR","fetch","useSWR","useState","useRef","useEffect","useCallback","completion","data","isAbortError","useCallback","useId","useRef","useState","useSWR","getOriginalFetch","fetch","error"]}
1
+ {"version":3,"sources":["../src/use-assistant.ts","../src/use-chat.ts","../src/throttle.ts","../src/util/use-stable-value.ts","../src/use-completion.ts","../src/use-object.ts"],"sourcesContent":["import { isAbortError } from '@ai-sdk/provider-utils';\nimport {\n AssistantStatus,\n CreateMessage,\n Message,\n UseAssistantOptions,\n generateId,\n processAssistantStream,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useRef, useState } from 'react';\n\n// use function to allow for mocking in tests:\nconst getOriginalFetch = () => fetch;\n\nexport type UseAssistantHelpers = {\n /**\n * The current array of chat messages.\n */\n messages: Message[];\n\n /**\n * Update the message store with a new array of messages.\n */\n setMessages: React.Dispatch<React.SetStateAction<Message[]>>;\n\n /**\n * The current thread ID.\n */\n threadId: string | undefined;\n\n /**\n * Set the current thread ID. Specifying a thread ID will switch to that thread, if it exists. If set to 'undefined', a new thread will be created. For both cases, `threadId` will be updated with the new value and `messages` will be cleared.\n */\n setThreadId: (threadId: string | undefined) => void;\n\n /**\n * The current value of the input field.\n */\n input: string;\n\n /**\n * Append a user message to the chat list. This triggers the API call to fetch\n * the assistant's response.\n * @param message The message to append\n * @param requestOptions Additional options to pass to the API call\n */\n append: (\n message: Message | CreateMessage,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => Promise<void>;\n\n /**\nAbort the current request immediately, keep the generated tokens if any.\n */\n stop: () => void;\n\n /**\n * setState-powered method to update the input value.\n */\n setInput: React.Dispatch<React.SetStateAction<string>>;\n\n /**\n * Handler for the `onChange` event of the input field to control the input's value.\n */\n handleInputChange: (\n event:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => void;\n\n /**\n * Form submission handler that automatically resets the input field and appends a user message.\n */\n submitMessage: (\n event?: React.FormEvent<HTMLFormElement>,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => Promise<void>;\n\n /**\n * The current status of the assistant. This can be used to show a loading indicator.\n */\n status: AssistantStatus;\n\n /**\n * The error thrown during the assistant message processing, if any.\n */\n error: undefined | Error;\n};\n\nexport function useAssistant({\n api,\n threadId: threadIdParam,\n credentials,\n headers,\n body,\n onError,\n fetch,\n}: UseAssistantOptions): UseAssistantHelpers {\n const [messages, setMessages] = useState<Message[]>([]);\n const [input, setInput] = useState('');\n const [currentThreadId, setCurrentThreadId] = useState<string | undefined>(\n undefined,\n );\n const [status, setStatus] = useState<AssistantStatus>('awaiting_message');\n const [error, setError] = useState<undefined | Error>(undefined);\n\n const handleInputChange = (\n event:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => {\n setInput(event.target.value);\n };\n\n // Abort controller to cancel the current API call.\n const abortControllerRef = useRef<AbortController | null>(null);\n\n const stop = useCallback(() => {\n if (abortControllerRef.current) {\n abortControllerRef.current.abort();\n abortControllerRef.current = null;\n }\n }, []);\n\n const append = async (\n message: Message | CreateMessage,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => {\n setStatus('in_progress');\n\n setMessages(messages => [\n ...messages,\n {\n ...message,\n id: message.id ?? generateId(),\n },\n ]);\n\n setInput('');\n\n const abortController = new AbortController();\n\n try {\n abortControllerRef.current = abortController;\n\n const actualFetch = fetch ?? getOriginalFetch();\n const response = await actualFetch(api, {\n method: 'POST',\n credentials,\n signal: abortController.signal,\n headers: { 'Content-Type': 'application/json', ...headers },\n body: JSON.stringify({\n ...body,\n // always use user-provided threadId when available:\n threadId: threadIdParam ?? currentThreadId ?? null,\n message: message.content,\n\n // optional request data:\n data: requestOptions?.data,\n }),\n });\n\n if (!response.ok) {\n throw new Error(\n (await response.text()) ?? 'Failed to fetch the assistant response.',\n );\n }\n\n if (response.body == null) {\n throw new Error('The response body is empty.');\n }\n\n await processAssistantStream({\n stream: response.body,\n onAssistantMessagePart(value) {\n setMessages(messages => [\n ...messages,\n {\n id: value.id,\n role: value.role,\n content: value.content[0].text.value,\n parts: [],\n },\n ]);\n },\n onTextPart(value) {\n // text delta - add to last message:\n setMessages(messages => {\n const lastMessage = messages[messages.length - 1];\n return [\n ...messages.slice(0, messages.length - 1),\n {\n id: lastMessage.id,\n role: lastMessage.role,\n content: lastMessage.content + value,\n parts: lastMessage.parts,\n },\n ];\n });\n },\n onAssistantControlDataPart(value) {\n setCurrentThreadId(value.threadId);\n\n // set id of last message:\n setMessages(messages => {\n const lastMessage = messages[messages.length - 1];\n lastMessage.id = value.messageId;\n return [...messages.slice(0, messages.length - 1), lastMessage];\n });\n },\n onDataMessagePart(value) {\n setMessages(messages => [\n ...messages,\n {\n id: value.id ?? generateId(),\n role: 'data',\n content: '',\n data: value.data,\n parts: [],\n },\n ]);\n },\n onErrorPart(value) {\n setError(new Error(value));\n },\n });\n } catch (error) {\n // Ignore abort errors as they are expected when the user cancels the request:\n if (isAbortError(error) && abortController.signal.aborted) {\n abortControllerRef.current = null;\n return;\n }\n\n if (onError && error instanceof Error) {\n onError(error);\n }\n\n setError(error as Error);\n } finally {\n abortControllerRef.current = null;\n setStatus('awaiting_message');\n }\n };\n\n const submitMessage = async (\n event?: React.FormEvent<HTMLFormElement>,\n requestOptions?: {\n data?: Record<string, string>;\n },\n ) => {\n event?.preventDefault?.();\n\n if (input === '') {\n return;\n }\n\n append({ role: 'user', content: input, parts: [] }, requestOptions);\n };\n\n const setThreadId = (threadId: string | undefined) => {\n setCurrentThreadId(threadId);\n setMessages([]);\n };\n\n return {\n append,\n messages,\n setMessages,\n threadId: currentThreadId,\n setThreadId,\n input,\n setInput,\n handleInputChange,\n submitMessage,\n status,\n error,\n stop,\n };\n}\n","import type {\n ChatRequest,\n ChatRequestOptions,\n CreateMessage,\n JSONValue,\n Message,\n UIMessage,\n UseChatOptions,\n} from '@ai-sdk/ui-utils';\nimport {\n callChatApi,\n extractMaxToolInvocationStep,\n fillMessageParts,\n generateId as generateIdFunc,\n getMessageParts,\n isAssistantMessageWithCompletedToolCalls,\n prepareAttachmentsForRequest,\n shouldResubmitMessages,\n updateToolCallResult,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useEffect, useMemo, useRef, useState } from 'react';\nimport useSWR from 'swr';\nimport { throttle } from './throttle';\nimport { useStableValue } from './util/use-stable-value';\n\nexport type { CreateMessage, Message, UseChatOptions };\n\nexport type UseChatHelpers = {\n /** Current messages in the chat */\n messages: UIMessage[];\n /** The error object of the API request */\n error: undefined | Error;\n /**\n * Append a user message to the chat list. This triggers the API call to fetch\n * the assistant's response.\n * @param message The message to append\n * @param options Additional options to pass to the API call\n */\n append: (\n message: Message | CreateMessage,\n chatRequestOptions?: ChatRequestOptions,\n ) => Promise<string | null | undefined>;\n /**\n * Reload the last AI chat response for the given chat history. If the last\n * message isn't from the assistant, it will request the API to generate a\n * new response.\n */\n reload: (\n chatRequestOptions?: ChatRequestOptions,\n ) => Promise<string | null | undefined>;\n /**\n * Abort the current request immediately, keep the generated tokens if any.\n */\n stop: () => void;\n /**\n * Update the `messages` state locally. This is useful when you want to\n * edit the messages on the client, and then trigger the `reload` method\n * manually to regenerate the AI response.\n */\n setMessages: (\n messages: Message[] | ((messages: Message[]) => Message[]),\n ) => void;\n /** The current value of the input */\n input: string;\n /** setState-powered method to update the input value */\n setInput: React.Dispatch<React.SetStateAction<string>>;\n /** An input/textarea-ready onChange handler to control the value of the input */\n handleInputChange: (\n e:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => void;\n /** Form submission handler to automatically reset input and append a user message */\n handleSubmit: (\n event?: { preventDefault?: () => void },\n chatRequestOptions?: ChatRequestOptions,\n ) => void;\n metadata?: Object;\n\n /**\n * Whether the API request is in progress\n *\n * @deprecated use `status` instead\n */\n isLoading: boolean;\n\n /**\n * Hook status:\n *\n * - `submitted`: The message has been sent to the API and we're awaiting the start of the response stream.\n * - `streaming`: The response is actively streaming in from the API, receiving chunks of data.\n * - `ready`: The full response has been received and processed; a new user message can be submitted.\n * - `error`: An error occurred during the API request, preventing successful completion.\n */\n status: 'submitted' | 'streaming' | 'ready' | 'error';\n\n /** Additional data added on the server via StreamData. */\n data?: JSONValue[];\n\n /** Set the data of the chat. You can use this to transform or clear the chat data. */\n setData: (\n data:\n | JSONValue[]\n | undefined\n | ((data: JSONValue[] | undefined) => JSONValue[] | undefined),\n ) => void;\n\n /** The id of the chat */\n id: string;\n};\n\nexport function useChat({\n api = '/api/chat',\n id,\n initialMessages,\n initialInput = '',\n sendExtraMessageFields,\n onToolCall,\n experimental_prepareRequestBody,\n maxSteps = 1,\n streamProtocol = 'data',\n onResponse,\n onFinish,\n onError,\n credentials,\n headers,\n body,\n generateId = generateIdFunc,\n fetch,\n keepLastMessageOnError = true,\n experimental_throttle: throttleWaitMs,\n}: UseChatOptions & {\n key?: string;\n\n /**\n * Experimental (React only). When a function is provided, it will be used\n * to prepare the request body for the chat API. This can be useful for\n * customizing the request body based on the messages and data in the chat.\n *\n * @param messages The current messages in the chat.\n * @param requestData The data object passed in the chat request.\n * @param requestBody The request body object passed in the chat request.\n */\n experimental_prepareRequestBody?: (options: {\n id: string;\n messages: UIMessage[];\n requestData?: JSONValue;\n requestBody?: object;\n }) => unknown;\n\n /**\nCustom throttle wait in ms for the chat messages and data updates.\nDefault is undefined, which disables throttling.\n */\n experimental_throttle?: number;\n\n /**\nMaximum number of sequential LLM calls (steps), e.g. when you use tool calls.\nMust be at least 1.\n\nA maximum number is required to prevent infinite loops in the case of misconfigured tools.\n\nBy default, it's set to 1, which means that only a single LLM call is made.\n */\n maxSteps?: number;\n} = {}): UseChatHelpers & {\n addToolResult: ({\n toolCallId,\n result,\n }: {\n toolCallId: string;\n result: any;\n }) => void;\n} {\n // Generate ID once, store in state for stability across re-renders\n const [hookId] = useState(generateId);\n\n // Use the caller-supplied ID if available; otherwise, fall back to our stable ID\n const chatId = id ?? hookId;\n const chatKey = typeof api === 'string' ? [api, chatId] : chatId;\n\n // Store array of the processed initial messages to avoid re-renders:\n const stableInitialMessages = useStableValue(initialMessages ?? []);\n const processedInitialMessages = useMemo(\n () => fillMessageParts(stableInitialMessages),\n [stableInitialMessages],\n );\n\n // Store the chat state in SWR, using the chatId as the key to share states.\n const { data: messages, mutate } = useSWR<UIMessage[]>(\n [chatKey, 'messages'],\n null,\n { fallbackData: processedInitialMessages },\n );\n\n // Keep the latest messages in a ref.\n const messagesRef = useRef<UIMessage[]>(messages || []);\n useEffect(() => {\n messagesRef.current = messages || [];\n }, [messages]);\n\n // stream data\n const { data: streamData, mutate: mutateStreamData } = useSWR<\n JSONValue[] | undefined\n >([chatKey, 'streamData'], null);\n\n // keep the latest stream data in a ref\n const streamDataRef = useRef<JSONValue[] | undefined>(streamData);\n useEffect(() => {\n streamDataRef.current = streamData;\n }, [streamData]);\n\n const { data: status = 'ready', mutate: mutateStatus } = useSWR<\n 'submitted' | 'streaming' | 'ready' | 'error'\n >([chatKey, 'status'], null);\n\n const { data: error = undefined, mutate: setError } = useSWR<\n undefined | Error\n >([chatKey, 'error'], null);\n\n // Abort controller to cancel the current API call.\n const abortControllerRef = useRef<AbortController | null>(null);\n\n const extraMetadataRef = useRef({\n credentials,\n headers,\n body,\n });\n\n useEffect(() => {\n extraMetadataRef.current = {\n credentials,\n headers,\n body,\n };\n }, [credentials, headers, body]);\n\n const triggerRequest = useCallback(\n async (chatRequest: ChatRequest) => {\n mutateStatus('submitted');\n setError(undefined);\n\n const chatMessages = fillMessageParts(chatRequest.messages);\n\n const messageCount = chatMessages.length;\n const maxStep = extractMaxToolInvocationStep(\n chatMessages[chatMessages.length - 1]?.toolInvocations,\n );\n\n try {\n const abortController = new AbortController();\n abortControllerRef.current = abortController;\n\n const throttledMutate = throttle(mutate, throttleWaitMs);\n const throttledMutateStreamData = throttle(\n mutateStreamData,\n throttleWaitMs,\n );\n\n // Do an optimistic update to the chat state to show the updated messages immediately:\n const previousMessages = messagesRef.current;\n throttledMutate(chatMessages, false);\n\n const constructedMessagesPayload = sendExtraMessageFields\n ? chatMessages\n : chatMessages.map(\n ({\n role,\n content,\n experimental_attachments,\n data,\n annotations,\n toolInvocations,\n parts,\n }) => ({\n role,\n content,\n ...(experimental_attachments !== undefined && {\n experimental_attachments,\n }),\n ...(data !== undefined && { data }),\n ...(annotations !== undefined && { annotations }),\n ...(toolInvocations !== undefined && { toolInvocations }),\n ...(parts !== undefined && { parts }),\n }),\n );\n\n const existingData = streamDataRef.current;\n\n await callChatApi({\n api,\n body: experimental_prepareRequestBody?.({\n id: chatId,\n messages: chatMessages,\n requestData: chatRequest.data,\n requestBody: chatRequest.body,\n }) ?? {\n id: chatId,\n messages: constructedMessagesPayload,\n data: chatRequest.data,\n ...extraMetadataRef.current.body,\n ...chatRequest.body,\n },\n streamProtocol,\n credentials: extraMetadataRef.current.credentials,\n headers: {\n ...extraMetadataRef.current.headers,\n ...chatRequest.headers,\n },\n abortController: () => abortControllerRef.current,\n restoreMessagesOnFailure() {\n if (!keepLastMessageOnError) {\n throttledMutate(previousMessages, false);\n }\n },\n onResponse,\n onUpdate({ message, data, replaceLastMessage }) {\n mutateStatus('streaming');\n\n throttledMutate(\n [\n ...(replaceLastMessage\n ? chatMessages.slice(0, chatMessages.length - 1)\n : chatMessages),\n message,\n ],\n false,\n );\n\n if (data?.length) {\n throttledMutateStreamData(\n [...(existingData ?? []), ...data],\n false,\n );\n }\n },\n onToolCall,\n onFinish,\n generateId,\n fetch,\n lastMessage: chatMessages[chatMessages.length - 1],\n });\n\n abortControllerRef.current = null;\n\n mutateStatus('ready');\n } catch (err) {\n // Ignore abort errors as they are expected.\n if ((err as any).name === 'AbortError') {\n abortControllerRef.current = null;\n mutateStatus('ready');\n return null;\n }\n\n if (onError && err instanceof Error) {\n onError(err);\n }\n\n setError(err as Error);\n mutateStatus('error');\n }\n\n // auto-submit when all tool calls in the last assistant message have results\n // and assistant has not answered yet\n const messages = messagesRef.current;\n if (\n shouldResubmitMessages({\n originalMaxToolInvocationStep: maxStep,\n originalMessageCount: messageCount,\n maxSteps,\n messages,\n })\n ) {\n await triggerRequest({ messages });\n }\n },\n [\n mutate,\n mutateStatus,\n api,\n extraMetadataRef,\n onResponse,\n onFinish,\n onError,\n setError,\n mutateStreamData,\n streamDataRef,\n streamProtocol,\n sendExtraMessageFields,\n experimental_prepareRequestBody,\n onToolCall,\n maxSteps,\n messagesRef,\n abortControllerRef,\n generateId,\n fetch,\n keepLastMessageOnError,\n throttleWaitMs,\n chatId,\n ],\n );\n\n const append = useCallback(\n async (\n message: Message | CreateMessage,\n {\n data,\n headers,\n body,\n experimental_attachments,\n }: ChatRequestOptions = {},\n ) => {\n const attachmentsForRequest = await prepareAttachmentsForRequest(\n experimental_attachments,\n );\n\n const messages = messagesRef.current.concat({\n ...message,\n id: message.id ?? generateId(),\n createdAt: message.createdAt ?? new Date(),\n experimental_attachments:\n attachmentsForRequest.length > 0 ? attachmentsForRequest : undefined,\n parts: getMessageParts(message),\n });\n\n return triggerRequest({ messages, headers, body, data });\n },\n [triggerRequest, generateId],\n );\n\n const reload = useCallback(\n async ({ data, headers, body }: ChatRequestOptions = {}) => {\n const messages = messagesRef.current;\n\n if (messages.length === 0) {\n return null;\n }\n\n // Remove last assistant message and retry last user message.\n const lastMessage = messages[messages.length - 1];\n return triggerRequest({\n messages:\n lastMessage.role === 'assistant' ? messages.slice(0, -1) : messages,\n headers,\n body,\n data,\n });\n },\n [triggerRequest],\n );\n\n const stop = useCallback(() => {\n if (abortControllerRef.current) {\n abortControllerRef.current.abort();\n abortControllerRef.current = null;\n }\n }, []);\n\n const setMessages = useCallback(\n (messages: Message[] | ((messages: Message[]) => Message[])) => {\n if (typeof messages === 'function') {\n messages = messages(messagesRef.current);\n }\n\n const messagesWithParts = fillMessageParts(messages);\n mutate(messagesWithParts, false);\n messagesRef.current = messagesWithParts;\n },\n [mutate],\n );\n\n const setData = useCallback(\n (\n data:\n | JSONValue[]\n | undefined\n | ((data: JSONValue[] | undefined) => JSONValue[] | undefined),\n ) => {\n if (typeof data === 'function') {\n data = data(streamDataRef.current);\n }\n\n mutateStreamData(data, false);\n streamDataRef.current = data;\n },\n [mutateStreamData],\n );\n\n // Input state and handlers.\n const [input, setInput] = useState(initialInput);\n\n const handleSubmit = useCallback(\n async (\n event?: { preventDefault?: () => void },\n options: ChatRequestOptions = {},\n metadata?: Object,\n ) => {\n event?.preventDefault?.();\n\n if (!input && !options.allowEmptySubmit) return;\n\n if (metadata) {\n extraMetadataRef.current = {\n ...extraMetadataRef.current,\n ...metadata,\n };\n }\n\n const attachmentsForRequest = await prepareAttachmentsForRequest(\n options.experimental_attachments,\n );\n\n const messages = messagesRef.current.concat({\n id: generateId(),\n createdAt: new Date(),\n role: 'user',\n content: input,\n experimental_attachments:\n attachmentsForRequest.length > 0 ? attachmentsForRequest : undefined,\n parts: [{ type: 'text', text: input }],\n });\n\n const chatRequest: ChatRequest = {\n messages,\n headers: options.headers,\n body: options.body,\n data: options.data,\n };\n\n triggerRequest(chatRequest);\n\n setInput('');\n },\n [input, generateId, triggerRequest],\n );\n\n const handleInputChange = (e: any) => {\n setInput(e.target.value);\n };\n\n const addToolResult = useCallback(\n ({ toolCallId, result }: { toolCallId: string; result: unknown }) => {\n const currentMessages = messagesRef.current;\n\n updateToolCallResult({\n messages: currentMessages,\n toolCallId,\n toolResult: result,\n });\n\n mutate(currentMessages, false);\n\n // auto-submit when all tool calls in the last assistant message have results:\n const lastMessage = currentMessages[currentMessages.length - 1];\n if (isAssistantMessageWithCompletedToolCalls(lastMessage)) {\n triggerRequest({ messages: currentMessages });\n }\n },\n [mutate, triggerRequest],\n );\n\n return {\n messages: messages ?? [],\n id: chatId,\n setMessages,\n data: streamData,\n setData,\n error,\n append,\n reload,\n stop,\n input,\n setInput,\n handleInputChange,\n handleSubmit,\n isLoading: status === 'submitted' || status === 'streaming',\n status,\n addToolResult,\n };\n}\n","import throttleFunction from 'throttleit';\n\nexport function throttle<T extends (...args: any[]) => any>(\n fn: T,\n waitMs: number | undefined,\n): T {\n return waitMs != null ? throttleFunction(fn, waitMs) : fn;\n}\n","import { isDeepEqualData } from '@ai-sdk/ui-utils';\nimport { useEffect, useState } from 'react';\n\n/**\n * Returns a stable value that only updates the stored value (and triggers a re-render)\n * when the value's contents differ by deep-compare.\n */\nexport function useStableValue<T>(latestValue: T): T {\n const [value, setValue] = useState<T>(latestValue);\n\n useEffect(() => {\n if (!isDeepEqualData(latestValue, value)) {\n setValue(latestValue);\n }\n }, [latestValue, value]);\n\n return value;\n}\n","import {\n JSONValue,\n RequestOptions,\n UseCompletionOptions,\n callCompletionApi,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useEffect, useId, useRef, useState } from 'react';\nimport useSWR from 'swr';\nimport { throttle } from './throttle';\n\nexport type { UseCompletionOptions };\n\nexport type UseCompletionHelpers = {\n /** The current completion result */\n completion: string;\n /**\n * Send a new prompt to the API endpoint and update the completion state.\n */\n complete: (\n prompt: string,\n options?: RequestOptions,\n ) => Promise<string | null | undefined>;\n /** The error object of the API request */\n error: undefined | Error;\n /**\n * Abort the current API request but keep the generated tokens.\n */\n stop: () => void;\n /**\n * Update the `completion` state locally.\n */\n setCompletion: (completion: string) => void;\n /** The current value of the input */\n input: string;\n /** setState-powered method to update the input value */\n setInput: React.Dispatch<React.SetStateAction<string>>;\n /**\n * An input/textarea-ready onChange handler to control the value of the input\n * @example\n * ```jsx\n * <input onChange={handleInputChange} value={input} />\n * ```\n */\n handleInputChange: (\n event:\n | React.ChangeEvent<HTMLInputElement>\n | React.ChangeEvent<HTMLTextAreaElement>,\n ) => void;\n\n /**\n * Form submission handler to automatically reset input and append a user message\n * @example\n * ```jsx\n * <form onSubmit={handleSubmit}>\n * <input onChange={handleInputChange} value={input} />\n * </form>\n * ```\n */\n handleSubmit: (event?: { preventDefault?: () => void }) => void;\n\n /** Whether the API request is in progress */\n isLoading: boolean;\n /** Additional data added on the server via StreamData */\n data?: JSONValue[];\n};\n\nexport function useCompletion({\n api = '/api/completion',\n id,\n initialCompletion = '',\n initialInput = '',\n credentials,\n headers,\n body,\n streamProtocol = 'data',\n fetch,\n onResponse,\n onFinish,\n onError,\n experimental_throttle: throttleWaitMs,\n}: UseCompletionOptions & {\n /**\n * Custom throttle wait in ms for the completion and data updates.\n * Default is undefined, which disables throttling.\n */\n experimental_throttle?: number;\n} = {}): UseCompletionHelpers {\n // Generate an unique id for the completion if not provided.\n const hookId = useId();\n const completionId = id || hookId;\n\n // Store the completion state in SWR, using the completionId as the key to share states.\n const { data, mutate } = useSWR<string>([api, completionId], null, {\n fallbackData: initialCompletion,\n });\n\n const { data: isLoading = false, mutate: mutateLoading } = useSWR<boolean>(\n [completionId, 'loading'],\n null,\n );\n\n const { data: streamData, mutate: mutateStreamData } = useSWR<\n JSONValue[] | undefined\n >([completionId, 'streamData'], null);\n\n const [error, setError] = useState<undefined | Error>(undefined);\n const completion = data!;\n\n // Abort controller to cancel the current API call.\n const [abortController, setAbortController] =\n useState<AbortController | null>(null);\n\n const extraMetadataRef = useRef({\n credentials,\n headers,\n body,\n });\n\n useEffect(() => {\n extraMetadataRef.current = {\n credentials,\n headers,\n body,\n };\n }, [credentials, headers, body]);\n\n const triggerRequest = useCallback(\n async (prompt: string, options?: RequestOptions) =>\n callCompletionApi({\n api,\n prompt,\n credentials: extraMetadataRef.current.credentials,\n headers: { ...extraMetadataRef.current.headers, ...options?.headers },\n body: {\n ...extraMetadataRef.current.body,\n ...options?.body,\n },\n streamProtocol,\n fetch,\n // throttle streamed ui updates:\n setCompletion: throttle(\n (completion: string) => mutate(completion, false),\n throttleWaitMs,\n ),\n onData: throttle(\n (data: JSONValue[]) =>\n mutateStreamData([...(streamData ?? []), ...(data ?? [])], false),\n throttleWaitMs,\n ),\n setLoading: mutateLoading,\n setError,\n setAbortController,\n onResponse,\n onFinish,\n onError,\n }),\n [\n mutate,\n mutateLoading,\n api,\n extraMetadataRef,\n setAbortController,\n onResponse,\n onFinish,\n onError,\n setError,\n streamData,\n streamProtocol,\n fetch,\n mutateStreamData,\n throttleWaitMs,\n ],\n );\n\n const stop = useCallback(() => {\n if (abortController) {\n abortController.abort();\n setAbortController(null);\n }\n }, [abortController]);\n\n const setCompletion = useCallback(\n (completion: string) => {\n mutate(completion, false);\n },\n [mutate],\n );\n\n const complete = useCallback<UseCompletionHelpers['complete']>(\n async (prompt, options) => {\n return triggerRequest(prompt, options);\n },\n [triggerRequest],\n );\n\n const [input, setInput] = useState(initialInput);\n\n const handleSubmit = useCallback(\n (event?: { preventDefault?: () => void }) => {\n event?.preventDefault?.();\n return input ? complete(input) : undefined;\n },\n [input, complete],\n );\n\n const handleInputChange = useCallback(\n (e: any) => {\n setInput(e.target.value);\n },\n [setInput],\n );\n\n return {\n completion,\n complete,\n error,\n setCompletion,\n stop,\n input,\n setInput,\n handleInputChange,\n handleSubmit,\n isLoading,\n data: streamData,\n };\n}\n","import {\n FetchFunction,\n isAbortError,\n safeValidateTypes,\n} from '@ai-sdk/provider-utils';\nimport {\n asSchema,\n DeepPartial,\n isDeepEqualData,\n parsePartialJson,\n Schema,\n} from '@ai-sdk/ui-utils';\nimport { useCallback, useId, useRef, useState } from 'react';\nimport useSWR from 'swr';\nimport z from 'zod';\n\n// use function to allow for mocking in tests:\nconst getOriginalFetch = () => fetch;\n\nexport type Experimental_UseObjectOptions<RESULT> = {\n /**\n * The API endpoint. It should stream JSON that matches the schema as chunked text.\n */\n api: string;\n\n /**\n * A Zod schema that defines the shape of the complete object.\n */\n schema: z.Schema<RESULT, z.ZodTypeDef, any> | Schema<RESULT>;\n\n /**\n * An unique identifier. If not provided, a random one will be\n * generated. When provided, the `useObject` hook with the same `id` will\n * have shared states across components.\n */\n id?: string;\n\n /**\n * An optional value for the initial object.\n */\n initialValue?: DeepPartial<RESULT>;\n\n /**\nCustom fetch implementation. You can use it as a middleware to intercept requests,\nor to provide a custom fetch implementation for e.g. testing.\n */\n fetch?: FetchFunction;\n\n /**\nCallback that is called when the stream has finished.\n */\n onFinish?: (event: {\n /**\nThe generated object (typed according to the schema).\nCan be undefined if the final object does not match the schema.\n */\n object: RESULT | undefined;\n\n /**\nOptional error object. This is e.g. a TypeValidationError when the final object does not match the schema.\n */\n error: Error | undefined;\n }) => Promise<void> | void;\n\n /**\n * Callback function to be called when an error is encountered.\n */\n onError?: (error: Error) => void;\n\n /**\n * Additional HTTP headers to be included in the request.\n */\n headers?: Record<string, string> | Headers;\n};\n\nexport type Experimental_UseObjectHelpers<RESULT, INPUT> = {\n /**\n * Calls the API with the provided input as JSON body.\n */\n submit: (input: INPUT) => void;\n\n /**\n * The current value for the generated object. Updated as the API streams JSON chunks.\n */\n object: DeepPartial<RESULT> | undefined;\n\n /**\n * The error object of the API request if any.\n */\n error: Error | undefined;\n\n /**\n * Flag that indicates whether an API request is in progress.\n */\n isLoading: boolean;\n\n /**\n * Abort the current request immediately, keep the current partial object if any.\n */\n stop: () => void;\n};\n\nfunction useObject<RESULT, INPUT = any>({\n api,\n id,\n schema, // required, in the future we will use it for validation\n initialValue,\n fetch,\n onError,\n onFinish,\n headers,\n}: Experimental_UseObjectOptions<RESULT>): Experimental_UseObjectHelpers<\n RESULT,\n INPUT\n> {\n // Generate an unique id if not provided.\n const hookId = useId();\n const completionId = id ?? hookId;\n\n // Store the completion state in SWR, using the completionId as the key to share states.\n const { data, mutate } = useSWR<DeepPartial<RESULT>>(\n [api, completionId],\n null,\n { fallbackData: initialValue },\n );\n\n const [error, setError] = useState<undefined | Error>(undefined);\n const [isLoading, setIsLoading] = useState(false);\n\n // Abort controller to cancel the current API call.\n const abortControllerRef = useRef<AbortController | null>(null);\n\n const stop = useCallback(() => {\n try {\n abortControllerRef.current?.abort();\n } catch (ignored) {\n } finally {\n setIsLoading(false);\n abortControllerRef.current = null;\n }\n }, []);\n\n const submit = async (input: INPUT) => {\n try {\n mutate(undefined); // reset the data\n setIsLoading(true);\n setError(undefined);\n\n const abortController = new AbortController();\n abortControllerRef.current = abortController;\n\n const actualFetch = fetch ?? getOriginalFetch();\n const response = await actualFetch(api, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n ...headers,\n },\n signal: abortController.signal,\n body: JSON.stringify(input),\n });\n\n if (!response.ok) {\n throw new Error(\n (await response.text()) ?? 'Failed to fetch the response.',\n );\n }\n\n if (response.body == null) {\n throw new Error('The response body is empty.');\n }\n\n let accumulatedText = '';\n let latestObject: DeepPartial<RESULT> | undefined = undefined;\n\n await response.body.pipeThrough(new TextDecoderStream()).pipeTo(\n new WritableStream<string>({\n write(chunk) {\n accumulatedText += chunk;\n\n const { value } = parsePartialJson(accumulatedText);\n const currentObject = value as DeepPartial<RESULT>;\n\n if (!isDeepEqualData(latestObject, currentObject)) {\n latestObject = currentObject;\n\n mutate(currentObject);\n }\n },\n\n close() {\n setIsLoading(false);\n abortControllerRef.current = null;\n\n if (onFinish != null) {\n const validationResult = safeValidateTypes({\n value: latestObject,\n schema: asSchema(schema),\n });\n\n onFinish(\n validationResult.success\n ? { object: validationResult.value, error: undefined }\n : { object: undefined, error: validationResult.error },\n );\n }\n },\n }),\n );\n } catch (error) {\n if (isAbortError(error)) {\n return;\n }\n\n if (onError && error instanceof Error) {\n onError(error);\n }\n\n setIsLoading(false);\n setError(error instanceof Error ? error : new Error(String(error)));\n }\n };\n\n return {\n submit,\n object: data,\n error,\n isLoading,\n stop,\n };\n}\n\nexport const experimental_useObject = useObject;\n"],"mappings":"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","names":["fetch","messages","_a","error","useCallback","useEffect","useRef","useState","useState","generateId","fetch","useState","useRef","useEffect","useCallback","messages","headers","body","useCallback","useEffect","useRef","useState","useSWR","fetch","useSWR","useState","useRef","useEffect","useCallback","completion","data","isAbortError","isDeepEqualData","useCallback","useId","useRef","useState","useSWR","getOriginalFetch","fetch","error"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ai-sdk/react",
3
- "version": "1.1.18",
3
+ "version": "1.1.20",
4
4
  "license": "Apache-2.0",
5
5
  "sideEffects": false,
6
6
  "main": "./dist/index.js",