@copilotkit/react-core 1.1.2 → 1.1.3-feat-runtime-remote-actions.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/CHANGELOG.md +24 -0
- package/README.md +32 -37
- package/dist/{chunk-T6L4EGTD.mjs → chunk-326LK7LX.mjs} +5 -5
- package/dist/chunk-326LK7LX.mjs.map +1 -0
- package/dist/{chunk-GE7LAL6V.mjs → chunk-3U22BXKC.mjs} +6 -4
- package/dist/chunk-3U22BXKC.mjs.map +1 -0
- package/dist/{chunk-VFDR4MIF.mjs → chunk-A37GANOW.mjs} +11 -7
- package/dist/chunk-A37GANOW.mjs.map +1 -0
- package/dist/chunk-BWYAGPEF.mjs +1 -0
- package/dist/{chunk-KONDJRB4.mjs → chunk-CODXG6KU.mjs} +5 -5
- package/dist/chunk-CODXG6KU.mjs.map +1 -0
- package/dist/{chunk-YYZNR3CS.mjs → chunk-HABY7NLH.mjs} +72 -14
- package/dist/chunk-HABY7NLH.mjs.map +1 -0
- package/dist/{chunk-3NHEWJ4V.mjs → chunk-J2YXDQHR.mjs} +19 -4
- package/dist/chunk-J2YXDQHR.mjs.map +1 -0
- package/dist/chunk-Q4TTTAXQ.mjs +87 -0
- package/dist/chunk-Q4TTTAXQ.mjs.map +1 -0
- package/dist/{chunk-TVR5CJ6E.mjs → chunk-RBNULK3U.mjs} +39 -5
- package/dist/chunk-RBNULK3U.mjs.map +1 -0
- package/dist/chunk-STUXJ3BN.mjs +44 -0
- package/dist/chunk-STUXJ3BN.mjs.map +1 -0
- package/dist/{chunk-UQRDVZ2N.mjs → chunk-TCZBK3HZ.mjs} +9 -5
- package/dist/chunk-TCZBK3HZ.mjs.map +1 -0
- package/dist/{chunk-AGGKI26A.mjs → chunk-XSZDVRPW.mjs} +64 -12
- package/dist/chunk-XSZDVRPW.mjs.map +1 -0
- package/dist/components/copilot-provider/copilotkit-props.d.ts +4 -0
- package/dist/components/copilot-provider/copilotkit-props.js.map +1 -1
- package/dist/components/copilot-provider/copilotkit.d.ts +2 -1
- package/dist/components/copilot-provider/copilotkit.js +50 -5
- package/dist/components/copilot-provider/copilotkit.js.map +1 -1
- package/dist/components/copilot-provider/copilotkit.mjs +2 -2
- package/dist/components/copilot-provider/index.d.ts +1 -0
- package/dist/components/copilot-provider/index.js +50 -5
- package/dist/components/copilot-provider/index.js.map +1 -1
- package/dist/components/copilot-provider/index.mjs +2 -2
- package/dist/components/index.d.ts +1 -0
- package/dist/components/index.js +50 -5
- package/dist/components/index.js.map +1 -1
- package/dist/components/index.mjs +2 -2
- package/dist/context/copilot-context.d.ts +21 -2
- package/dist/context/copilot-context.js +18 -3
- package/dist/context/copilot-context.js.map +1 -1
- package/dist/context/copilot-context.mjs +1 -1
- package/dist/context/index.d.ts +2 -0
- package/dist/context/index.js +18 -3
- package/dist/context/index.js.map +1 -1
- package/dist/context/index.mjs +1 -1
- package/dist/hooks/index.d.ts +4 -0
- package/dist/hooks/index.js +274 -31
- package/dist/hooks/index.js.map +1 -1
- package/dist/hooks/index.mjs +21 -12
- package/dist/hooks/use-chat.d.ts +26 -4
- package/dist/hooks/use-chat.js +59 -10
- package/dist/hooks/use-chat.js.map +1 -1
- package/dist/hooks/use-chat.mjs +1 -1
- package/dist/hooks/use-coagent-action.d.ts +5 -0
- package/dist/hooks/use-coagent-action.js +156 -0
- package/dist/hooks/use-coagent-action.js.map +1 -0
- package/dist/hooks/use-coagent-action.mjs +9 -0
- package/dist/hooks/use-coagent-action.mjs.map +1 -0
- package/dist/hooks/use-coagent.d.ts +27 -0
- package/dist/hooks/use-coagent.js +219 -0
- package/dist/hooks/use-coagent.js.map +1 -0
- package/dist/hooks/use-coagent.mjs +10 -0
- package/dist/hooks/use-coagent.mjs.map +1 -0
- package/dist/hooks/use-copilot-action.js +27 -5
- package/dist/hooks/use-copilot-action.js.map +1 -1
- package/dist/hooks/use-copilot-action.mjs +2 -2
- package/dist/hooks/use-copilot-chat.js +144 -20
- package/dist/hooks/use-copilot-chat.js.map +1 -1
- package/dist/hooks/use-copilot-chat.mjs +4 -4
- package/dist/hooks/use-copilot-readable.js +21 -3
- package/dist/hooks/use-copilot-readable.js.map +1 -1
- package/dist/hooks/use-copilot-readable.mjs +2 -2
- package/dist/hooks/use-make-copilot-document-readable.js +21 -3
- package/dist/hooks/use-make-copilot-document-readable.js.map +1 -1
- package/dist/hooks/use-make-copilot-document-readable.mjs +2 -2
- package/dist/index.d.ts +5 -0
- package/dist/index.js +320 -44
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +24 -16
- package/dist/lib/copilot-task.d.ts +2 -0
- package/dist/lib/copilot-task.js +3 -2
- package/dist/lib/copilot-task.js.map +1 -1
- package/dist/lib/copilot-task.mjs +3 -3
- package/dist/lib/index.d.ts +2 -0
- package/dist/lib/index.js +3 -2
- package/dist/lib/index.js.map +1 -1
- package/dist/lib/index.mjs +3 -3
- package/dist/types/coagent-action.d.ts +17 -0
- package/dist/types/coagent-action.js +19 -0
- package/dist/types/coagent-action.js.map +1 -0
- package/dist/types/coagent-action.mjs +1 -0
- package/dist/types/coagent-action.mjs.map +1 -0
- package/dist/types/coagent-state.d.ts +11 -0
- package/dist/types/coagent-state.js +19 -0
- package/dist/types/coagent-state.js.map +1 -0
- package/dist/types/coagent-state.mjs +1 -0
- package/dist/types/coagent-state.mjs.map +1 -0
- package/dist/types/frontend-action.d.ts +1 -0
- package/dist/types/frontend-action.js.map +1 -1
- package/dist/utils/extract.d.ts +2 -0
- package/dist/utils/extract.js +3 -2
- package/dist/utils/extract.js.map +1 -1
- package/dist/utils/extract.mjs +3 -3
- package/dist/utils/index.d.ts +2 -0
- package/dist/utils/index.js +3 -2
- package/dist/utils/index.js.map +1 -1
- package/dist/utils/index.mjs +3 -3
- package/package.json +5 -5
- package/src/components/copilot-provider/copilotkit-props.tsx +5 -0
- package/src/components/copilot-provider/copilotkit.tsx +45 -3
- package/src/context/copilot-context.tsx +44 -3
- package/src/hooks/index.ts +2 -0
- package/src/hooks/use-chat.ts +107 -11
- package/src/hooks/use-coagent-action.ts +44 -0
- package/src/hooks/use-coagent.ts +133 -0
- package/src/hooks/use-copilot-action.ts +9 -5
- package/src/hooks/use-copilot-chat.ts +80 -8
- package/src/hooks/use-copilot-readable.ts +3 -3
- package/src/hooks/use-make-copilot-document-readable.ts +3 -3
- package/src/lib/copilot-task.ts +3 -1
- package/src/types/coagent-action.ts +17 -0
- package/src/types/coagent-state.ts +9 -0
- package/src/types/frontend-action.ts +1 -0
- package/src/utils/extract.ts +8 -2
- package/dist/chunk-3NHEWJ4V.mjs.map +0 -1
- package/dist/chunk-5JB4B2SV.mjs +0 -1
- package/dist/chunk-AGGKI26A.mjs.map +0 -1
- package/dist/chunk-GE7LAL6V.mjs.map +0 -1
- package/dist/chunk-KONDJRB4.mjs.map +0 -1
- package/dist/chunk-T6L4EGTD.mjs.map +0 -1
- package/dist/chunk-TVR5CJ6E.mjs.map +0 -1
- package/dist/chunk-UQRDVZ2N.mjs.map +0 -1
- package/dist/chunk-VFDR4MIF.mjs.map +0 -1
- package/dist/chunk-YYZNR3CS.mjs.map +0 -1
- /package/dist/{chunk-5JB4B2SV.mjs.map → chunk-BWYAGPEF.mjs.map} +0 -0
package/dist/utils/index.mjs
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
import "../chunk-YJLRG5U3.mjs";
|
|
2
2
|
import {
|
|
3
3
|
extract
|
|
4
|
-
} from "../chunk-
|
|
4
|
+
} from "../chunk-TCZBK3HZ.mjs";
|
|
5
5
|
import "../chunk-JD7BAH7U.mjs";
|
|
6
6
|
import "../chunk-SPCZTZCY.mjs";
|
|
7
|
-
import "../chunk-
|
|
7
|
+
import "../chunk-RBNULK3U.mjs";
|
|
8
8
|
import "../chunk-5FHSUKQL.mjs";
|
|
9
9
|
import "../chunk-6U3UH3KO.mjs";
|
|
10
|
-
import "../chunk-
|
|
10
|
+
import "../chunk-J2YXDQHR.mjs";
|
|
11
11
|
import "../chunk-SKC7AJIV.mjs";
|
|
12
12
|
export {
|
|
13
13
|
extract
|
package/package.json
CHANGED
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
"publishConfig": {
|
|
10
10
|
"access": "public"
|
|
11
11
|
},
|
|
12
|
-
"version": "1.1.
|
|
12
|
+
"version": "1.1.3-feat-runtime-remote-actions.1",
|
|
13
13
|
"sideEffects": false,
|
|
14
14
|
"main": "./dist/index.js",
|
|
15
15
|
"module": "./dist/index.mjs",
|
|
@@ -36,14 +36,14 @@
|
|
|
36
36
|
"tsup": "^6.7.0",
|
|
37
37
|
"typescript": "^5.2.3",
|
|
38
38
|
"@types/react-dom": "^18.2.4",
|
|
39
|
-
"eslint-config-custom": "1.1.1",
|
|
40
|
-
"tsconfig": "1.1.1"
|
|
39
|
+
"eslint-config-custom": "1.1.2-feat-runtime-remote-actions.1",
|
|
40
|
+
"tsconfig": "1.1.2-feat-runtime-remote-actions.1"
|
|
41
41
|
},
|
|
42
42
|
"dependencies": {
|
|
43
43
|
"@scarf/scarf": "^1.3.0",
|
|
44
44
|
"untruncate-json": "^0.0.1",
|
|
45
|
-
"@copilotkit/
|
|
46
|
-
"@copilotkit/
|
|
45
|
+
"@copilotkit/shared": "1.1.3-feat-runtime-remote-actions.1",
|
|
46
|
+
"@copilotkit/runtime-client-gql": "1.1.3-feat-runtime-remote-actions.1"
|
|
47
47
|
},
|
|
48
48
|
"keywords": [
|
|
49
49
|
"copilotkit",
|
|
@@ -35,6 +35,8 @@ import {
|
|
|
35
35
|
CopilotContext,
|
|
36
36
|
CopilotApiConfig,
|
|
37
37
|
InChatRenderFunction,
|
|
38
|
+
ChatComponentsCache,
|
|
39
|
+
AgentSession,
|
|
38
40
|
} from "../../context/copilot-context";
|
|
39
41
|
import useTree from "../../hooks/use-tree";
|
|
40
42
|
import { CopilotChatSuggestionConfiguration, DocumentPointer } from "../../types";
|
|
@@ -44,11 +46,13 @@ import {
|
|
|
44
46
|
CopilotCloudConfig,
|
|
45
47
|
FunctionCallHandler,
|
|
46
48
|
} from "@copilotkit/shared";
|
|
47
|
-
import { Message } from "@copilotkit/runtime-client-gql";
|
|
49
|
+
import { AgentStateMessage, Message } from "@copilotkit/runtime-client-gql";
|
|
48
50
|
|
|
49
51
|
import { FrontendAction } from "../../types/frontend-action";
|
|
50
52
|
import useFlatCategoryStore from "../../hooks/use-flat-category-store";
|
|
51
53
|
import { CopilotKitProps } from "./copilotkit-props";
|
|
54
|
+
import { CoagentAction } from "../../types/coagent-action";
|
|
55
|
+
import { CoagentState } from "../../types/coagent-state";
|
|
52
56
|
|
|
53
57
|
export function CopilotKit({ children, ...props }: CopilotKitProps) {
|
|
54
58
|
// Compute all the functions and properties that we need to pass
|
|
@@ -63,7 +67,11 @@ export function CopilotKit({ children, ...props }: CopilotKitProps) {
|
|
|
63
67
|
const chatApiEndpoint = props.runtimeUrl || COPILOT_CLOUD_CHAT_URL;
|
|
64
68
|
|
|
65
69
|
const [actions, setActions] = useState<Record<string, FrontendAction<any>>>({});
|
|
66
|
-
const
|
|
70
|
+
const [coagentActions, setCoagentActions] = useState<Record<string, CoagentAction<any>>>({});
|
|
71
|
+
const chatComponentsCache = useRef<ChatComponentsCache>({
|
|
72
|
+
actions: {},
|
|
73
|
+
coagentActions: {},
|
|
74
|
+
});
|
|
67
75
|
const { addElement, removeElement, printTree } = useTree();
|
|
68
76
|
const [messages, setMessages] = useState<Message[]>([]);
|
|
69
77
|
const [isLoading, setIsLoading] = useState(false);
|
|
@@ -92,6 +100,23 @@ export function CopilotKit({ children, ...props }: CopilotKitProps) {
|
|
|
92
100
|
});
|
|
93
101
|
}, []);
|
|
94
102
|
|
|
103
|
+
const setCoagentAction = useCallback((id: string, action: CoagentAction<any>) => {
|
|
104
|
+
setCoagentActions((prevPoints) => {
|
|
105
|
+
return {
|
|
106
|
+
...prevPoints,
|
|
107
|
+
[id]: action,
|
|
108
|
+
};
|
|
109
|
+
});
|
|
110
|
+
}, []);
|
|
111
|
+
|
|
112
|
+
const removeCoagentAction = useCallback((id: string) => {
|
|
113
|
+
setCoagentActions((prevPoints) => {
|
|
114
|
+
const newPoints = { ...prevPoints };
|
|
115
|
+
delete newPoints[id];
|
|
116
|
+
return newPoints;
|
|
117
|
+
});
|
|
118
|
+
}, []);
|
|
119
|
+
|
|
95
120
|
const getContextString = useCallback(
|
|
96
121
|
(documents: DocumentPointer[], categories: string[]) => {
|
|
97
122
|
const documentsString = documents
|
|
@@ -206,6 +231,16 @@ export function CopilotKit({ children, ...props }: CopilotKitProps) {
|
|
|
206
231
|
});
|
|
207
232
|
};
|
|
208
233
|
|
|
234
|
+
const [coagentStates, setCoagentStates] = useState<Record<string, CoagentState>>({});
|
|
235
|
+
let initialAgentSession: AgentSession | null = null;
|
|
236
|
+
if (props.agent) {
|
|
237
|
+
initialAgentSession = {
|
|
238
|
+
agentName: props.agent,
|
|
239
|
+
};
|
|
240
|
+
}
|
|
241
|
+
|
|
242
|
+
const [agentSession, setAgentSession] = useState<AgentSession | null>(initialAgentSession);
|
|
243
|
+
|
|
209
244
|
return (
|
|
210
245
|
<CopilotContext.Provider
|
|
211
246
|
value={{
|
|
@@ -214,6 +249,9 @@ export function CopilotKit({ children, ...props }: CopilotKitProps) {
|
|
|
214
249
|
getFunctionCallHandler,
|
|
215
250
|
setAction,
|
|
216
251
|
removeAction,
|
|
252
|
+
coagentActions,
|
|
253
|
+
setCoagentAction,
|
|
254
|
+
removeCoagentAction,
|
|
217
255
|
getContextString,
|
|
218
256
|
addContext,
|
|
219
257
|
removeContext,
|
|
@@ -231,6 +269,10 @@ export function CopilotKit({ children, ...props }: CopilotKitProps) {
|
|
|
231
269
|
chatInstructions,
|
|
232
270
|
setChatInstructions,
|
|
233
271
|
showDevConsole: props.showDevConsole === undefined ? "auto" : props.showDevConsole,
|
|
272
|
+
coagentStates,
|
|
273
|
+
setCoagentStates,
|
|
274
|
+
agentSession,
|
|
275
|
+
setAgentSession,
|
|
234
276
|
}}
|
|
235
277
|
>
|
|
236
278
|
{children}
|
|
@@ -253,7 +295,7 @@ function entryPointsToFunctionCallHandler(actions: FrontendAction<any>[]): Funct
|
|
|
253
295
|
await new Promise<void>((resolve, reject) => {
|
|
254
296
|
flushSync(async () => {
|
|
255
297
|
try {
|
|
256
|
-
result = await action.handler(args);
|
|
298
|
+
result = await action.handler?.(args);
|
|
257
299
|
resolve();
|
|
258
300
|
} catch (error) {
|
|
259
301
|
reject(error);
|
|
@@ -5,6 +5,8 @@ import React from "react";
|
|
|
5
5
|
import { TreeNodeId } from "../hooks/use-tree";
|
|
6
6
|
import { DocumentPointer } from "../types";
|
|
7
7
|
import { CopilotChatSuggestionConfiguration } from "../types/chat-suggestion-configuration";
|
|
8
|
+
import { CoagentAction, CoagentActionRenderProps } from "../types/coagent-action";
|
|
9
|
+
import { CoagentState } from "../types/coagent-state";
|
|
8
10
|
|
|
9
11
|
/**
|
|
10
12
|
* Interface for the configuration of the Copilot API.
|
|
@@ -67,13 +69,33 @@ export interface CopilotApiConfig {
|
|
|
67
69
|
}
|
|
68
70
|
|
|
69
71
|
export type InChatRenderFunction = (props: ActionRenderProps<any>) => string | JSX.Element;
|
|
72
|
+
export type CoagentInChatRenderFunction = (
|
|
73
|
+
props: CoagentActionRenderProps<any>,
|
|
74
|
+
) => string | JSX.Element;
|
|
75
|
+
|
|
76
|
+
export interface ChatComponentsCache {
|
|
77
|
+
actions: Record<string, InChatRenderFunction | string>;
|
|
78
|
+
coagentActions: Record<string, CoagentInChatRenderFunction | string>;
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
export interface AgentSession {
|
|
82
|
+
agentName: string;
|
|
83
|
+
threadId?: string;
|
|
84
|
+
nodeName?: string;
|
|
85
|
+
}
|
|
70
86
|
|
|
71
87
|
export interface CopilotContextParams {
|
|
72
88
|
// function-calling
|
|
73
89
|
actions: Record<string, FrontendAction<any>>;
|
|
74
90
|
setAction: (id: string, action: FrontendAction<any>) => void;
|
|
75
91
|
removeAction: (id: string) => void;
|
|
76
|
-
|
|
92
|
+
|
|
93
|
+
// coagent actions
|
|
94
|
+
coagentActions: Record<string, CoagentAction<any>>;
|
|
95
|
+
setCoagentAction: (id: string, action: CoagentAction<any>) => void;
|
|
96
|
+
removeCoagentAction: (id: string) => void;
|
|
97
|
+
|
|
98
|
+
chatComponentsCache: React.RefObject<ChatComponentsCache>;
|
|
77
99
|
|
|
78
100
|
getFunctionCallHandler: (
|
|
79
101
|
customEntryPoints?: Record<string, FrontendAction<any>>,
|
|
@@ -110,6 +132,12 @@ export interface CopilotContextParams {
|
|
|
110
132
|
copilotApiConfig: CopilotApiConfig;
|
|
111
133
|
|
|
112
134
|
showDevConsole: boolean | "auto";
|
|
135
|
+
|
|
136
|
+
// agents
|
|
137
|
+
coagentStates: Record<string, CoagentState>;
|
|
138
|
+
setCoagentStates: React.Dispatch<React.SetStateAction<Record<string, CoagentState>>>;
|
|
139
|
+
agentSession: AgentSession | null;
|
|
140
|
+
setAgentSession: React.Dispatch<React.SetStateAction<AgentSession | null>>;
|
|
113
141
|
}
|
|
114
142
|
|
|
115
143
|
const emptyCopilotContext: CopilotContextParams = {
|
|
@@ -117,7 +145,11 @@ const emptyCopilotContext: CopilotContextParams = {
|
|
|
117
145
|
setAction: () => {},
|
|
118
146
|
removeAction: () => {},
|
|
119
147
|
|
|
120
|
-
|
|
148
|
+
coagentActions: {},
|
|
149
|
+
setCoagentAction: () => {},
|
|
150
|
+
removeCoagentAction: () => {},
|
|
151
|
+
|
|
152
|
+
chatComponentsCache: { current: { actions: {}, coagentActions: {} } },
|
|
121
153
|
getContextString: (documents: DocumentPointer[], categories: string[]) =>
|
|
122
154
|
returnAndThrowInDebug(""),
|
|
123
155
|
addContext: () => "",
|
|
@@ -155,12 +187,21 @@ const emptyCopilotContext: CopilotContextParams = {
|
|
|
155
187
|
addChatSuggestionConfiguration: () => {},
|
|
156
188
|
removeChatSuggestionConfiguration: () => {},
|
|
157
189
|
showDevConsole: "auto",
|
|
190
|
+
coagentStates: {},
|
|
191
|
+
setCoagentStates: () => {},
|
|
192
|
+
|
|
193
|
+
agentSession: null,
|
|
194
|
+
setAgentSession: () => {},
|
|
158
195
|
};
|
|
159
196
|
|
|
160
197
|
export const CopilotContext = React.createContext<CopilotContextParams>(emptyCopilotContext);
|
|
161
198
|
|
|
162
199
|
export function useCopilotContext(): CopilotContextParams {
|
|
163
|
-
|
|
200
|
+
const context = React.useContext(CopilotContext);
|
|
201
|
+
if (context === emptyCopilotContext) {
|
|
202
|
+
throw new Error("Remember to wrap your app in a `<CopilotKit> {...} </CopilotKit>` !!!");
|
|
203
|
+
}
|
|
204
|
+
return context;
|
|
164
205
|
}
|
|
165
206
|
|
|
166
207
|
function returnAndThrowInDebug<T>(value: T): T {
|
package/src/hooks/index.ts
CHANGED
|
@@ -3,6 +3,8 @@ export type { UseCopilotChatOptions } from "./use-copilot-chat";
|
|
|
3
3
|
export type { UseCopilotChatReturn } from "./use-copilot-chat";
|
|
4
4
|
|
|
5
5
|
export { useCopilotAction } from "./use-copilot-action";
|
|
6
|
+
export { useCoAgentAction } from "./use-coagent-action";
|
|
6
7
|
export { useMakeCopilotDocumentReadable } from "./use-make-copilot-document-readable";
|
|
7
8
|
export { type UseChatHelpers } from "./use-chat";
|
|
8
9
|
export { useCopilotReadable } from "./use-copilot-readable";
|
|
10
|
+
export { useCoAgent } from "./use-coagent";
|
package/src/hooks/use-chat.ts
CHANGED
|
@@ -2,8 +2,8 @@ import { useRef } from "react";
|
|
|
2
2
|
import {
|
|
3
3
|
FunctionCallHandler,
|
|
4
4
|
COPILOT_CLOUD_PUBLIC_API_KEY_HEADER,
|
|
5
|
-
Action,
|
|
6
5
|
actionParametersToJsonSchema,
|
|
6
|
+
CoagentActionHandler,
|
|
7
7
|
} from "@copilotkit/shared";
|
|
8
8
|
import {
|
|
9
9
|
Message,
|
|
@@ -12,14 +12,20 @@ import {
|
|
|
12
12
|
ResultMessage,
|
|
13
13
|
CopilotRuntimeClient,
|
|
14
14
|
convertMessagesToGqlInput,
|
|
15
|
+
filterAdjacentAgentStateMessages,
|
|
16
|
+
filterAgentStateMessages,
|
|
15
17
|
convertGqlOutputToMessages,
|
|
16
18
|
MessageStatusCode,
|
|
17
19
|
MessageRole,
|
|
18
20
|
Role,
|
|
19
21
|
CopilotRequestType,
|
|
22
|
+
AgentStateMessage,
|
|
20
23
|
} from "@copilotkit/runtime-client-gql";
|
|
21
24
|
|
|
22
25
|
import { CopilotApiConfig } from "../context";
|
|
26
|
+
import { FrontendAction } from "../types/frontend-action";
|
|
27
|
+
import { CoagentState } from "../types/coagent-state";
|
|
28
|
+
import { AgentSession } from "../context/copilot-context";
|
|
23
29
|
|
|
24
30
|
export type UseChatOptions = {
|
|
25
31
|
/**
|
|
@@ -32,10 +38,16 @@ export type UseChatOptions = {
|
|
|
32
38
|
* automatically to the API and will be used to update the chat.
|
|
33
39
|
*/
|
|
34
40
|
onFunctionCall?: FunctionCallHandler;
|
|
41
|
+
|
|
42
|
+
/**
|
|
43
|
+
* Callback function to be called when a coagent action is received.
|
|
44
|
+
*/
|
|
45
|
+
onCoagentAction?: CoagentActionHandler;
|
|
46
|
+
|
|
35
47
|
/**
|
|
36
48
|
* Function definitions to be sent to the API.
|
|
37
49
|
*/
|
|
38
|
-
actions:
|
|
50
|
+
actions: FrontendAction<any>[];
|
|
39
51
|
|
|
40
52
|
/**
|
|
41
53
|
* The CopilotKit API configuration.
|
|
@@ -65,6 +77,26 @@ export type UseChatOptions = {
|
|
|
65
77
|
* setState-powered method to update the isChatLoading value
|
|
66
78
|
*/
|
|
67
79
|
setIsLoading: React.Dispatch<React.SetStateAction<boolean>>;
|
|
80
|
+
|
|
81
|
+
/**
|
|
82
|
+
* The current list of coagent states.
|
|
83
|
+
*/
|
|
84
|
+
coagentStates: Record<string, CoagentState>;
|
|
85
|
+
|
|
86
|
+
/**
|
|
87
|
+
* setState-powered method to update the agent states
|
|
88
|
+
*/
|
|
89
|
+
setCoagentStates: React.Dispatch<React.SetStateAction<Record<string, CoagentState>>>;
|
|
90
|
+
|
|
91
|
+
/**
|
|
92
|
+
* The current agent session.
|
|
93
|
+
*/
|
|
94
|
+
agentSession: AgentSession | null;
|
|
95
|
+
|
|
96
|
+
/**
|
|
97
|
+
* setState-powered method to update the agent session
|
|
98
|
+
*/
|
|
99
|
+
setAgentSession: React.Dispatch<React.SetStateAction<AgentSession | null>>;
|
|
68
100
|
};
|
|
69
101
|
|
|
70
102
|
export type UseChatHelpers = {
|
|
@@ -97,11 +129,19 @@ export function useChat(options: UseChatOptions): UseChatHelpers {
|
|
|
97
129
|
isLoading,
|
|
98
130
|
actions,
|
|
99
131
|
onFunctionCall,
|
|
132
|
+
onCoagentAction,
|
|
133
|
+
setCoagentStates,
|
|
134
|
+
coagentStates,
|
|
135
|
+
agentSession,
|
|
136
|
+
setAgentSession,
|
|
100
137
|
} = options;
|
|
138
|
+
|
|
101
139
|
const abortControllerRef = useRef<AbortController>();
|
|
102
140
|
const threadIdRef = useRef<string | null>(null);
|
|
103
141
|
const runIdRef = useRef<string | null>(null);
|
|
142
|
+
|
|
104
143
|
const publicApiKey = copilotConfig.publicApiKey;
|
|
144
|
+
|
|
105
145
|
const headers = {
|
|
106
146
|
...(copilotConfig.headers || {}),
|
|
107
147
|
...(publicApiKey ? { [COPILOT_CLOUD_PUBLIC_API_KEY_HEADER]: publicApiKey } : {}),
|
|
@@ -143,10 +183,11 @@ export function useChat(options: UseChatOptions): UseChatHelpers {
|
|
|
143
183
|
description: action.description || "",
|
|
144
184
|
jsonSchema: JSON.stringify(actionParametersToJsonSchema(action.parameters || [])),
|
|
145
185
|
})),
|
|
186
|
+
url: window.location.href,
|
|
146
187
|
},
|
|
147
188
|
threadId: threadIdRef.current,
|
|
148
189
|
runId: runIdRef.current,
|
|
149
|
-
messages: convertMessagesToGqlInput(messagesWithContext),
|
|
190
|
+
messages: convertMessagesToGqlInput(filterAgentStateMessages(messagesWithContext)),
|
|
150
191
|
...(copilotConfig.cloud
|
|
151
192
|
? {
|
|
152
193
|
cloud: {
|
|
@@ -168,6 +209,15 @@ export function useChat(options: UseChatOptions): UseChatHelpers {
|
|
|
168
209
|
metadata: {
|
|
169
210
|
requestType: CopilotRequestType.Chat,
|
|
170
211
|
},
|
|
212
|
+
...(agentSession
|
|
213
|
+
? {
|
|
214
|
+
agentSession,
|
|
215
|
+
}
|
|
216
|
+
: {}),
|
|
217
|
+
agentStates: Object.values(coagentStates).map((state) => ({
|
|
218
|
+
agentName: state.name,
|
|
219
|
+
state: JSON.stringify(state.state),
|
|
220
|
+
})),
|
|
171
221
|
},
|
|
172
222
|
properties: copilotConfig.properties,
|
|
173
223
|
signal: abortControllerRef.current?.signal,
|
|
@@ -179,7 +229,8 @@ export function useChat(options: UseChatOptions): UseChatHelpers {
|
|
|
179
229
|
|
|
180
230
|
const reader = stream.getReader();
|
|
181
231
|
|
|
182
|
-
let
|
|
232
|
+
let actionResults: { [id: string]: string } = {};
|
|
233
|
+
let executedCoagentActions: string[] = [];
|
|
183
234
|
|
|
184
235
|
try {
|
|
185
236
|
while (true) {
|
|
@@ -196,7 +247,9 @@ export function useChat(options: UseChatOptions): UseChatHelpers {
|
|
|
196
247
|
threadIdRef.current = value.generateCopilotResponse.threadId || null;
|
|
197
248
|
runIdRef.current = value.generateCopilotResponse.runId || null;
|
|
198
249
|
|
|
199
|
-
const messages = convertGqlOutputToMessages(
|
|
250
|
+
const messages = convertGqlOutputToMessages(
|
|
251
|
+
filterAdjacentAgentStateMessages(value.generateCopilotResponse.messages),
|
|
252
|
+
);
|
|
200
253
|
|
|
201
254
|
if (messages.length === 0) {
|
|
202
255
|
continue;
|
|
@@ -221,14 +274,37 @@ export function useChat(options: UseChatOptions): UseChatHelpers {
|
|
|
221
274
|
else {
|
|
222
275
|
for (const message of messages) {
|
|
223
276
|
newMessages.push(message);
|
|
224
|
-
|
|
277
|
+
if (message instanceof AgentStateMessage) {
|
|
278
|
+
if (message.running) {
|
|
279
|
+
setCoagentStates((prevAgentStates) => ({
|
|
280
|
+
...prevAgentStates,
|
|
281
|
+
[message.agentName]: {
|
|
282
|
+
name: message.agentName,
|
|
283
|
+
state: message.state,
|
|
284
|
+
running: message.running,
|
|
285
|
+
active: message.active,
|
|
286
|
+
threadId: message.threadId,
|
|
287
|
+
nodeName: message.nodeName,
|
|
288
|
+
runId: message.runId,
|
|
289
|
+
},
|
|
290
|
+
}));
|
|
291
|
+
setAgentSession({
|
|
292
|
+
threadId: message.threadId,
|
|
293
|
+
agentName: message.agentName,
|
|
294
|
+
nodeName: message.nodeName,
|
|
295
|
+
});
|
|
296
|
+
} else {
|
|
297
|
+
setAgentSession(null);
|
|
298
|
+
}
|
|
299
|
+
}
|
|
300
|
+
// execute regular action executions
|
|
225
301
|
if (
|
|
226
302
|
message instanceof ActionExecutionMessage &&
|
|
227
303
|
message.status.code !== MessageStatusCode.Pending &&
|
|
228
304
|
message.scope === "client" &&
|
|
229
305
|
onFunctionCall
|
|
230
306
|
) {
|
|
231
|
-
if (!(message.id in
|
|
307
|
+
if (!(message.id in actionResults)) {
|
|
232
308
|
// Do not execute a function call if guardrails are enabled but the status is not known
|
|
233
309
|
if (guardrailsEnabled && value.generateCopilotResponse.status === undefined) {
|
|
234
310
|
break;
|
|
@@ -239,29 +315,48 @@ export function useChat(options: UseChatOptions): UseChatHelpers {
|
|
|
239
315
|
name: message.name,
|
|
240
316
|
args: message.arguments,
|
|
241
317
|
});
|
|
242
|
-
|
|
318
|
+
actionResults[message.id] = result;
|
|
243
319
|
}
|
|
244
|
-
|
|
245
320
|
// add the result message
|
|
246
321
|
newMessages.push(
|
|
247
322
|
new ResultMessage({
|
|
248
|
-
result: ResultMessage.encodeResult(
|
|
323
|
+
result: ResultMessage.encodeResult(actionResults[message.id]),
|
|
249
324
|
actionExecutionId: message.id,
|
|
250
325
|
actionName: message.name,
|
|
251
326
|
}),
|
|
252
327
|
);
|
|
253
328
|
}
|
|
329
|
+
// execute coagent actions
|
|
330
|
+
if (
|
|
331
|
+
message instanceof AgentStateMessage &&
|
|
332
|
+
!message.active &&
|
|
333
|
+
!executedCoagentActions.includes(message.id) &&
|
|
334
|
+
onCoagentAction
|
|
335
|
+
) {
|
|
336
|
+
// Do not execute a coagent action if guardrails are enabled but the status is not known
|
|
337
|
+
if (guardrailsEnabled && value.generateCopilotResponse.status === undefined) {
|
|
338
|
+
break;
|
|
339
|
+
}
|
|
340
|
+
// execute coagent action
|
|
341
|
+
await onCoagentAction({
|
|
342
|
+
name: message.agentName,
|
|
343
|
+
nodeName: message.nodeName,
|
|
344
|
+
state: message.state,
|
|
345
|
+
});
|
|
346
|
+
executedCoagentActions.push(message.id);
|
|
347
|
+
}
|
|
254
348
|
}
|
|
255
349
|
}
|
|
256
350
|
|
|
257
351
|
if (newMessages.length > 0) {
|
|
352
|
+
// Update message state
|
|
258
353
|
setMessages([...previousMessages, ...newMessages]);
|
|
259
354
|
}
|
|
260
355
|
}
|
|
261
356
|
|
|
262
357
|
if (
|
|
263
358
|
// if we have client side results
|
|
264
|
-
Object.values(
|
|
359
|
+
Object.values(actionResults).length ||
|
|
265
360
|
// or the last message we received is a result
|
|
266
361
|
(newMessages.length && newMessages[newMessages.length - 1] instanceof ResultMessage)
|
|
267
362
|
) {
|
|
@@ -288,6 +383,7 @@ export function useChat(options: UseChatOptions): UseChatHelpers {
|
|
|
288
383
|
if (isLoading) {
|
|
289
384
|
return;
|
|
290
385
|
}
|
|
386
|
+
|
|
291
387
|
const newMessages = [...messages, message];
|
|
292
388
|
setMessages(newMessages);
|
|
293
389
|
return runChatCompletionAndHandleFunctionCall(newMessages);
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import { useRef, useContext, useEffect } from "react";
|
|
2
|
+
import { CopilotContext } from "../context/copilot-context";
|
|
3
|
+
import { randomId } from "@copilotkit/shared";
|
|
4
|
+
import { CoagentAction } from "../types/coagent-action";
|
|
5
|
+
|
|
6
|
+
// We implement useCoAgentAction dependency handling so that
|
|
7
|
+
// the developer has the option to not provide any dependencies.
|
|
8
|
+
// see useCopilotAction for more details about this approach.
|
|
9
|
+
export function useCoAgentAction<T = any>(action: CoagentAction<T>, dependencies?: any[]): void {
|
|
10
|
+
const { setCoagentAction, removeCoagentAction, coagentActions, chatComponentsCache } =
|
|
11
|
+
useContext(CopilotContext);
|
|
12
|
+
const idRef = useRef<string>(randomId());
|
|
13
|
+
|
|
14
|
+
const key = `${action.name}-${action.nodeName || "global"}`;
|
|
15
|
+
|
|
16
|
+
if (dependencies === undefined) {
|
|
17
|
+
if (coagentActions[idRef.current]) {
|
|
18
|
+
coagentActions[idRef.current].handler = action.handler as any;
|
|
19
|
+
if (typeof action.render === "function") {
|
|
20
|
+
if (chatComponentsCache.current !== null) {
|
|
21
|
+
chatComponentsCache.current.coagentActions[key] = action.render;
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
useEffect(() => {
|
|
28
|
+
setCoagentAction(idRef.current, action as any);
|
|
29
|
+
if (chatComponentsCache.current !== null && action.render !== undefined) {
|
|
30
|
+
chatComponentsCache.current.coagentActions[key] = action.render;
|
|
31
|
+
}
|
|
32
|
+
return () => {
|
|
33
|
+
removeCoagentAction(idRef.current);
|
|
34
|
+
};
|
|
35
|
+
}, [
|
|
36
|
+
setCoagentAction,
|
|
37
|
+
removeCoagentAction,
|
|
38
|
+
action.name,
|
|
39
|
+
// include render only if it's a string
|
|
40
|
+
typeof action.render === "string" ? action.render : undefined,
|
|
41
|
+
// dependencies set by the developer
|
|
42
|
+
...(dependencies || []),
|
|
43
|
+
]);
|
|
44
|
+
}
|
|
@@ -0,0 +1,133 @@
|
|
|
1
|
+
import { useEffect } from "react";
|
|
2
|
+
import { useCopilotContext } from "../context";
|
|
3
|
+
import { CoagentState } from "../types/coagent-state";
|
|
4
|
+
|
|
5
|
+
interface WithInternalStateManagementAndInitial<T> {
|
|
6
|
+
name: string;
|
|
7
|
+
initialState: T;
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
interface WithInternalStateManagement {
|
|
11
|
+
name: string;
|
|
12
|
+
initialState?: any; // Optional initialState with default type any
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
interface WithExternalStateManagement<T> {
|
|
16
|
+
name: string;
|
|
17
|
+
state: T;
|
|
18
|
+
setState: (newState: T | ((prevState: T | undefined) => T)) => void;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
type UseCoagentOptions<T> =
|
|
22
|
+
| WithInternalStateManagementAndInitial<T>
|
|
23
|
+
| WithInternalStateManagement
|
|
24
|
+
| WithExternalStateManagement<T>;
|
|
25
|
+
|
|
26
|
+
export interface UseCoagentReturnType<T> {
|
|
27
|
+
name: string;
|
|
28
|
+
nodeName?: string;
|
|
29
|
+
threadId?: string;
|
|
30
|
+
running: boolean;
|
|
31
|
+
state: T;
|
|
32
|
+
setState: (newState: T | ((prevState: T | undefined) => T)) => void;
|
|
33
|
+
start: () => void;
|
|
34
|
+
stop: () => void;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
export function useCoAgent<T = any>(options: UseCoagentOptions<T>): UseCoagentReturnType<T> {
|
|
38
|
+
const isExternalStateManagement = (
|
|
39
|
+
options: UseCoagentOptions<T>,
|
|
40
|
+
): options is WithExternalStateManagement<T> => {
|
|
41
|
+
return "state" in options && "setState" in options;
|
|
42
|
+
};
|
|
43
|
+
|
|
44
|
+
const { name } = options;
|
|
45
|
+
|
|
46
|
+
const isInternalStateManagementWithInitial = (
|
|
47
|
+
options: UseCoagentOptions<T>,
|
|
48
|
+
): options is WithInternalStateManagementAndInitial<T> => {
|
|
49
|
+
return "initialState" in options;
|
|
50
|
+
};
|
|
51
|
+
|
|
52
|
+
const { coagentStates, setCoagentStates } = useCopilotContext();
|
|
53
|
+
|
|
54
|
+
const getCoagentState = (coagentStates: Record<string, CoagentState>, name: string) => {
|
|
55
|
+
if (coagentStates[name]) {
|
|
56
|
+
return coagentStates[name];
|
|
57
|
+
} else {
|
|
58
|
+
return {
|
|
59
|
+
name,
|
|
60
|
+
state: isInternalStateManagementWithInitial(options) ? options.initialState : {},
|
|
61
|
+
running: false,
|
|
62
|
+
active: false,
|
|
63
|
+
threadId: undefined,
|
|
64
|
+
nodeName: undefined,
|
|
65
|
+
runId: undefined,
|
|
66
|
+
};
|
|
67
|
+
}
|
|
68
|
+
};
|
|
69
|
+
|
|
70
|
+
// if we manage state internally, we need to provide a function to set the state
|
|
71
|
+
const setState = (newState: T | ((prevState: T | undefined) => T)) => {
|
|
72
|
+
setCoagentStates((prevAgentStates) => {
|
|
73
|
+
let coagentState: CoagentState = getCoagentState(prevAgentStates, name);
|
|
74
|
+
|
|
75
|
+
const updatedState =
|
|
76
|
+
typeof newState === "function" ? (newState as Function)(coagentState.state) : newState;
|
|
77
|
+
|
|
78
|
+
return {
|
|
79
|
+
...prevAgentStates,
|
|
80
|
+
[name]: {
|
|
81
|
+
...coagentState,
|
|
82
|
+
state: updatedState,
|
|
83
|
+
},
|
|
84
|
+
};
|
|
85
|
+
});
|
|
86
|
+
};
|
|
87
|
+
|
|
88
|
+
const coagentState = getCoagentState(coagentStates, name);
|
|
89
|
+
|
|
90
|
+
const state = isExternalStateManagement(options) ? options.state : coagentState.state;
|
|
91
|
+
|
|
92
|
+
// Sync internal state with external state if state management is external
|
|
93
|
+
useEffect(() => {
|
|
94
|
+
if (isExternalStateManagement(options)) {
|
|
95
|
+
setState(options.state);
|
|
96
|
+
} else if (coagentStates[name] === undefined) {
|
|
97
|
+
setState(options.initialState === undefined ? {} : options.initialState);
|
|
98
|
+
}
|
|
99
|
+
}, [isExternalStateManagement(options) ? JSON.stringify(options.state) : undefined]);
|
|
100
|
+
|
|
101
|
+
// Return the state and setState function
|
|
102
|
+
return {
|
|
103
|
+
name,
|
|
104
|
+
nodeName: coagentState.nodeName,
|
|
105
|
+
state,
|
|
106
|
+
setState,
|
|
107
|
+
running: coagentState.running,
|
|
108
|
+
start: () => {
|
|
109
|
+
startAgent(name);
|
|
110
|
+
},
|
|
111
|
+
stop: () => {
|
|
112
|
+
stopAgent(name);
|
|
113
|
+
},
|
|
114
|
+
};
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
function startAgent(name: string) {
|
|
118
|
+
const { setAgentSession } = useCopilotContext();
|
|
119
|
+
setAgentSession({
|
|
120
|
+
agentName: name,
|
|
121
|
+
});
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
function stopAgent(name: string) {
|
|
125
|
+
const { agentSession, setAgentSession } = useCopilotContext();
|
|
126
|
+
if (agentSession && agentSession.agentName === name) {
|
|
127
|
+
setAgentSession(null);
|
|
128
|
+
} else {
|
|
129
|
+
console.warn(`No agent session found for ${name}`);
|
|
130
|
+
}
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
// <CopilotKit agent="lockedInAgentName" />
|