@copilotkitnext/react 0.0.7 → 0.0.9-alpha.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.mts +41 -19
- package/dist/index.d.ts +41 -19
- package/dist/index.js +275 -138
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +286 -150
- package/dist/index.mjs.map +1 -1
- package/dist/styles.css +1 -1
- package/package.json +8 -7
package/dist/index.mjs
CHANGED
|
@@ -11,6 +11,7 @@ import { Plus, Settings2, Mic, ArrowUp, X, Check } from "lucide-react";
|
|
|
11
11
|
|
|
12
12
|
// src/providers/CopilotChatConfigurationProvider.tsx
|
|
13
13
|
import { createContext, useContext } from "react";
|
|
14
|
+
import { DEFAULT_AGENT_ID } from "@copilotkitnext/shared";
|
|
14
15
|
import { jsx } from "react/jsx-runtime";
|
|
15
16
|
var CopilotChatDefaultLabels = {
|
|
16
17
|
chatInputPlaceholder: "Type a message...",
|
|
@@ -31,16 +32,20 @@ var CopilotChatDefaultLabels = {
|
|
|
31
32
|
chatDisclaimerText: "AI can make mistakes. Please verify important information."
|
|
32
33
|
};
|
|
33
34
|
var CopilotChatConfiguration = createContext(null);
|
|
34
|
-
var CopilotChatConfigurationProvider = ({
|
|
35
|
+
var CopilotChatConfigurationProvider = ({
|
|
36
|
+
children,
|
|
37
|
+
labels = {},
|
|
38
|
+
agentId,
|
|
39
|
+
threadId
|
|
40
|
+
}) => {
|
|
35
41
|
const mergedLabels = {
|
|
36
42
|
...CopilotChatDefaultLabels,
|
|
37
43
|
...labels
|
|
38
44
|
};
|
|
39
45
|
const configurationValue = {
|
|
40
46
|
labels: mergedLabels,
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
onChangeInput
|
|
47
|
+
agentId: agentId ?? DEFAULT_AGENT_ID,
|
|
48
|
+
threadId
|
|
44
49
|
};
|
|
45
50
|
return /* @__PURE__ */ jsx(CopilotChatConfiguration.Provider, { value: configurationValue, children });
|
|
46
51
|
};
|
|
@@ -490,10 +495,14 @@ function CopilotChatInput({
|
|
|
490
495
|
className,
|
|
491
496
|
...props
|
|
492
497
|
}) {
|
|
493
|
-
const
|
|
494
|
-
value
|
|
495
|
-
|
|
496
|
-
|
|
498
|
+
const isControlled = value !== void 0;
|
|
499
|
+
const [internalValue, setInternalValue] = useState(() => value ?? "");
|
|
500
|
+
useEffect2(() => {
|
|
501
|
+
if (!isControlled && value !== void 0) {
|
|
502
|
+
setInternalValue(value);
|
|
503
|
+
}
|
|
504
|
+
}, [isControlled, value]);
|
|
505
|
+
const resolvedValue = isControlled ? value ?? "" : internalValue;
|
|
497
506
|
const inputRef = useRef2(null);
|
|
498
507
|
const audioRecorderRef = useRef2(null);
|
|
499
508
|
useEffect2(() => {
|
|
@@ -510,7 +519,11 @@ function CopilotChatInput({
|
|
|
510
519
|
}
|
|
511
520
|
}, [mode]);
|
|
512
521
|
const handleChange = (e) => {
|
|
513
|
-
|
|
522
|
+
const nextValue = e.target.value;
|
|
523
|
+
if (!isControlled) {
|
|
524
|
+
setInternalValue(nextValue);
|
|
525
|
+
}
|
|
526
|
+
onChange?.(nextValue);
|
|
514
527
|
};
|
|
515
528
|
const handleKeyDown = (e) => {
|
|
516
529
|
if (e.key === "Enter" && !e.shiftKey) {
|
|
@@ -519,17 +532,25 @@ function CopilotChatInput({
|
|
|
519
532
|
}
|
|
520
533
|
};
|
|
521
534
|
const send = () => {
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
535
|
+
if (!onSubmitMessage) {
|
|
536
|
+
return;
|
|
537
|
+
}
|
|
538
|
+
const trimmed = resolvedValue.trim();
|
|
539
|
+
if (!trimmed) {
|
|
540
|
+
return;
|
|
541
|
+
}
|
|
542
|
+
onSubmitMessage(trimmed);
|
|
543
|
+
if (!isControlled) {
|
|
544
|
+
setInternalValue("");
|
|
545
|
+
onChange?.("");
|
|
546
|
+
}
|
|
547
|
+
if (inputRef.current) {
|
|
548
|
+
inputRef.current.focus();
|
|
528
549
|
}
|
|
529
550
|
};
|
|
530
551
|
const BoundTextArea = renderSlot(textArea, CopilotChatInput.TextArea, {
|
|
531
552
|
ref: inputRef,
|
|
532
|
-
value,
|
|
553
|
+
value: resolvedValue,
|
|
533
554
|
onChange: handleChange,
|
|
534
555
|
onKeyDown: handleKeyDown,
|
|
535
556
|
autoFocus
|
|
@@ -543,7 +564,7 @@ function CopilotChatInput({
|
|
|
543
564
|
);
|
|
544
565
|
const BoundSendButton = renderSlot(sendButton, CopilotChatInput.SendButton, {
|
|
545
566
|
onClick: send,
|
|
546
|
-
disabled: !
|
|
567
|
+
disabled: !resolvedValue.trim() || !onSubmitMessage
|
|
547
568
|
});
|
|
548
569
|
const BoundStartTranscribeButton = renderSlot(
|
|
549
570
|
startTranscribeButton,
|
|
@@ -879,7 +900,7 @@ import "katex/dist/katex.min.css";
|
|
|
879
900
|
import { completePartialMarkdown } from "@copilotkitnext/core";
|
|
880
901
|
|
|
881
902
|
// src/hooks/use-render-tool-call.tsx
|
|
882
|
-
import { useCallback } from "react";
|
|
903
|
+
import { useCallback, useEffect as useEffect4, useState as useState3 } from "react";
|
|
883
904
|
import { ToolCallStatus } from "@copilotkitnext/core";
|
|
884
905
|
|
|
885
906
|
// src/providers/CopilotKitProvider.tsx
|
|
@@ -979,13 +1000,9 @@ var CopilotKitProvider = ({
|
|
|
979
1000
|
return { tools: processedTools, renderToolCalls: processedRenderToolCalls };
|
|
980
1001
|
}, [humanInTheLoopList]);
|
|
981
1002
|
const allTools = useMemo(() => {
|
|
982
|
-
const tools =
|
|
983
|
-
|
|
984
|
-
|
|
985
|
-
});
|
|
986
|
-
processedHumanInTheLoopTools.tools.forEach((tool) => {
|
|
987
|
-
tools[tool.name] = tool;
|
|
988
|
-
});
|
|
1003
|
+
const tools = [];
|
|
1004
|
+
tools.push(...frontendToolsList);
|
|
1005
|
+
tools.push(...processedHumanInTheLoopTools.tools);
|
|
989
1006
|
return tools;
|
|
990
1007
|
}, [frontendToolsList, processedHumanInTheLoopTools]);
|
|
991
1008
|
const allRenderToolCalls = useMemo(() => {
|
|
@@ -1015,9 +1032,30 @@ var CopilotKitProvider = ({
|
|
|
1015
1032
|
return copilotkit2;
|
|
1016
1033
|
}, [allTools]);
|
|
1017
1034
|
useEffect3(() => {
|
|
1018
|
-
setCurrentRenderToolCalls(
|
|
1019
|
-
(
|
|
1020
|
-
|
|
1035
|
+
setCurrentRenderToolCalls((prev) => {
|
|
1036
|
+
const keyOf = (rc) => `${rc?.agentId ?? ""}:${rc?.name ?? ""}`;
|
|
1037
|
+
const computedMap = /* @__PURE__ */ new Map();
|
|
1038
|
+
for (const rc of allRenderToolCalls) {
|
|
1039
|
+
computedMap.set(keyOf(rc), rc);
|
|
1040
|
+
}
|
|
1041
|
+
const merged = [...computedMap.values()];
|
|
1042
|
+
for (const rc of prev) {
|
|
1043
|
+
const k = keyOf(rc);
|
|
1044
|
+
if (!computedMap.has(k)) merged.push(rc);
|
|
1045
|
+
}
|
|
1046
|
+
const sameLength = merged.length === prev.length;
|
|
1047
|
+
if (sameLength) {
|
|
1048
|
+
let same = true;
|
|
1049
|
+
for (let i = 0; i < merged.length; i++) {
|
|
1050
|
+
if (merged[i] !== prev[i]) {
|
|
1051
|
+
same = false;
|
|
1052
|
+
break;
|
|
1053
|
+
}
|
|
1054
|
+
}
|
|
1055
|
+
if (same) return prev;
|
|
1056
|
+
}
|
|
1057
|
+
return merged;
|
|
1058
|
+
});
|
|
1021
1059
|
}, [allRenderToolCalls]);
|
|
1022
1060
|
useEffect3(() => {
|
|
1023
1061
|
copilotkit.setRuntimeUrl(runtimeUrl);
|
|
@@ -1046,10 +1084,7 @@ var useCopilotKit = () => {
|
|
|
1046
1084
|
}
|
|
1047
1085
|
useEffect3(() => {
|
|
1048
1086
|
const unsubscribe = context.copilotkit.subscribe({
|
|
1049
|
-
|
|
1050
|
-
forceUpdate();
|
|
1051
|
-
},
|
|
1052
|
-
onRuntimeLoadError: () => {
|
|
1087
|
+
onRuntimeConnectionStatusChanged: () => {
|
|
1053
1088
|
forceUpdate();
|
|
1054
1089
|
}
|
|
1055
1090
|
});
|
|
@@ -1064,35 +1099,73 @@ var useCopilotKit = () => {
|
|
|
1064
1099
|
import { partialJSONParse } from "@copilotkitnext/shared";
|
|
1065
1100
|
import { jsx as jsx8 } from "react/jsx-runtime";
|
|
1066
1101
|
function useRenderToolCall() {
|
|
1067
|
-
const { currentRenderToolCalls } = useCopilotKit();
|
|
1102
|
+
const { currentRenderToolCalls, copilotkit } = useCopilotKit();
|
|
1103
|
+
const { agentId } = useCopilotChatConfiguration();
|
|
1104
|
+
const [executingToolCallIds, setExecutingToolCallIds] = useState3(() => /* @__PURE__ */ new Set());
|
|
1105
|
+
useEffect4(() => {
|
|
1106
|
+
const unsubscribe = copilotkit.subscribe({
|
|
1107
|
+
onToolExecutionStart: ({ toolCallId }) => {
|
|
1108
|
+
setExecutingToolCallIds((prev) => {
|
|
1109
|
+
if (prev.has(toolCallId)) return prev;
|
|
1110
|
+
const next = new Set(prev);
|
|
1111
|
+
next.add(toolCallId);
|
|
1112
|
+
return next;
|
|
1113
|
+
});
|
|
1114
|
+
},
|
|
1115
|
+
onToolExecutionEnd: ({ toolCallId }) => {
|
|
1116
|
+
setExecutingToolCallIds((prev) => {
|
|
1117
|
+
if (!prev.has(toolCallId)) return prev;
|
|
1118
|
+
const next = new Set(prev);
|
|
1119
|
+
next.delete(toolCallId);
|
|
1120
|
+
return next;
|
|
1121
|
+
});
|
|
1122
|
+
}
|
|
1123
|
+
});
|
|
1124
|
+
return () => unsubscribe();
|
|
1125
|
+
}, [copilotkit]);
|
|
1068
1126
|
const renderToolCall = useCallback(
|
|
1069
1127
|
({
|
|
1070
1128
|
toolCall,
|
|
1071
1129
|
toolMessage,
|
|
1072
|
-
|
|
1130
|
+
isRunning
|
|
1073
1131
|
}) => {
|
|
1074
|
-
const
|
|
1132
|
+
const exactMatches = currentRenderToolCalls.filter(
|
|
1075
1133
|
(rc) => rc.name === toolCall.function.name
|
|
1076
|
-
)
|
|
1134
|
+
);
|
|
1135
|
+
const renderConfig = exactMatches.find((rc) => rc.agentId === agentId) || exactMatches.find((rc) => !rc.agentId) || exactMatches[0] || currentRenderToolCalls.find((rc) => rc.name === "*");
|
|
1077
1136
|
if (!renderConfig) {
|
|
1078
1137
|
return null;
|
|
1079
1138
|
}
|
|
1080
1139
|
const RenderComponent = renderConfig.render;
|
|
1081
1140
|
const args = partialJSONParse(toolCall.function.arguments);
|
|
1141
|
+
const toolName = toolCall.function.name;
|
|
1082
1142
|
if (toolMessage) {
|
|
1083
1143
|
return /* @__PURE__ */ jsx8(
|
|
1084
1144
|
RenderComponent,
|
|
1085
1145
|
{
|
|
1146
|
+
name: toolName,
|
|
1086
1147
|
args,
|
|
1087
1148
|
status: ToolCallStatus.Complete,
|
|
1088
1149
|
result: toolMessage.content
|
|
1089
1150
|
},
|
|
1090
1151
|
toolCall.id
|
|
1091
1152
|
);
|
|
1092
|
-
} else if (
|
|
1153
|
+
} else if (executingToolCallIds.has(toolCall.id)) {
|
|
1154
|
+
return /* @__PURE__ */ jsx8(
|
|
1155
|
+
RenderComponent,
|
|
1156
|
+
{
|
|
1157
|
+
name: toolName,
|
|
1158
|
+
args,
|
|
1159
|
+
status: ToolCallStatus.Executing,
|
|
1160
|
+
result: void 0
|
|
1161
|
+
},
|
|
1162
|
+
toolCall.id
|
|
1163
|
+
);
|
|
1164
|
+
} else if (isRunning) {
|
|
1093
1165
|
return /* @__PURE__ */ jsx8(
|
|
1094
1166
|
RenderComponent,
|
|
1095
1167
|
{
|
|
1168
|
+
name: toolName,
|
|
1096
1169
|
args,
|
|
1097
1170
|
status: ToolCallStatus.InProgress,
|
|
1098
1171
|
result: void 0
|
|
@@ -1103,6 +1176,7 @@ function useRenderToolCall() {
|
|
|
1103
1176
|
return /* @__PURE__ */ jsx8(
|
|
1104
1177
|
RenderComponent,
|
|
1105
1178
|
{
|
|
1179
|
+
name: toolName,
|
|
1106
1180
|
args,
|
|
1107
1181
|
status: ToolCallStatus.Complete,
|
|
1108
1182
|
result: ""
|
|
@@ -1111,54 +1185,57 @@ function useRenderToolCall() {
|
|
|
1111
1185
|
);
|
|
1112
1186
|
}
|
|
1113
1187
|
},
|
|
1114
|
-
[currentRenderToolCalls]
|
|
1188
|
+
[currentRenderToolCalls, executingToolCallIds, agentId]
|
|
1115
1189
|
);
|
|
1116
1190
|
return renderToolCall;
|
|
1117
1191
|
}
|
|
1118
1192
|
|
|
1119
1193
|
// src/hooks/use-frontend-tool.tsx
|
|
1120
|
-
import { useEffect as
|
|
1194
|
+
import { useEffect as useEffect5 } from "react";
|
|
1121
1195
|
function useFrontendTool(tool) {
|
|
1122
|
-
const {
|
|
1123
|
-
|
|
1124
|
-
|
|
1196
|
+
const { copilotkit, setCurrentRenderToolCalls } = useCopilotKit();
|
|
1197
|
+
useEffect5(() => {
|
|
1198
|
+
const name = tool.name;
|
|
1199
|
+
if (copilotkit.getTool({ toolName: name, agentId: tool.agentId })) {
|
|
1125
1200
|
console.warn(
|
|
1126
|
-
`Tool '${
|
|
1201
|
+
`Tool '${name}' already exists for agent '${tool.agentId || "global"}'. Overriding with latest registration.`
|
|
1127
1202
|
);
|
|
1203
|
+
copilotkit.removeTool(name, tool.agentId);
|
|
1128
1204
|
}
|
|
1129
1205
|
copilotkit.addTool(tool);
|
|
1130
|
-
if (tool.render
|
|
1131
|
-
|
|
1132
|
-
|
|
1133
|
-
|
|
1134
|
-
|
|
1135
|
-
|
|
1136
|
-
|
|
1137
|
-
|
|
1138
|
-
|
|
1139
|
-
|
|
1140
|
-
|
|
1141
|
-
|
|
1142
|
-
|
|
1143
|
-
|
|
1206
|
+
if (tool.render) {
|
|
1207
|
+
setCurrentRenderToolCalls((prev) => {
|
|
1208
|
+
const replaced = prev.filter(
|
|
1209
|
+
(rc) => !(rc.name === name && rc.agentId === tool.agentId)
|
|
1210
|
+
);
|
|
1211
|
+
return [
|
|
1212
|
+
...replaced,
|
|
1213
|
+
{
|
|
1214
|
+
name,
|
|
1215
|
+
args: tool.parameters,
|
|
1216
|
+
agentId: tool.agentId,
|
|
1217
|
+
render: tool.render
|
|
1218
|
+
}
|
|
1219
|
+
];
|
|
1220
|
+
});
|
|
1144
1221
|
}
|
|
1145
1222
|
return () => {
|
|
1146
|
-
copilotkit.removeTool(tool.
|
|
1147
|
-
setCurrentRenderToolCalls(
|
|
1148
|
-
(prev) => prev.filter((rc) => rc.name !== tool.name)
|
|
1149
|
-
);
|
|
1223
|
+
copilotkit.removeTool(name, tool.agentId);
|
|
1150
1224
|
};
|
|
1151
|
-
}, [tool, copilotkit,
|
|
1225
|
+
}, [tool.name, copilotkit, setCurrentRenderToolCalls]);
|
|
1152
1226
|
}
|
|
1153
1227
|
|
|
1154
1228
|
// src/hooks/use-human-in-the-loop.tsx
|
|
1155
|
-
import { useState as
|
|
1229
|
+
import { useState as useState4, useCallback as useCallback2, useRef as useRef4, useEffect as useEffect6 } from "react";
|
|
1156
1230
|
import React6 from "react";
|
|
1157
1231
|
function useHumanInTheLoop(tool) {
|
|
1158
|
-
const [status, setStatus] =
|
|
1232
|
+
const [status, setStatus] = useState4(
|
|
1159
1233
|
"inProgress"
|
|
1160
1234
|
);
|
|
1235
|
+
const statusRef = useRef4(status);
|
|
1161
1236
|
const resolvePromiseRef = useRef4(null);
|
|
1237
|
+
const { setCurrentRenderToolCalls } = useCopilotKit();
|
|
1238
|
+
statusRef.current = status;
|
|
1162
1239
|
const respond = useCallback2(async (result) => {
|
|
1163
1240
|
if (resolvePromiseRef.current) {
|
|
1164
1241
|
resolvePromiseRef.current(result);
|
|
@@ -1175,7 +1252,8 @@ function useHumanInTheLoop(tool) {
|
|
|
1175
1252
|
const RenderComponent = useCallback2(
|
|
1176
1253
|
(props) => {
|
|
1177
1254
|
const ToolComponent = tool.render;
|
|
1178
|
-
|
|
1255
|
+
const currentStatus = statusRef.current;
|
|
1256
|
+
if (currentStatus === "inProgress" && props.status === "inProgress") {
|
|
1179
1257
|
const enhancedProps = {
|
|
1180
1258
|
...props,
|
|
1181
1259
|
name: tool.name,
|
|
@@ -1183,7 +1261,7 @@ function useHumanInTheLoop(tool) {
|
|
|
1183
1261
|
respond: void 0
|
|
1184
1262
|
};
|
|
1185
1263
|
return React6.createElement(ToolComponent, enhancedProps);
|
|
1186
|
-
} else if (
|
|
1264
|
+
} else if (currentStatus === "executing" && props.status === "executing") {
|
|
1187
1265
|
const enhancedProps = {
|
|
1188
1266
|
...props,
|
|
1189
1267
|
name: tool.name,
|
|
@@ -1191,7 +1269,7 @@ function useHumanInTheLoop(tool) {
|
|
|
1191
1269
|
respond
|
|
1192
1270
|
};
|
|
1193
1271
|
return React6.createElement(ToolComponent, enhancedProps);
|
|
1194
|
-
} else if (
|
|
1272
|
+
} else if (currentStatus === "complete" && props.status === "complete") {
|
|
1195
1273
|
const enhancedProps = {
|
|
1196
1274
|
...props,
|
|
1197
1275
|
name: tool.name,
|
|
@@ -1202,7 +1280,7 @@ function useHumanInTheLoop(tool) {
|
|
|
1202
1280
|
}
|
|
1203
1281
|
return React6.createElement(ToolComponent, props);
|
|
1204
1282
|
},
|
|
1205
|
-
[tool.render, tool.name, tool.description,
|
|
1283
|
+
[tool.render, tool.name, tool.description, respond]
|
|
1206
1284
|
);
|
|
1207
1285
|
const frontendTool = {
|
|
1208
1286
|
...tool,
|
|
@@ -1210,51 +1288,84 @@ function useHumanInTheLoop(tool) {
|
|
|
1210
1288
|
render: RenderComponent
|
|
1211
1289
|
};
|
|
1212
1290
|
useFrontendTool(frontendTool);
|
|
1291
|
+
useEffect6(() => {
|
|
1292
|
+
return () => {
|
|
1293
|
+
setCurrentRenderToolCalls(
|
|
1294
|
+
(prev) => prev.filter(
|
|
1295
|
+
(rc) => rc.name !== tool.name || rc.agentId !== tool.agentId
|
|
1296
|
+
)
|
|
1297
|
+
);
|
|
1298
|
+
};
|
|
1299
|
+
}, [setCurrentRenderToolCalls, tool.name, tool.agentId]);
|
|
1213
1300
|
}
|
|
1214
1301
|
|
|
1215
1302
|
// src/hooks/use-agent.tsx
|
|
1216
|
-
import { useMemo as useMemo2, useEffect as
|
|
1217
|
-
import { DEFAULT_AGENT_ID } from "@copilotkitnext/shared";
|
|
1218
|
-
|
|
1219
|
-
|
|
1303
|
+
import { useMemo as useMemo2, useEffect as useEffect7, useReducer as useReducer2 } from "react";
|
|
1304
|
+
import { DEFAULT_AGENT_ID as DEFAULT_AGENT_ID2 } from "@copilotkitnext/shared";
|
|
1305
|
+
var ALL_UPDATES = [
|
|
1306
|
+
"OnMessagesChanged" /* OnMessagesChanged */,
|
|
1307
|
+
"OnStateChanged" /* OnStateChanged */,
|
|
1308
|
+
"OnRunStatusChanged" /* OnRunStatusChanged */
|
|
1309
|
+
];
|
|
1310
|
+
function useAgent({ agentId, updates } = {}) {
|
|
1311
|
+
agentId ??= DEFAULT_AGENT_ID2;
|
|
1220
1312
|
const { copilotkit } = useCopilotKit();
|
|
1221
1313
|
const [, forceUpdate] = useReducer2((x) => x + 1, 0);
|
|
1222
|
-
const
|
|
1314
|
+
const updateFlags = useMemo2(
|
|
1315
|
+
() => updates ?? ALL_UPDATES,
|
|
1316
|
+
[JSON.stringify(updates)]
|
|
1317
|
+
);
|
|
1223
1318
|
const agent = useMemo2(() => {
|
|
1224
1319
|
return copilotkit.getAgent(agentId);
|
|
1225
|
-
}, [
|
|
1226
|
-
|
|
1227
|
-
|
|
1228
|
-
|
|
1320
|
+
}, [
|
|
1321
|
+
agentId,
|
|
1322
|
+
copilotkit.agents,
|
|
1323
|
+
copilotkit.runtimeConnectionStatus,
|
|
1324
|
+
copilotkit
|
|
1325
|
+
]);
|
|
1326
|
+
useEffect7(() => {
|
|
1327
|
+
if (!agent) {
|
|
1328
|
+
return;
|
|
1329
|
+
}
|
|
1330
|
+
if (updateFlags.length === 0) {
|
|
1331
|
+
return;
|
|
1332
|
+
}
|
|
1333
|
+
const handlers = {};
|
|
1334
|
+
if (updateFlags.includes("OnMessagesChanged" /* OnMessagesChanged */)) {
|
|
1335
|
+
handlers.onMessagesChanged = () => {
|
|
1229
1336
|
forceUpdate();
|
|
1230
|
-
}
|
|
1231
|
-
|
|
1337
|
+
};
|
|
1338
|
+
}
|
|
1339
|
+
if (updateFlags.includes("OnStateChanged" /* OnStateChanged */)) {
|
|
1340
|
+
handlers.onStateChanged = () => {
|
|
1232
1341
|
forceUpdate();
|
|
1233
|
-
}
|
|
1234
|
-
|
|
1235
|
-
|
|
1236
|
-
|
|
1237
|
-
|
|
1238
|
-
|
|
1239
|
-
|
|
1240
|
-
|
|
1241
|
-
|
|
1242
|
-
|
|
1243
|
-
|
|
1244
|
-
|
|
1245
|
-
|
|
1342
|
+
};
|
|
1343
|
+
}
|
|
1344
|
+
if (updateFlags.includes("OnRunStatusChanged" /* OnRunStatusChanged */)) {
|
|
1345
|
+
handlers.onRunInitialized = () => {
|
|
1346
|
+
forceUpdate();
|
|
1347
|
+
};
|
|
1348
|
+
handlers.onRunFinalized = () => {
|
|
1349
|
+
forceUpdate();
|
|
1350
|
+
};
|
|
1351
|
+
handlers.onRunFailed = () => {
|
|
1352
|
+
forceUpdate();
|
|
1353
|
+
};
|
|
1354
|
+
}
|
|
1355
|
+
const subscription = agent.subscribe(handlers);
|
|
1356
|
+
return () => subscription.unsubscribe();
|
|
1357
|
+
}, [agent, forceUpdate, JSON.stringify(updateFlags)]);
|
|
1246
1358
|
return {
|
|
1247
|
-
agent
|
|
1248
|
-
isRunning
|
|
1359
|
+
agent
|
|
1249
1360
|
};
|
|
1250
1361
|
}
|
|
1251
1362
|
|
|
1252
1363
|
// src/hooks/use-agent-context.tsx
|
|
1253
|
-
import { useEffect as
|
|
1364
|
+
import { useEffect as useEffect8 } from "react";
|
|
1254
1365
|
function useAgentContext(context) {
|
|
1255
1366
|
const { description, value } = context;
|
|
1256
1367
|
const { copilotkit } = useCopilotKit();
|
|
1257
|
-
|
|
1368
|
+
useEffect8(() => {
|
|
1258
1369
|
if (!copilotkit) return;
|
|
1259
1370
|
const id = copilotkit.addContext(context);
|
|
1260
1371
|
return () => {
|
|
@@ -1269,7 +1380,7 @@ import { Fragment as Fragment2, jsx as jsx9 } from "react/jsx-runtime";
|
|
|
1269
1380
|
function CopilotChatToolCallsView({
|
|
1270
1381
|
message,
|
|
1271
1382
|
messages = [],
|
|
1272
|
-
|
|
1383
|
+
isRunning = false
|
|
1273
1384
|
}) {
|
|
1274
1385
|
const renderToolCall = useRenderToolCall();
|
|
1275
1386
|
if (!message.toolCalls || message.toolCalls.length === 0) {
|
|
@@ -1282,7 +1393,7 @@ function CopilotChatToolCallsView({
|
|
|
1282
1393
|
return /* @__PURE__ */ jsx9(React7.Fragment, { children: renderToolCall({
|
|
1283
1394
|
toolCall,
|
|
1284
1395
|
toolMessage,
|
|
1285
|
-
|
|
1396
|
+
isRunning
|
|
1286
1397
|
}) }, toolCall.id);
|
|
1287
1398
|
}) });
|
|
1288
1399
|
}
|
|
@@ -1293,7 +1404,7 @@ import { Fragment as Fragment3, jsx as jsx10, jsxs as jsxs4 } from "react/jsx-ru
|
|
|
1293
1404
|
function CopilotChatAssistantMessage({
|
|
1294
1405
|
message,
|
|
1295
1406
|
messages,
|
|
1296
|
-
|
|
1407
|
+
isRunning,
|
|
1297
1408
|
onThumbsUp,
|
|
1298
1409
|
onThumbsDown,
|
|
1299
1410
|
onReadAloud,
|
|
@@ -1382,7 +1493,7 @@ function CopilotChatAssistantMessage({
|
|
|
1382
1493
|
{
|
|
1383
1494
|
message,
|
|
1384
1495
|
messages,
|
|
1385
|
-
|
|
1496
|
+
isRunning
|
|
1386
1497
|
}
|
|
1387
1498
|
);
|
|
1388
1499
|
if (children) {
|
|
@@ -1397,7 +1508,7 @@ function CopilotChatAssistantMessage({
|
|
|
1397
1508
|
regenerateButton: boundRegenerateButton,
|
|
1398
1509
|
message,
|
|
1399
1510
|
messages,
|
|
1400
|
-
|
|
1511
|
+
isRunning,
|
|
1401
1512
|
onThumbsUp,
|
|
1402
1513
|
onThumbsDown,
|
|
1403
1514
|
onReadAloud,
|
|
@@ -1870,7 +1981,7 @@ function CopilotChatMessageView({
|
|
|
1870
1981
|
assistantMessage,
|
|
1871
1982
|
userMessage,
|
|
1872
1983
|
cursor,
|
|
1873
|
-
|
|
1984
|
+
isRunning = false,
|
|
1874
1985
|
children,
|
|
1875
1986
|
className,
|
|
1876
1987
|
...props
|
|
@@ -1881,7 +1992,7 @@ function CopilotChatMessageView({
|
|
|
1881
1992
|
key: message.id,
|
|
1882
1993
|
message,
|
|
1883
1994
|
messages,
|
|
1884
|
-
|
|
1995
|
+
isRunning
|
|
1885
1996
|
});
|
|
1886
1997
|
} else if (message.role === "user") {
|
|
1887
1998
|
return renderSlot(userMessage, CopilotChatUserMessage_default, {
|
|
@@ -1892,11 +2003,11 @@ function CopilotChatMessageView({
|
|
|
1892
2003
|
return;
|
|
1893
2004
|
}).filter(Boolean);
|
|
1894
2005
|
if (children) {
|
|
1895
|
-
return children({ messageElements, messages,
|
|
2006
|
+
return children({ messageElements, messages, isRunning });
|
|
1896
2007
|
}
|
|
1897
2008
|
return /* @__PURE__ */ jsxs6("div", { className: twMerge6("flex flex-col", className), ...props, children: [
|
|
1898
2009
|
messageElements,
|
|
1899
|
-
|
|
2010
|
+
isRunning && renderSlot(cursor, CopilotChatMessageView.Cursor, {})
|
|
1900
2011
|
] });
|
|
1901
2012
|
}
|
|
1902
2013
|
CopilotChatMessageView.Cursor = function Cursor({
|
|
@@ -1917,7 +2028,7 @@ CopilotChatMessageView.Cursor = function Cursor({
|
|
|
1917
2028
|
var CopilotChatMessageView_default = CopilotChatMessageView;
|
|
1918
2029
|
|
|
1919
2030
|
// src/components/chat/CopilotChatView.tsx
|
|
1920
|
-
import React8, { useRef as useRef5, useState as useState7, useEffect as
|
|
2031
|
+
import React8, { useRef as useRef5, useState as useState7, useEffect as useEffect9 } from "react";
|
|
1921
2032
|
import { twMerge as twMerge7 } from "tailwind-merge";
|
|
1922
2033
|
import { StickToBottom, useStickToBottom, useStickToBottomContext } from "use-stick-to-bottom";
|
|
1923
2034
|
import { ChevronDown } from "lucide-react";
|
|
@@ -1932,6 +2043,8 @@ function CopilotChatView({
|
|
|
1932
2043
|
disclaimer,
|
|
1933
2044
|
messages = [],
|
|
1934
2045
|
autoScroll = true,
|
|
2046
|
+
inputProps,
|
|
2047
|
+
isRunning = false,
|
|
1935
2048
|
children,
|
|
1936
2049
|
className,
|
|
1937
2050
|
...props
|
|
@@ -1940,7 +2053,7 @@ function CopilotChatView({
|
|
|
1940
2053
|
const [inputContainerHeight, setInputContainerHeight] = useState7(0);
|
|
1941
2054
|
const [isResizing, setIsResizing] = useState7(false);
|
|
1942
2055
|
const resizeTimeoutRef = useRef5(null);
|
|
1943
|
-
|
|
2056
|
+
useEffect9(() => {
|
|
1944
2057
|
const element = inputContainerRef.current;
|
|
1945
2058
|
if (!element) return;
|
|
1946
2059
|
const resizeObserver = new ResizeObserver((entries) => {
|
|
@@ -1971,9 +2084,14 @@ function CopilotChatView({
|
|
|
1971
2084
|
};
|
|
1972
2085
|
}, []);
|
|
1973
2086
|
const BoundMessageView = renderSlot(messageView, CopilotChatMessageView_default, {
|
|
1974
|
-
messages
|
|
2087
|
+
messages,
|
|
2088
|
+
isRunning
|
|
1975
2089
|
});
|
|
1976
|
-
const BoundInput = renderSlot(
|
|
2090
|
+
const BoundInput = renderSlot(
|
|
2091
|
+
input,
|
|
2092
|
+
CopilotChatInput_default,
|
|
2093
|
+
inputProps ?? {}
|
|
2094
|
+
);
|
|
1977
2095
|
const BoundFeather = renderSlot(feather, CopilotChatView.Feather, {});
|
|
1978
2096
|
const BoundScrollView = renderSlot(scrollView, CopilotChatView.ScrollView, {
|
|
1979
2097
|
autoScroll,
|
|
@@ -2055,10 +2173,10 @@ function CopilotChatView({
|
|
|
2055
2173
|
const [hasMounted, setHasMounted] = useState7(false);
|
|
2056
2174
|
const { scrollRef, contentRef, scrollToBottom } = useStickToBottom();
|
|
2057
2175
|
const [showScrollButton, setShowScrollButton] = useState7(false);
|
|
2058
|
-
|
|
2176
|
+
useEffect9(() => {
|
|
2059
2177
|
setHasMounted(true);
|
|
2060
2178
|
}, []);
|
|
2061
|
-
|
|
2179
|
+
useEffect9(() => {
|
|
2062
2180
|
if (autoScroll) return;
|
|
2063
2181
|
const scrollElement = scrollRef.current;
|
|
2064
2182
|
if (!scrollElement) return;
|
|
@@ -2191,83 +2309,100 @@ function CopilotChatView({
|
|
|
2191
2309
|
var CopilotChatView_default = CopilotChatView;
|
|
2192
2310
|
|
|
2193
2311
|
// src/components/chat/CopilotChat.tsx
|
|
2194
|
-
import { DEFAULT_AGENT_ID as
|
|
2195
|
-
import { useCallback as useCallback3,
|
|
2312
|
+
import { DEFAULT_AGENT_ID as DEFAULT_AGENT_ID3, randomUUID } from "@copilotkitnext/shared";
|
|
2313
|
+
import { useCallback as useCallback3, useEffect as useEffect10, useMemo as useMemo3 } from "react";
|
|
2196
2314
|
import { merge } from "ts-deepmerge";
|
|
2315
|
+
import { AGUIConnectNotImplementedError } from "@ag-ui/client";
|
|
2197
2316
|
import { jsx as jsx14 } from "react/jsx-runtime";
|
|
2198
2317
|
function CopilotChat({
|
|
2199
|
-
agentId =
|
|
2318
|
+
agentId = DEFAULT_AGENT_ID3,
|
|
2200
2319
|
threadId,
|
|
2201
2320
|
...props
|
|
2202
2321
|
}) {
|
|
2203
2322
|
const { agent } = useAgent({ agentId });
|
|
2204
|
-
const
|
|
2205
|
-
|
|
2206
|
-
|
|
2207
|
-
|
|
2208
|
-
|
|
2209
|
-
|
|
2210
|
-
|
|
2211
|
-
|
|
2212
|
-
|
|
2213
|
-
|
|
2214
|
-
|
|
2215
|
-
|
|
2216
|
-
},
|
|
2217
|
-
subscriber
|
|
2218
|
-
);
|
|
2219
|
-
setIsLoading(false);
|
|
2323
|
+
const { copilotkit } = useCopilotKit();
|
|
2324
|
+
const resolvedThreadId = useMemo3(() => threadId ?? randomUUID(), [threadId]);
|
|
2325
|
+
useEffect10(() => {
|
|
2326
|
+
const connect = async (agent2) => {
|
|
2327
|
+
try {
|
|
2328
|
+
await copilotkit.connectAgent({ agent: agent2, agentId });
|
|
2329
|
+
} catch (error) {
|
|
2330
|
+
if (error instanceof AGUIConnectNotImplementedError) {
|
|
2331
|
+
} else {
|
|
2332
|
+
throw error;
|
|
2333
|
+
}
|
|
2334
|
+
}
|
|
2220
2335
|
};
|
|
2221
2336
|
if (agent) {
|
|
2222
|
-
agent.threadId =
|
|
2223
|
-
|
|
2224
|
-
connect();
|
|
2225
|
-
} else {
|
|
2226
|
-
setIsLoading(false);
|
|
2227
|
-
}
|
|
2337
|
+
agent.threadId = resolvedThreadId;
|
|
2338
|
+
connect(agent);
|
|
2228
2339
|
}
|
|
2229
2340
|
return () => {
|
|
2230
2341
|
};
|
|
2231
|
-
}, [
|
|
2232
|
-
const [inputValue, setInputValue] = useState8("");
|
|
2342
|
+
}, [resolvedThreadId, agent, copilotkit, agentId]);
|
|
2233
2343
|
const onSubmitInput = useCallback3(
|
|
2234
2344
|
async (value) => {
|
|
2235
|
-
setInputValue("");
|
|
2236
2345
|
agent?.addMessage({
|
|
2237
2346
|
id: randomUUID(),
|
|
2238
2347
|
role: "user",
|
|
2239
2348
|
content: value
|
|
2240
2349
|
});
|
|
2241
|
-
|
|
2242
|
-
|
|
2243
|
-
|
|
2350
|
+
if (agent) {
|
|
2351
|
+
try {
|
|
2352
|
+
await copilotkit.runAgent({ agent, agentId });
|
|
2353
|
+
} catch (error) {
|
|
2354
|
+
console.error("CopilotChat: runAgent failed", error);
|
|
2355
|
+
}
|
|
2356
|
+
}
|
|
2244
2357
|
},
|
|
2245
|
-
[agent]
|
|
2358
|
+
[agent, copilotkit, agentId]
|
|
2246
2359
|
);
|
|
2360
|
+
const {
|
|
2361
|
+
inputProps: providedInputProps,
|
|
2362
|
+
messageView: providedMessageView,
|
|
2363
|
+
...restProps
|
|
2364
|
+
} = props;
|
|
2247
2365
|
const mergedProps = merge(
|
|
2248
2366
|
{
|
|
2249
|
-
|
|
2367
|
+
isRunning: agent?.isRunning ?? false
|
|
2250
2368
|
},
|
|
2251
2369
|
{
|
|
2252
|
-
...
|
|
2253
|
-
...typeof
|
|
2370
|
+
...restProps,
|
|
2371
|
+
...typeof providedMessageView === "string" ? { messageView: { className: providedMessageView } } : providedMessageView !== void 0 ? { messageView: providedMessageView } : {}
|
|
2254
2372
|
}
|
|
2255
2373
|
);
|
|
2256
2374
|
return /* @__PURE__ */ jsx14(
|
|
2257
2375
|
CopilotChatConfigurationProvider,
|
|
2258
2376
|
{
|
|
2259
|
-
|
|
2260
|
-
|
|
2261
|
-
onChangeInput: setInputValue,
|
|
2377
|
+
agentId,
|
|
2378
|
+
threadId: resolvedThreadId,
|
|
2262
2379
|
children: /* @__PURE__ */ jsx14(
|
|
2263
2380
|
CopilotChatView,
|
|
2264
2381
|
{
|
|
2265
|
-
...{
|
|
2382
|
+
...{
|
|
2383
|
+
messages: agent?.messages ?? [],
|
|
2384
|
+
inputProps: {
|
|
2385
|
+
onSubmitMessage: onSubmitInput,
|
|
2386
|
+
...providedInputProps
|
|
2387
|
+
},
|
|
2388
|
+
...mergedProps
|
|
2389
|
+
}
|
|
2266
2390
|
}
|
|
2267
2391
|
)
|
|
2268
2392
|
}
|
|
2269
2393
|
);
|
|
2270
2394
|
}
|
|
2395
|
+
|
|
2396
|
+
// src/types/defineToolCallRender.ts
|
|
2397
|
+
function defineToolCallRender(def) {
|
|
2398
|
+
return {
|
|
2399
|
+
name: def.name,
|
|
2400
|
+
args: def.args,
|
|
2401
|
+
// Coerce to ComponentType to align with ReactToolCallRender
|
|
2402
|
+
render: def.render,
|
|
2403
|
+
...def.agentId ? { agentId: def.agentId } : {}
|
|
2404
|
+
};
|
|
2405
|
+
}
|
|
2271
2406
|
export {
|
|
2272
2407
|
AudioRecorderError,
|
|
2273
2408
|
CopilotChat,
|
|
@@ -2280,6 +2415,7 @@ export {
|
|
|
2280
2415
|
CopilotChatUserMessage_default as CopilotChatUserMessage,
|
|
2281
2416
|
CopilotChatView_default as CopilotChatView,
|
|
2282
2417
|
CopilotKitProvider,
|
|
2418
|
+
defineToolCallRender,
|
|
2283
2419
|
useAgent,
|
|
2284
2420
|
useAgentContext,
|
|
2285
2421
|
useCopilotChatConfiguration,
|