@ai-sdk/react 2.0.0-canary.9 → 2.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.mjs CHANGED
@@ -1,17 +1,27 @@
1
+ var __accessCheck = (obj, member, msg) => {
2
+ if (!member.has(obj))
3
+ throw TypeError("Cannot " + msg);
4
+ };
5
+ var __privateGet = (obj, member, getter) => {
6
+ __accessCheck(obj, member, "read from private field");
7
+ return getter ? getter.call(obj) : member.get(obj);
8
+ };
9
+ var __privateAdd = (obj, member, value) => {
10
+ if (member.has(obj))
11
+ throw TypeError("Cannot add the same private member more than once");
12
+ member instanceof WeakSet ? member.add(obj) : member.set(obj, value);
13
+ };
14
+ var __privateSet = (obj, member, value, setter) => {
15
+ __accessCheck(obj, member, "write to private field");
16
+ setter ? setter.call(obj, value) : member.set(obj, value);
17
+ return value;
18
+ };
19
+
1
20
  // src/use-chat.ts
2
- import {
3
- callChatApi,
4
- extractMaxToolInvocationStep,
5
- fillMessageParts,
6
- generateId as generateIdFunc,
7
- getMessageParts,
8
- isAssistantMessageWithCompletedToolCalls,
9
- prepareAttachmentsForRequest,
10
- shouldResubmitMessages,
11
- updateToolCallResult
12
- } from "ai";
13
- import { useCallback, useEffect as useEffect2, useMemo, useRef, useState as useState2 } from "react";
14
- import useSWR from "swr";
21
+ import { useCallback, useEffect, useRef, useSyncExternalStore } from "react";
22
+
23
+ // src/chat.react.ts
24
+ import { AbstractChat } from "ai";
15
25
 
16
26
  // src/throttle.ts
17
27
  import throttleFunction from "throttleit";
@@ -19,363 +29,170 @@ function throttle(fn, waitMs) {
19
29
  return waitMs != null ? throttleFunction(fn, waitMs) : fn;
20
30
  }
21
31
 
22
- // src/util/use-stable-value.ts
23
- import { isDeepEqualData } from "ai";
24
- import { useEffect, useState } from "react";
25
- function useStableValue(latestValue) {
26
- const [value, setValue] = useState(latestValue);
27
- useEffect(() => {
28
- if (!isDeepEqualData(latestValue, value)) {
29
- setValue(latestValue);
30
- }
31
- }, [latestValue, value]);
32
- return value;
33
- }
32
+ // src/chat.react.ts
33
+ var _messages, _status, _error, _messagesCallbacks, _statusCallbacks, _errorCallbacks, _callMessagesCallbacks, _callStatusCallbacks, _callErrorCallbacks;
34
+ var ReactChatState = class {
35
+ constructor(initialMessages = []) {
36
+ __privateAdd(this, _messages, void 0);
37
+ __privateAdd(this, _status, "ready");
38
+ __privateAdd(this, _error, void 0);
39
+ __privateAdd(this, _messagesCallbacks, /* @__PURE__ */ new Set());
40
+ __privateAdd(this, _statusCallbacks, /* @__PURE__ */ new Set());
41
+ __privateAdd(this, _errorCallbacks, /* @__PURE__ */ new Set());
42
+ this.pushMessage = (message) => {
43
+ __privateSet(this, _messages, __privateGet(this, _messages).concat(message));
44
+ __privateGet(this, _callMessagesCallbacks).call(this);
45
+ };
46
+ this.popMessage = () => {
47
+ __privateSet(this, _messages, __privateGet(this, _messages).slice(0, -1));
48
+ __privateGet(this, _callMessagesCallbacks).call(this);
49
+ };
50
+ this.replaceMessage = (index, message) => {
51
+ __privateSet(this, _messages, [
52
+ ...__privateGet(this, _messages).slice(0, index),
53
+ // We deep clone the message here to ensure the new React Compiler (currently in RC) detects deeply nested parts/metadata changes:
54
+ this.snapshot(message),
55
+ ...__privateGet(this, _messages).slice(index + 1)
56
+ ]);
57
+ __privateGet(this, _callMessagesCallbacks).call(this);
58
+ };
59
+ this.snapshot = (value) => structuredClone(value);
60
+ this["~registerMessagesCallback"] = (onChange, throttleWaitMs) => {
61
+ const callback = throttleWaitMs ? throttle(onChange, throttleWaitMs) : onChange;
62
+ __privateGet(this, _messagesCallbacks).add(callback);
63
+ return () => {
64
+ __privateGet(this, _messagesCallbacks).delete(callback);
65
+ };
66
+ };
67
+ this["~registerStatusCallback"] = (onChange) => {
68
+ __privateGet(this, _statusCallbacks).add(onChange);
69
+ return () => {
70
+ __privateGet(this, _statusCallbacks).delete(onChange);
71
+ };
72
+ };
73
+ this["~registerErrorCallback"] = (onChange) => {
74
+ __privateGet(this, _errorCallbacks).add(onChange);
75
+ return () => {
76
+ __privateGet(this, _errorCallbacks).delete(onChange);
77
+ };
78
+ };
79
+ __privateAdd(this, _callMessagesCallbacks, () => {
80
+ __privateGet(this, _messagesCallbacks).forEach((callback) => callback());
81
+ });
82
+ __privateAdd(this, _callStatusCallbacks, () => {
83
+ __privateGet(this, _statusCallbacks).forEach((callback) => callback());
84
+ });
85
+ __privateAdd(this, _callErrorCallbacks, () => {
86
+ __privateGet(this, _errorCallbacks).forEach((callback) => callback());
87
+ });
88
+ __privateSet(this, _messages, initialMessages);
89
+ }
90
+ get status() {
91
+ return __privateGet(this, _status);
92
+ }
93
+ set status(newStatus) {
94
+ __privateSet(this, _status, newStatus);
95
+ __privateGet(this, _callStatusCallbacks).call(this);
96
+ }
97
+ get error() {
98
+ return __privateGet(this, _error);
99
+ }
100
+ set error(newError) {
101
+ __privateSet(this, _error, newError);
102
+ __privateGet(this, _callErrorCallbacks).call(this);
103
+ }
104
+ get messages() {
105
+ return __privateGet(this, _messages);
106
+ }
107
+ set messages(newMessages) {
108
+ __privateSet(this, _messages, [...newMessages]);
109
+ __privateGet(this, _callMessagesCallbacks).call(this);
110
+ }
111
+ };
112
+ _messages = new WeakMap();
113
+ _status = new WeakMap();
114
+ _error = new WeakMap();
115
+ _messagesCallbacks = new WeakMap();
116
+ _statusCallbacks = new WeakMap();
117
+ _errorCallbacks = new WeakMap();
118
+ _callMessagesCallbacks = new WeakMap();
119
+ _callStatusCallbacks = new WeakMap();
120
+ _callErrorCallbacks = new WeakMap();
121
+ var _state;
122
+ var Chat = class extends AbstractChat {
123
+ constructor({ messages, ...init }) {
124
+ const state = new ReactChatState(messages);
125
+ super({ ...init, state });
126
+ __privateAdd(this, _state, void 0);
127
+ this["~registerMessagesCallback"] = (onChange, throttleWaitMs) => __privateGet(this, _state)["~registerMessagesCallback"](onChange, throttleWaitMs);
128
+ this["~registerStatusCallback"] = (onChange) => __privateGet(this, _state)["~registerStatusCallback"](onChange);
129
+ this["~registerErrorCallback"] = (onChange) => __privateGet(this, _state)["~registerErrorCallback"](onChange);
130
+ __privateSet(this, _state, state);
131
+ }
132
+ };
133
+ _state = new WeakMap();
34
134
 
35
135
  // src/use-chat.ts
36
136
  function useChat({
37
- api = "/api/chat",
38
- id,
39
- initialMessages,
40
- initialInput = "",
41
- sendExtraMessageFields,
42
- onToolCall,
43
- experimental_prepareRequestBody,
44
- maxSteps = 1,
45
- streamProtocol = "data",
46
- onResponse,
47
- onFinish,
48
- onError,
49
- credentials,
50
- headers,
51
- body,
52
- generateId = generateIdFunc,
53
- fetch: fetch2,
54
- keepLastMessageOnError = true,
55
- experimental_throttle: throttleWaitMs
137
+ experimental_throttle: throttleWaitMs,
138
+ resume = false,
139
+ ...options
56
140
  } = {}) {
57
- const [hookId] = useState2(generateId);
58
- const chatId = id != null ? id : hookId;
59
- const chatKey = typeof api === "string" ? [api, chatId] : chatId;
60
- const stableInitialMessages = useStableValue(initialMessages != null ? initialMessages : []);
61
- const processedInitialMessages = useMemo(
62
- () => fillMessageParts(stableInitialMessages),
63
- [stableInitialMessages]
141
+ const chatRef = useRef(
142
+ "chat" in options ? options.chat : new Chat(options)
64
143
  );
65
- const { data: messages, mutate } = useSWR(
66
- [chatKey, "messages"],
67
- null,
68
- { fallbackData: processedInitialMessages }
144
+ const shouldRecreateChat = "chat" in options && options.chat !== chatRef.current || "id" in options && chatRef.current.id !== options.id;
145
+ if (shouldRecreateChat) {
146
+ chatRef.current = "chat" in options ? options.chat : new Chat(options);
147
+ }
148
+ const optionsId = "id" in options ? options.id : null;
149
+ const subscribeToMessages = useCallback(
150
+ (update) => chatRef.current["~registerMessagesCallback"](update, throttleWaitMs),
151
+ // optionsId is required to trigger re-subscription when the chat ID changes
152
+ // eslint-disable-next-line react-hooks/exhaustive-deps
153
+ [throttleWaitMs, optionsId]
69
154
  );
70
- const messagesRef = useRef(messages || []);
71
- useEffect2(() => {
72
- messagesRef.current = messages || [];
73
- }, [messages]);
74
- const { data: streamData, mutate: mutateStreamData } = useSWR([chatKey, "streamData"], null);
75
- const streamDataRef = useRef(streamData);
76
- useEffect2(() => {
77
- streamDataRef.current = streamData;
78
- }, [streamData]);
79
- const { data: status = "ready", mutate: mutateStatus } = useSWR([chatKey, "status"], null);
80
- const { data: error = void 0, mutate: setError } = useSWR([chatKey, "error"], null);
81
- const abortControllerRef = useRef(null);
82
- const extraMetadataRef = useRef({
83
- credentials,
84
- headers,
85
- body
86
- });
87
- useEffect2(() => {
88
- extraMetadataRef.current = {
89
- credentials,
90
- headers,
91
- body
92
- };
93
- }, [credentials, headers, body]);
94
- const triggerRequest = useCallback(
95
- async (chatRequest) => {
96
- var _a, _b;
97
- mutateStatus("submitted");
98
- setError(void 0);
99
- const chatMessages = fillMessageParts(chatRequest.messages);
100
- const messageCount = chatMessages.length;
101
- const maxStep = extractMaxToolInvocationStep(
102
- (_a = chatMessages[chatMessages.length - 1]) == null ? void 0 : _a.toolInvocations
103
- );
104
- try {
105
- const abortController = new AbortController();
106
- abortControllerRef.current = abortController;
107
- const throttledMutate = throttle(mutate, throttleWaitMs);
108
- const throttledMutateStreamData = throttle(
109
- mutateStreamData,
110
- throttleWaitMs
111
- );
112
- const previousMessages = messagesRef.current;
113
- throttledMutate(chatMessages, false);
114
- const constructedMessagesPayload = sendExtraMessageFields ? chatMessages : chatMessages.map(
115
- ({
116
- role,
117
- content,
118
- experimental_attachments,
119
- data,
120
- annotations,
121
- toolInvocations,
122
- parts
123
- }) => ({
124
- role,
125
- content,
126
- ...experimental_attachments !== void 0 && {
127
- experimental_attachments
128
- },
129
- ...data !== void 0 && { data },
130
- ...annotations !== void 0 && { annotations },
131
- ...toolInvocations !== void 0 && { toolInvocations },
132
- ...parts !== void 0 && { parts }
133
- })
134
- );
135
- const existingData = streamDataRef.current;
136
- await callChatApi({
137
- api,
138
- body: (_b = experimental_prepareRequestBody == null ? void 0 : experimental_prepareRequestBody({
139
- id: chatId,
140
- messages: chatMessages,
141
- requestData: chatRequest.data,
142
- requestBody: chatRequest.body
143
- })) != null ? _b : {
144
- id: chatId,
145
- messages: constructedMessagesPayload,
146
- data: chatRequest.data,
147
- ...extraMetadataRef.current.body,
148
- ...chatRequest.body
149
- },
150
- streamProtocol,
151
- credentials: extraMetadataRef.current.credentials,
152
- headers: {
153
- ...extraMetadataRef.current.headers,
154
- ...chatRequest.headers
155
- },
156
- abortController: () => abortControllerRef.current,
157
- restoreMessagesOnFailure() {
158
- if (!keepLastMessageOnError) {
159
- throttledMutate(previousMessages, false);
160
- }
161
- },
162
- onResponse,
163
- onUpdate({ message, data, replaceLastMessage }) {
164
- mutateStatus("streaming");
165
- throttledMutate(
166
- [
167
- ...replaceLastMessage ? chatMessages.slice(0, chatMessages.length - 1) : chatMessages,
168
- message
169
- ],
170
- false
171
- );
172
- if (data == null ? void 0 : data.length) {
173
- throttledMutateStreamData(
174
- [...existingData != null ? existingData : [], ...data],
175
- false
176
- );
177
- }
178
- },
179
- onToolCall,
180
- onFinish,
181
- generateId,
182
- fetch: fetch2,
183
- lastMessage: chatMessages[chatMessages.length - 1]
184
- });
185
- abortControllerRef.current = null;
186
- mutateStatus("ready");
187
- } catch (err) {
188
- if (err.name === "AbortError") {
189
- abortControllerRef.current = null;
190
- mutateStatus("ready");
191
- return null;
192
- }
193
- if (onError && err instanceof Error) {
194
- onError(err);
195
- }
196
- setError(err);
197
- mutateStatus("error");
198
- }
199
- const messages2 = messagesRef.current;
200
- if (shouldResubmitMessages({
201
- originalMaxToolInvocationStep: maxStep,
202
- originalMessageCount: messageCount,
203
- maxSteps,
204
- messages: messages2
205
- })) {
206
- await triggerRequest({ messages: messages2 });
207
- }
208
- },
209
- [
210
- mutate,
211
- mutateStatus,
212
- api,
213
- extraMetadataRef,
214
- onResponse,
215
- onFinish,
216
- onError,
217
- setError,
218
- mutateStreamData,
219
- streamDataRef,
220
- streamProtocol,
221
- sendExtraMessageFields,
222
- experimental_prepareRequestBody,
223
- onToolCall,
224
- maxSteps,
225
- messagesRef,
226
- abortControllerRef,
227
- generateId,
228
- fetch2,
229
- keepLastMessageOnError,
230
- throttleWaitMs,
231
- chatId
232
- ]
155
+ const messages = useSyncExternalStore(
156
+ subscribeToMessages,
157
+ () => chatRef.current.messages,
158
+ () => chatRef.current.messages
233
159
  );
234
- const append = useCallback(
235
- async (message, {
236
- data,
237
- headers: headers2,
238
- body: body2,
239
- experimental_attachments
240
- } = {}) => {
241
- var _a, _b;
242
- const attachmentsForRequest = await prepareAttachmentsForRequest(
243
- experimental_attachments
244
- );
245
- const messages2 = messagesRef.current.concat({
246
- ...message,
247
- id: (_a = message.id) != null ? _a : generateId(),
248
- createdAt: (_b = message.createdAt) != null ? _b : /* @__PURE__ */ new Date(),
249
- experimental_attachments: attachmentsForRequest.length > 0 ? attachmentsForRequest : void 0,
250
- parts: getMessageParts(message)
251
- });
252
- return triggerRequest({ messages: messages2, headers: headers2, body: body2, data });
253
- },
254
- [triggerRequest, generateId]
160
+ const status = useSyncExternalStore(
161
+ chatRef.current["~registerStatusCallback"],
162
+ () => chatRef.current.status,
163
+ () => chatRef.current.status
255
164
  );
256
- const reload = useCallback(
257
- async ({ data, headers: headers2, body: body2 } = {}) => {
258
- const messages2 = messagesRef.current;
259
- if (messages2.length === 0) {
260
- return null;
261
- }
262
- const lastMessage = messages2[messages2.length - 1];
263
- return triggerRequest({
264
- messages: lastMessage.role === "assistant" ? messages2.slice(0, -1) : messages2,
265
- headers: headers2,
266
- body: body2,
267
- data
268
- });
269
- },
270
- [triggerRequest]
165
+ const error = useSyncExternalStore(
166
+ chatRef.current["~registerErrorCallback"],
167
+ () => chatRef.current.error,
168
+ () => chatRef.current.error
271
169
  );
272
- const stop = useCallback(() => {
273
- if (abortControllerRef.current) {
274
- abortControllerRef.current.abort();
275
- abortControllerRef.current = null;
276
- }
277
- }, []);
278
170
  const setMessages = useCallback(
279
- (messages2) => {
280
- if (typeof messages2 === "function") {
281
- messages2 = messages2(messagesRef.current);
282
- }
283
- const messagesWithParts = fillMessageParts(messages2);
284
- mutate(messagesWithParts, false);
285
- messagesRef.current = messagesWithParts;
286
- },
287
- [mutate]
288
- );
289
- const setData = useCallback(
290
- (data) => {
291
- if (typeof data === "function") {
292
- data = data(streamDataRef.current);
293
- }
294
- mutateStreamData(data, false);
295
- streamDataRef.current = data;
296
- },
297
- [mutateStreamData]
298
- );
299
- const [input, setInput] = useState2(initialInput);
300
- const handleSubmit = useCallback(
301
- async (event, options = {}, metadata) => {
302
- var _a;
303
- (_a = event == null ? void 0 : event.preventDefault) == null ? void 0 : _a.call(event);
304
- if (!input && !options.allowEmptySubmit)
305
- return;
306
- if (metadata) {
307
- extraMetadataRef.current = {
308
- ...extraMetadataRef.current,
309
- ...metadata
310
- };
171
+ (messagesParam) => {
172
+ if (typeof messagesParam === "function") {
173
+ messagesParam = messagesParam(chatRef.current.messages);
311
174
  }
312
- const attachmentsForRequest = await prepareAttachmentsForRequest(
313
- options.experimental_attachments
314
- );
315
- const messages2 = messagesRef.current.concat({
316
- id: generateId(),
317
- createdAt: /* @__PURE__ */ new Date(),
318
- role: "user",
319
- content: input,
320
- experimental_attachments: attachmentsForRequest.length > 0 ? attachmentsForRequest : void 0,
321
- parts: [{ type: "text", text: input }]
322
- });
323
- const chatRequest = {
324
- messages: messages2,
325
- headers: options.headers,
326
- body: options.body,
327
- data: options.data
328
- };
329
- triggerRequest(chatRequest);
330
- setInput("");
175
+ chatRef.current.messages = messagesParam;
331
176
  },
332
- [input, generateId, triggerRequest]
333
- );
334
- const handleInputChange = (e) => {
335
- setInput(e.target.value);
336
- };
337
- const addToolResult = useCallback(
338
- ({ toolCallId, result }) => {
339
- const currentMessages = messagesRef.current;
340
- updateToolCallResult({
341
- messages: currentMessages,
342
- toolCallId,
343
- toolResult: result
344
- });
345
- mutate(
346
- [
347
- ...currentMessages.slice(0, currentMessages.length - 1),
348
- { ...currentMessages[currentMessages.length - 1] }
349
- ],
350
- false
351
- );
352
- if (status === "submitted" || status === "streaming") {
353
- return;
354
- }
355
- const lastMessage = currentMessages[currentMessages.length - 1];
356
- if (isAssistantMessageWithCompletedToolCalls(lastMessage)) {
357
- triggerRequest({ messages: currentMessages });
358
- }
359
- },
360
- [mutate, status, triggerRequest]
177
+ [chatRef]
361
178
  );
179
+ useEffect(() => {
180
+ if (resume) {
181
+ chatRef.current.resumeStream();
182
+ }
183
+ }, [resume, chatRef]);
362
184
  return {
363
- messages: messages != null ? messages : [],
364
- id: chatId,
185
+ id: chatRef.current.id,
186
+ messages,
365
187
  setMessages,
366
- data: streamData,
367
- setData,
188
+ sendMessage: chatRef.current.sendMessage,
189
+ regenerate: chatRef.current.regenerate,
190
+ clearError: chatRef.current.clearError,
191
+ stop: chatRef.current.stop,
368
192
  error,
369
- append,
370
- reload,
371
- stop,
372
- input,
373
- setInput,
374
- handleInputChange,
375
- handleSubmit,
376
- isLoading: status === "submitted" || status === "streaming",
193
+ resumeStream: chatRef.current.resumeStream,
377
194
  status,
378
- addToolResult
195
+ addToolResult: chatRef.current.addToolResult
379
196
  };
380
197
  }
381
198
 
@@ -383,8 +200,8 @@ function useChat({
383
200
  import {
384
201
  callCompletionApi
385
202
  } from "ai";
386
- import { useCallback as useCallback2, useEffect as useEffect3, useId, useRef as useRef2, useState as useState3 } from "react";
387
- import useSWR2 from "swr";
203
+ import { useCallback as useCallback2, useEffect as useEffect2, useId, useRef as useRef2, useState } from "react";
204
+ import useSWR from "swr";
388
205
  function useCompletion({
389
206
  api = "/api/completion",
390
207
  id,
@@ -395,30 +212,28 @@ function useCompletion({
395
212
  body,
396
213
  streamProtocol = "data",
397
214
  fetch: fetch2,
398
- onResponse,
399
215
  onFinish,
400
216
  onError,
401
217
  experimental_throttle: throttleWaitMs
402
218
  } = {}) {
403
219
  const hookId = useId();
404
220
  const completionId = id || hookId;
405
- const { data, mutate } = useSWR2([api, completionId], null, {
221
+ const { data, mutate } = useSWR([api, completionId], null, {
406
222
  fallbackData: initialCompletion
407
223
  });
408
- const { data: isLoading = false, mutate: mutateLoading } = useSWR2(
224
+ const { data: isLoading = false, mutate: mutateLoading } = useSWR(
409
225
  [completionId, "loading"],
410
226
  null
411
227
  );
412
- const { data: streamData, mutate: mutateStreamData } = useSWR2([completionId, "streamData"], null);
413
- const [error, setError] = useState3(void 0);
228
+ const [error, setError] = useState(void 0);
414
229
  const completion = data;
415
- const [abortController, setAbortController] = useState3(null);
230
+ const [abortController, setAbortController] = useState(null);
416
231
  const extraMetadataRef = useRef2({
417
232
  credentials,
418
233
  headers,
419
234
  body
420
235
  });
421
- useEffect3(() => {
236
+ useEffect2(() => {
422
237
  extraMetadataRef.current = {
423
238
  credentials,
424
239
  headers,
@@ -442,14 +257,9 @@ function useCompletion({
442
257
  (completion2) => mutate(completion2, false),
443
258
  throttleWaitMs
444
259
  ),
445
- onData: throttle(
446
- (data2) => mutateStreamData([...streamData != null ? streamData : [], ...data2 != null ? data2 : []], false),
447
- throttleWaitMs
448
- ),
449
260
  setLoading: mutateLoading,
450
261
  setError,
451
262
  setAbortController,
452
- onResponse,
453
263
  onFinish,
454
264
  onError
455
265
  }),
@@ -459,14 +269,11 @@ function useCompletion({
459
269
  api,
460
270
  extraMetadataRef,
461
271
  setAbortController,
462
- onResponse,
463
272
  onFinish,
464
273
  onError,
465
274
  setError,
466
- streamData,
467
275
  streamProtocol,
468
276
  fetch2,
469
- mutateStreamData,
470
277
  throttleWaitMs
471
278
  ]
472
279
  );
@@ -488,7 +295,7 @@ function useCompletion({
488
295
  },
489
296
  [triggerRequest]
490
297
  );
491
- const [input, setInput] = useState3(initialInput);
298
+ const [input, setInput] = useState(initialInput);
492
299
  const handleSubmit = useCallback2(
493
300
  (event) => {
494
301
  var _a;
@@ -513,8 +320,7 @@ function useCompletion({
513
320
  setInput,
514
321
  handleInputChange,
515
322
  handleSubmit,
516
- isLoading,
517
- data: streamData
323
+ isLoading
518
324
  };
519
325
  }
520
326
 
@@ -525,11 +331,11 @@ import {
525
331
  } from "@ai-sdk/provider-utils";
526
332
  import {
527
333
  asSchema,
528
- isDeepEqualData as isDeepEqualData2,
334
+ isDeepEqualData,
529
335
  parsePartialJson
530
336
  } from "ai";
531
- import { useCallback as useCallback3, useId as useId2, useRef as useRef3, useState as useState4 } from "react";
532
- import useSWR3 from "swr";
337
+ import { useCallback as useCallback3, useId as useId2, useRef as useRef3, useState as useState2 } from "react";
338
+ import useSWR2 from "swr";
533
339
  var getOriginalFetch = () => fetch;
534
340
  function useObject({
535
341
  api,
@@ -545,13 +351,13 @@ function useObject({
545
351
  }) {
546
352
  const hookId = useId2();
547
353
  const completionId = id != null ? id : hookId;
548
- const { data, mutate } = useSWR3(
354
+ const { data, mutate } = useSWR2(
549
355
  [api, completionId],
550
356
  null,
551
357
  { fallbackData: initialValue }
552
358
  );
553
- const [error, setError] = useState4(void 0);
554
- const [isLoading, setIsLoading] = useState4(false);
359
+ const [error, setError] = useState2(void 0);
360
+ const [isLoading, setIsLoading] = useState2(false);
555
361
  const abortControllerRef = useRef3(null);
556
362
  const stop = useCallback3(() => {
557
363
  var _a;
@@ -566,9 +372,8 @@ function useObject({
566
372
  const submit = async (input) => {
567
373
  var _a;
568
374
  try {
569
- mutate(void 0);
375
+ clearObject();
570
376
  setIsLoading(true);
571
- setError(void 0);
572
377
  const abortController = new AbortController();
573
378
  abortControllerRef.current = abortController;
574
379
  const actualFetch = fetch2 != null ? fetch2 : getOriginalFetch();
@@ -594,20 +399,20 @@ function useObject({
594
399
  let latestObject = void 0;
595
400
  await response.body.pipeThrough(new TextDecoderStream()).pipeTo(
596
401
  new WritableStream({
597
- write(chunk) {
402
+ async write(chunk) {
598
403
  accumulatedText += chunk;
599
- const { value } = parsePartialJson(accumulatedText);
404
+ const { value } = await parsePartialJson(accumulatedText);
600
405
  const currentObject = value;
601
- if (!isDeepEqualData2(latestObject, currentObject)) {
406
+ if (!isDeepEqualData(latestObject, currentObject)) {
602
407
  latestObject = currentObject;
603
408
  mutate(currentObject);
604
409
  }
605
410
  },
606
- close() {
411
+ async close() {
607
412
  setIsLoading(false);
608
413
  abortControllerRef.current = null;
609
414
  if (onFinish != null) {
610
- const validationResult = safeValidateTypes({
415
+ const validationResult = await safeValidateTypes({
611
416
  value: latestObject,
612
417
  schema: asSchema(schema)
613
418
  });
@@ -629,16 +434,27 @@ function useObject({
629
434
  setError(error2 instanceof Error ? error2 : new Error(String(error2)));
630
435
  }
631
436
  };
437
+ const clear = () => {
438
+ stop();
439
+ clearObject();
440
+ };
441
+ const clearObject = () => {
442
+ setError(void 0);
443
+ setIsLoading(false);
444
+ mutate(void 0);
445
+ };
632
446
  return {
633
447
  submit,
634
448
  object: data,
635
449
  error,
636
450
  isLoading,
637
- stop
451
+ stop,
452
+ clear
638
453
  };
639
454
  }
640
455
  var experimental_useObject = useObject;
641
456
  export {
457
+ Chat,
642
458
  experimental_useObject,
643
459
  useChat,
644
460
  useCompletion