@langchain/langgraph-sdk 1.3.1 → 1.4.5
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/_virtual/rolldown_runtime.cjs +10 -6
- package/dist/auth/error.cjs.map +1 -1
- package/dist/auth/error.d.cts.map +1 -1
- package/dist/auth/error.d.ts.map +1 -1
- package/dist/auth/error.js.map +1 -1
- package/dist/auth/index.cjs.map +1 -1
- package/dist/auth/index.d.cts +1 -3
- package/dist/auth/index.d.cts.map +1 -1
- package/dist/auth/index.d.ts +1 -3
- package/dist/auth/index.d.ts.map +1 -1
- package/dist/auth/index.js.map +1 -1
- package/dist/auth/types.d.cts +1 -1
- package/dist/auth/types.d.cts.map +1 -1
- package/dist/auth/types.d.ts +1 -1
- package/dist/auth/types.d.ts.map +1 -1
- package/dist/client.cjs +15 -24
- package/dist/client.cjs.map +1 -1
- package/dist/client.d.cts +2 -6
- package/dist/client.d.cts.map +1 -1
- package/dist/client.d.ts +2 -6
- package/dist/client.d.ts.map +1 -1
- package/dist/client.js +15 -24
- package/dist/client.js.map +1 -1
- package/dist/index.d.cts +2 -1
- package/dist/index.d.ts +2 -1
- package/dist/logging/index.cjs.map +1 -1
- package/dist/logging/index.d.cts +0 -1
- package/dist/logging/index.d.cts.map +1 -1
- package/dist/logging/index.d.ts +0 -1
- package/dist/logging/index.d.ts.map +1 -1
- package/dist/logging/index.js.map +1 -1
- package/dist/react/index.d.cts +3 -2
- package/dist/react/index.d.ts +3 -2
- package/dist/react/stream.cjs +1 -1
- package/dist/react/stream.cjs.map +1 -1
- package/dist/react/stream.custom.cjs +12 -6
- package/dist/react/stream.custom.cjs.map +1 -1
- package/dist/react/stream.custom.d.cts +3 -2
- package/dist/react/stream.custom.d.cts.map +1 -1
- package/dist/react/stream.custom.d.ts +3 -2
- package/dist/react/stream.custom.d.ts.map +1 -1
- package/dist/react/stream.custom.js +11 -5
- package/dist/react/stream.custom.js.map +1 -1
- package/dist/react/stream.d.cts +116 -34
- package/dist/react/stream.d.cts.map +1 -1
- package/dist/react/stream.d.ts +116 -34
- package/dist/react/stream.d.ts.map +1 -1
- package/dist/react/stream.js.map +1 -1
- package/dist/react/stream.lgp.cjs +15 -13
- package/dist/react/stream.lgp.cjs.map +1 -1
- package/dist/react/stream.lgp.js +14 -12
- package/dist/react/stream.lgp.js.map +1 -1
- package/dist/react/thread.cjs +1 -2
- package/dist/react/thread.cjs.map +1 -1
- package/dist/react/thread.js +0 -1
- package/dist/react/thread.js.map +1 -1
- package/dist/react/types.d.cts +73 -284
- package/dist/react/types.d.cts.map +1 -1
- package/dist/react/types.d.ts +73 -284
- package/dist/react/types.d.ts.map +1 -1
- package/dist/react-ui/client.cjs +8 -7
- package/dist/react-ui/client.cjs.map +1 -1
- package/dist/react-ui/client.d.cts +4 -21
- package/dist/react-ui/client.d.cts.map +1 -1
- package/dist/react-ui/client.d.ts +4 -21
- package/dist/react-ui/client.d.ts.map +1 -1
- package/dist/react-ui/client.js +2 -4
- package/dist/react-ui/client.js.map +1 -1
- package/dist/react-ui/index.cjs.map +1 -1
- package/dist/react-ui/index.js.map +1 -1
- package/dist/react-ui/server/server.cjs +1 -1
- package/dist/react-ui/server/server.cjs.map +1 -1
- package/dist/react-ui/server/server.d.cts.map +1 -1
- package/dist/react-ui/server/server.d.ts.map +1 -1
- package/dist/react-ui/server/server.js.map +1 -1
- package/dist/react-ui/types.cjs.map +1 -1
- package/dist/react-ui/types.d.cts.map +1 -1
- package/dist/react-ui/types.d.ts.map +1 -1
- package/dist/react-ui/types.js.map +1 -1
- package/dist/schema.d.cts +6 -6
- package/dist/schema.d.cts.map +1 -1
- package/dist/schema.d.ts +6 -6
- package/dist/schema.d.ts.map +1 -1
- package/dist/singletons/fetch.cjs.map +1 -1
- package/dist/singletons/fetch.js.map +1 -1
- package/dist/types.d.cts +1 -1
- package/dist/types.d.cts.map +1 -1
- package/dist/types.d.ts +1 -1
- package/dist/types.d.ts.map +1 -1
- package/dist/types.messages.d.cts +207 -34
- package/dist/types.messages.d.cts.map +1 -1
- package/dist/types.messages.d.ts +207 -34
- package/dist/types.messages.d.ts.map +1 -1
- package/dist/types.stream.d.cts +1 -3
- package/dist/types.stream.d.cts.map +1 -1
- package/dist/types.stream.d.ts +1 -3
- package/dist/types.stream.d.ts.map +1 -1
- package/dist/types.template.d.cts +19 -0
- package/dist/types.template.d.cts.map +1 -0
- package/dist/types.template.d.ts +19 -0
- package/dist/types.template.d.ts.map +1 -0
- package/dist/ui/branching.cjs.map +1 -1
- package/dist/ui/branching.d.cts +0 -3
- package/dist/ui/branching.d.cts.map +1 -1
- package/dist/ui/branching.d.ts +0 -3
- package/dist/ui/branching.d.ts.map +1 -1
- package/dist/ui/branching.js.map +1 -1
- package/dist/ui/errors.cjs.map +1 -1
- package/dist/ui/errors.js.map +1 -1
- package/dist/ui/manager.cjs +8 -2
- package/dist/ui/manager.cjs.map +1 -1
- package/dist/ui/manager.js +8 -2
- package/dist/ui/manager.js.map +1 -1
- package/dist/ui/messages.cjs +10 -10
- package/dist/ui/messages.cjs.map +1 -1
- package/dist/ui/messages.js.map +1 -1
- package/dist/ui/types.d.cts +420 -0
- package/dist/ui/types.d.cts.map +1 -0
- package/dist/ui/types.d.ts +420 -0
- package/dist/ui/types.d.ts.map +1 -0
- package/dist/ui/utils.cjs +0 -1
- package/dist/ui/utils.cjs.map +1 -1
- package/dist/ui/utils.js +0 -1
- package/dist/ui/utils.js.map +1 -1
- package/dist/utils/async_caller.cjs +12 -4
- package/dist/utils/async_caller.cjs.map +1 -1
- package/dist/utils/async_caller.d.cts +1 -3
- package/dist/utils/async_caller.d.cts.map +1 -1
- package/dist/utils/async_caller.d.ts +1 -3
- package/dist/utils/async_caller.d.ts.map +1 -1
- package/dist/utils/async_caller.js +8 -2
- package/dist/utils/async_caller.js.map +1 -1
- package/dist/utils/env.cjs +1 -1
- package/dist/utils/env.cjs.map +1 -1
- package/dist/utils/env.js +1 -1
- package/dist/utils/env.js.map +1 -1
- package/dist/utils/error.cjs.map +1 -1
- package/dist/utils/error.js.map +1 -1
- package/dist/utils/signals.cjs.map +1 -1
- package/dist/utils/signals.js.map +1 -1
- package/dist/utils/sse.cjs.map +1 -1
- package/dist/utils/sse.js.map +1 -1
- package/dist/utils/stream.cjs +1 -3
- package/dist/utils/stream.cjs.map +1 -1
- package/dist/utils/stream.js +1 -3
- package/dist/utils/stream.js.map +1 -1
- package/dist/utils/tools.cjs +52 -0
- package/dist/utils/tools.cjs.map +1 -0
- package/dist/utils/tools.js +51 -0
- package/dist/utils/tools.js.map +1 -0
- package/package.json +5 -5
- package/CHANGELOG.md +0 -281
package/dist/ui/branching.d.ts
CHANGED
|
@@ -1,18 +1,15 @@
|
|
|
1
1
|
import { ThreadState } from "../schema.js";
|
|
2
2
|
|
|
3
3
|
//#region src/ui/branching.d.ts
|
|
4
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
5
4
|
interface Node<StateType = any> {
|
|
6
5
|
type: "node";
|
|
7
6
|
value: ThreadState<StateType>;
|
|
8
7
|
path: string[];
|
|
9
8
|
}
|
|
10
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
11
9
|
interface Fork<StateType = any> {
|
|
12
10
|
type: "fork";
|
|
13
11
|
items: Array<Sequence<StateType>>;
|
|
14
12
|
}
|
|
15
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
16
13
|
interface Sequence<StateType = any> {
|
|
17
14
|
type: "sequence";
|
|
18
15
|
items: Array<Node<StateType> | Fork<StateType>>;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"branching.d.ts","names":["ThreadState","Node","StateType","Fork","Sequence","Array","getBranchSequence","Record","getBranchView","getBranchContext"],"sources":["../../src/ui/branching.d.ts"],"sourcesContent":["import type { ThreadState } from \"../schema.js\";\
|
|
1
|
+
{"version":3,"file":"branching.d.ts","names":["ThreadState","Node","StateType","Fork","Sequence","Array","getBranchSequence","Record","getBranchView","getBranchContext"],"sources":["../../src/ui/branching.d.ts"],"sourcesContent":["import type { ThreadState } from \"../schema.js\";\ninterface Node<StateType = any> {\n type: \"node\";\n value: ThreadState<StateType>;\n path: string[];\n}\ninterface Fork<StateType = any> {\n type: \"fork\";\n items: Array<Sequence<StateType>>;\n}\nexport interface Sequence<StateType = any> {\n type: \"sequence\";\n items: Array<Node<StateType> | Fork<StateType>>;\n}\nexport declare function getBranchSequence<StateType extends Record<string, unknown>>(history: ThreadState<StateType>[]): {\n rootSequence: Sequence<any>;\n paths: string[][];\n};\nexport declare function getBranchView<StateType extends Record<string, unknown>>(sequence: Sequence<StateType>, paths: string[][], branch: string): {\n history: ThreadState<StateType>[];\n branchByCheckpoint: Record<string, {\n branch: string | undefined;\n branchOptions: string[] | undefined;\n }>;\n};\nexport declare function getBranchContext<StateType extends Record<string, unknown>>(branch: string, history: ThreadState<StateType>[] | undefined): {\n branchTree: Sequence<any>;\n flatHistory: ThreadState<any>[];\n branchByCheckpoint: Record<string, {\n branch: string | undefined;\n branchOptions: string[] | undefined;\n }>;\n threadHead: ThreadState<any> | undefined;\n};\nexport {};\n"],"mappings":";;;UACUC;;EAAAA,KAAAA,EAECD,WAFG,CAESE,SAFT,CAAA;EAAA,IAAA,EAAA,MAAA,EAAA;;UAKJC,IAHCH,CAAAA,YAAAA,GAAAA,CAAAA,CAAAA;EAAW,IAAA,EAAA,MAAA;EAGZG,KAAAA,EAECE,KAFG,CAEGD,QAFH,CAEYF,SAFZ,CAAA,CAAA;;AAEYA,UAETE,QAFSF,CAAAA,YAAAA,GAAAA,CAAAA,CAAAA;MAATE,EAAAA,UAAAA;OAANC,EAIAA,KAJAA,CAIMJ,IAJNI,CAIWH,SAJXG,CAAAA,GAIwBF,IAJxBE,CAI6BH,SAJ7BG,CAAAA,CAAAA"}
|
package/dist/ui/branching.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"branching.js","names":["childrenMap: Record<string, ThreadState<StateType>[]>","queue: string[]","queue","rootSequence: Sequence","queue: Task[]","paths: string[][]","fork: Fork | undefined","pathMap: Record<string, string[][]>","path","history: ThreadState<StateType>[]","branchByCheckpoint: Record<\n string,\n { branch: string | undefined; branchOptions: string[] | undefined }\n >","queue: (Node<StateType> | Fork<StateType>)[]"],"sources":["../../src/ui/branching.ts"],"sourcesContent":["import type { ThreadState } from \"../schema.js\";\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\ninterface Node<StateType = any> {\n type: \"node\";\n value: ThreadState<StateType>;\n path: string[];\n}\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\ninterface Fork<StateType = any> {\n type: \"fork\";\n items: Array<Sequence<StateType>>;\n}\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\nexport interface Sequence<StateType = any> {\n type: \"sequence\";\n items: Array<Node<StateType> | Fork<StateType>>;\n}\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\ninterface ValidFork<StateType = any> {\n type: \"fork\";\n items: Array<ValidSequence<StateType>>;\n}\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\ninterface ValidSequence<StateType = any> {\n type: \"sequence\";\n items: [Node<StateType>, ...(Node<StateType> | ValidFork<StateType>)[]];\n}\n\nexport function getBranchSequence<StateType extends Record<string, unknown>>(\n history: ThreadState<StateType>[]\n) {\n const nodeIds = new Set<string>();\n const childrenMap: Record<string, ThreadState<StateType>[]> = {};\n\n // Short circuit if there's only a singular one state\n if (history.length <= 1) {\n return {\n rootSequence: {\n type: \"sequence\",\n items: history.map((value) => ({ type: \"node\", value, path: [] })),\n } satisfies Sequence<StateType>,\n paths: [],\n };\n }\n\n // First pass - collect nodes for each checkpoint\n history.forEach((state) => {\n const checkpointId = state.parent_checkpoint?.checkpoint_id ?? \"$\";\n childrenMap[checkpointId] ??= [];\n childrenMap[checkpointId].push(state);\n\n if (state.checkpoint?.checkpoint_id != null) {\n nodeIds.add(state.checkpoint.checkpoint_id);\n }\n });\n\n // If dealing with partial history, take the branch\n // with the latest checkpoint and mark it as the root.\n const maxId = (...ids: (string | null)[]) =>\n ids\n .filter((i) => i != null)\n .sort((a, b) => a.localeCompare(b))\n .at(-1)!;\n\n const lastOrphanedNode =\n childrenMap.$ == null\n ? Object.keys(childrenMap)\n .filter((parentId) => !nodeIds.has(parentId))\n .map((parentId) => {\n const queue: string[] = [parentId];\n const seen = new Set<string>();\n\n let lastId = parentId;\n\n while (queue.length > 0) {\n const current = queue.shift()!;\n\n if (seen.has(current)) continue;\n seen.add(current);\n\n const children = (childrenMap[current] ?? []).flatMap(\n (i) => i.checkpoint?.checkpoint_id ?? []\n );\n\n lastId = maxId(lastId, ...children);\n queue.push(...children);\n }\n\n return { parentId, lastId };\n })\n .sort((a, b) => a.lastId.localeCompare(b.lastId))\n .at(-1)?.parentId\n : undefined;\n\n if (lastOrphanedNode != null) childrenMap.$ = childrenMap[lastOrphanedNode];\n\n // Second pass - create a tree of sequences\n type Task = { id: string; sequence: Sequence; path: string[] };\n const rootSequence: Sequence = { type: \"sequence\", items: [] };\n const queue: Task[] = [{ id: \"$\", sequence: rootSequence, path: [] }];\n\n const paths: string[][] = [];\n\n const visited = new Set<string>();\n while (queue.length > 0) {\n const task = queue.shift()!;\n if (visited.has(task.id)) continue;\n visited.add(task.id);\n\n const children = childrenMap[task.id];\n if (children == null || children.length === 0) continue;\n\n // If we've encountered a fork (2+ children), push the fork\n // to the sequence and add a new sequence for each child\n let fork: Fork | undefined;\n if (children.length > 1) {\n fork = { type: \"fork\", items: [] };\n task.sequence.items.push(fork);\n }\n\n for (const value of children) {\n const id = value.checkpoint?.checkpoint_id;\n if (id == null) continue;\n\n let { sequence } = task;\n let { path } = task;\n if (fork != null) {\n sequence = { type: \"sequence\", items: [] };\n fork.items.unshift(sequence);\n\n path = path.slice();\n path.push(id);\n paths.push(path);\n }\n\n sequence.items.push({ type: \"node\", value, path });\n queue.push({ id, sequence, path });\n }\n }\n\n return { rootSequence, paths };\n}\n\nconst PATH_SEP = \">\";\nconst ROOT_ID = \"$\";\n\n// Get flat view\nexport function getBranchView<StateType extends Record<string, unknown>>(\n sequence: Sequence<StateType>,\n paths: string[][],\n branch: string\n) {\n const path = branch.split(PATH_SEP);\n const pathMap: Record<string, string[][]> = {};\n\n for (const path of paths) {\n const parent = path.at(-2) ?? ROOT_ID;\n pathMap[parent] ??= [];\n pathMap[parent].unshift(path);\n }\n\n const history: ThreadState<StateType>[] = [];\n const branchByCheckpoint: Record<\n string,\n { branch: string | undefined; branchOptions: string[] | undefined }\n > = {};\n\n const forkStack = path.slice();\n const queue: (Node<StateType> | Fork<StateType>)[] = [...sequence.items];\n\n while (queue.length > 0) {\n const item = queue.shift()!;\n\n if (item.type === \"node\") {\n history.push(item.value);\n const checkpointId = item.value.checkpoint?.checkpoint_id;\n if (checkpointId == null) continue;\n\n branchByCheckpoint[checkpointId] = {\n branch: item.path.join(PATH_SEP),\n branchOptions: (item.path.length > 0\n ? pathMap[item.path.at(-2) ?? ROOT_ID] ?? []\n : []\n ).map((p) => p.join(PATH_SEP)),\n };\n }\n if (item.type === \"fork\") {\n const forkId = forkStack.shift();\n const index =\n forkId != null\n ? item.items.findIndex((value) => {\n const firstItem = value.items.at(0);\n if (!firstItem || firstItem.type !== \"node\") return false;\n return firstItem.value.checkpoint?.checkpoint_id === forkId;\n })\n : -1;\n\n const nextItems = item.items.at(index)?.items ?? [];\n queue.push(...nextItems);\n }\n }\n\n return { history, branchByCheckpoint };\n}\n\nexport function getBranchContext<StateType extends Record<string, unknown>>(\n branch: string,\n history: ThreadState<StateType>[] | undefined\n) {\n const { rootSequence: branchTree, paths } = getBranchSequence(history ?? []);\n const { history: flatHistory, branchByCheckpoint } = getBranchView(\n branchTree,\n paths,\n branch\n );\n\n return {\n branchTree,\n flatHistory,\n branchByCheckpoint,\n threadHead: flatHistory.at(-1),\n };\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"branching.js","names":["queue","path"],"sources":["../../src/ui/branching.ts"],"sourcesContent":["import type { ThreadState } from \"../schema.js\";\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\ninterface Node<StateType = any> {\n type: \"node\";\n value: ThreadState<StateType>;\n path: string[];\n}\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\ninterface Fork<StateType = any> {\n type: \"fork\";\n items: Array<Sequence<StateType>>;\n}\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\nexport interface Sequence<StateType = any> {\n type: \"sequence\";\n items: Array<Node<StateType> | Fork<StateType>>;\n}\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\ninterface ValidFork<StateType = any> {\n type: \"fork\";\n items: Array<ValidSequence<StateType>>;\n}\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\ninterface ValidSequence<StateType = any> {\n type: \"sequence\";\n items: [Node<StateType>, ...(Node<StateType> | ValidFork<StateType>)[]];\n}\n\nexport function getBranchSequence<StateType extends Record<string, unknown>>(\n history: ThreadState<StateType>[]\n) {\n const nodeIds = new Set<string>();\n const childrenMap: Record<string, ThreadState<StateType>[]> = {};\n\n // Short circuit if there's only a singular one state\n if (history.length <= 1) {\n return {\n rootSequence: {\n type: \"sequence\",\n items: history.map((value) => ({ type: \"node\", value, path: [] })),\n } satisfies Sequence<StateType>,\n paths: [],\n };\n }\n\n // First pass - collect nodes for each checkpoint\n history.forEach((state) => {\n const checkpointId = state.parent_checkpoint?.checkpoint_id ?? \"$\";\n childrenMap[checkpointId] ??= [];\n childrenMap[checkpointId].push(state);\n\n if (state.checkpoint?.checkpoint_id != null) {\n nodeIds.add(state.checkpoint.checkpoint_id);\n }\n });\n\n // If dealing with partial history, take the branch\n // with the latest checkpoint and mark it as the root.\n const maxId = (...ids: (string | null)[]) =>\n ids\n .filter((i): i is string => i != null)\n .sort((a, b) => a.localeCompare(b))\n .at(-1)!;\n\n const lastOrphanedNode =\n childrenMap.$ == null\n ? Object.keys(childrenMap)\n .filter((parentId) => !nodeIds.has(parentId))\n .map((parentId) => {\n const queue: string[] = [parentId];\n const seen = new Set<string>();\n\n let lastId = parentId;\n\n while (queue.length > 0) {\n const current = queue.shift()!;\n\n if (seen.has(current)) continue;\n seen.add(current);\n\n const children = (childrenMap[current] ?? []).flatMap(\n (i) => i.checkpoint?.checkpoint_id ?? []\n );\n\n lastId = maxId(lastId, ...children);\n queue.push(...children);\n }\n\n return { parentId, lastId };\n })\n .sort((a, b) => a.lastId.localeCompare(b.lastId))\n .at(-1)?.parentId\n : undefined;\n\n if (lastOrphanedNode != null) childrenMap.$ = childrenMap[lastOrphanedNode];\n\n // Second pass - create a tree of sequences\n type Task = { id: string; sequence: Sequence; path: string[] };\n const rootSequence: Sequence = { type: \"sequence\", items: [] };\n const queue: Task[] = [{ id: \"$\", sequence: rootSequence, path: [] }];\n\n const paths: string[][] = [];\n\n const visited = new Set<string>();\n while (queue.length > 0) {\n const task = queue.shift()!;\n if (visited.has(task.id)) continue;\n visited.add(task.id);\n\n const children = childrenMap[task.id];\n if (children == null || children.length === 0) continue;\n\n // If we've encountered a fork (2+ children), push the fork\n // to the sequence and add a new sequence for each child\n let fork: Fork | undefined;\n if (children.length > 1) {\n fork = { type: \"fork\", items: [] };\n task.sequence.items.push(fork);\n }\n\n for (const value of children) {\n const id = value.checkpoint?.checkpoint_id;\n if (id == null) continue;\n\n let { sequence } = task;\n let { path } = task;\n if (fork != null) {\n sequence = { type: \"sequence\", items: [] };\n fork.items.unshift(sequence);\n\n path = path.slice();\n path.push(id);\n paths.push(path);\n }\n\n sequence.items.push({ type: \"node\", value, path });\n queue.push({ id, sequence, path });\n }\n }\n\n return { rootSequence, paths };\n}\n\nconst PATH_SEP = \">\";\nconst ROOT_ID = \"$\";\n\n// Get flat view\nexport function getBranchView<StateType extends Record<string, unknown>>(\n sequence: Sequence<StateType>,\n paths: string[][],\n branch: string\n) {\n const path = branch.split(PATH_SEP);\n const pathMap: Record<string, string[][]> = {};\n\n for (const path of paths) {\n const parent = path.at(-2) ?? ROOT_ID;\n pathMap[parent] ??= [];\n pathMap[parent].unshift(path);\n }\n\n const history: ThreadState<StateType>[] = [];\n const branchByCheckpoint: Record<\n string,\n { branch: string | undefined; branchOptions: string[] | undefined }\n > = {};\n\n const forkStack = path.slice();\n const queue: (Node<StateType> | Fork<StateType>)[] = [...sequence.items];\n\n while (queue.length > 0) {\n const item = queue.shift()!;\n\n if (item.type === \"node\") {\n history.push(item.value);\n const checkpointId = item.value.checkpoint?.checkpoint_id;\n if (checkpointId == null) continue;\n\n branchByCheckpoint[checkpointId] = {\n branch: item.path.join(PATH_SEP),\n branchOptions: (item.path.length > 0\n ? pathMap[item.path.at(-2) ?? ROOT_ID] ?? []\n : []\n ).map((p) => p.join(PATH_SEP)),\n };\n }\n if (item.type === \"fork\") {\n const forkId = forkStack.shift();\n const index =\n forkId != null\n ? item.items.findIndex((value) => {\n const firstItem = value.items.at(0);\n if (!firstItem || firstItem.type !== \"node\") return false;\n return firstItem.value.checkpoint?.checkpoint_id === forkId;\n })\n : -1;\n\n const nextItems = item.items.at(index)?.items ?? [];\n queue.push(...nextItems);\n }\n }\n\n return { history, branchByCheckpoint };\n}\n\nexport function getBranchContext<StateType extends Record<string, unknown>>(\n branch: string,\n history: ThreadState<StateType>[] | undefined\n) {\n const { rootSequence: branchTree, paths } = getBranchSequence(history ?? []);\n const { history: flatHistory, branchByCheckpoint } = getBranchView(\n branchTree,\n paths,\n branch\n );\n\n return {\n branchTree,\n flatHistory,\n branchByCheckpoint,\n threadHead: flatHistory.at(-1),\n };\n}\n"],"mappings":"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"}
|
package/dist/ui/errors.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"errors.cjs","names":[],"sources":["../../src/ui/errors.ts"],"sourcesContent":["export class StreamError extends Error {\n constructor(data: { error?: string; name?: string; message: string }) {\n super(data.message);\n this.name = data.name ?? data.error ?? \"StreamError\";\n }\n\n static isStructuredError(error: unknown): error is {\n error?: string;\n name?: string;\n message: string;\n } {\n return typeof error === \"object\" && error != null && \"message\" in error;\n }\n}\n"],"mappings":";;AAAA,IAAa,cAAb,cAAiC,MAAM;CACrC,YAAY,MAA0D;AACpE,QAAM,KAAK;
|
|
1
|
+
{"version":3,"file":"errors.cjs","names":[],"sources":["../../src/ui/errors.ts"],"sourcesContent":["export class StreamError extends Error {\n constructor(data: { error?: string; name?: string; message: string }) {\n super(data.message);\n this.name = data.name ?? data.error ?? \"StreamError\";\n }\n\n static isStructuredError(error: unknown): error is {\n error?: string;\n name?: string;\n message: string;\n } {\n return typeof error === \"object\" && error != null && \"message\" in error;\n }\n}\n"],"mappings":";;AAAA,IAAa,cAAb,cAAiC,MAAM;CACrC,YAAY,MAA0D;AACpE,QAAM,KAAK,QAAQ;AACnB,OAAK,OAAO,KAAK,QAAQ,KAAK,SAAS;;CAGzC,OAAO,kBAAkB,OAIvB;AACA,SAAO,OAAO,UAAU,YAAY,SAAS,QAAQ,aAAa"}
|
package/dist/ui/errors.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"errors.js","names":[],"sources":["../../src/ui/errors.ts"],"sourcesContent":["export class StreamError extends Error {\n constructor(data: { error?: string; name?: string; message: string }) {\n super(data.message);\n this.name = data.name ?? data.error ?? \"StreamError\";\n }\n\n static isStructuredError(error: unknown): error is {\n error?: string;\n name?: string;\n message: string;\n } {\n return typeof error === \"object\" && error != null && \"message\" in error;\n }\n}\n"],"mappings":";AAAA,IAAa,cAAb,cAAiC,MAAM;CACrC,YAAY,MAA0D;AACpE,QAAM,KAAK;
|
|
1
|
+
{"version":3,"file":"errors.js","names":[],"sources":["../../src/ui/errors.ts"],"sourcesContent":["export class StreamError extends Error {\n constructor(data: { error?: string; name?: string; message: string }) {\n super(data.message);\n this.name = data.name ?? data.error ?? \"StreamError\";\n }\n\n static isStructuredError(error: unknown): error is {\n error?: string;\n name?: string;\n message: string;\n } {\n return typeof error === \"object\" && error != null && \"message\" in error;\n }\n}\n"],"mappings":";AAAA,IAAa,cAAb,cAAiC,MAAM;CACrC,YAAY,MAA0D;AACpE,QAAM,KAAK,QAAQ;AACnB,OAAK,OAAO,KAAK,QAAQ,KAAK,SAAS;;CAGzC,OAAO,kBAAkB,OAIvB;AACA,SAAO,OAAO,UAAU,YAAY,SAAS,QAAQ,aAAa"}
|
package/dist/ui/manager.cjs
CHANGED
|
@@ -2,6 +2,11 @@ const require_errors = require('./errors.cjs');
|
|
|
2
2
|
const require_messages = require('./messages.cjs');
|
|
3
3
|
|
|
4
4
|
//#region src/ui/manager.ts
|
|
5
|
+
/**
|
|
6
|
+
* Special ID used by LangGraph's messagesStateReducer to signal
|
|
7
|
+
* that all messages should be removed from the state.
|
|
8
|
+
*/
|
|
9
|
+
const REMOVE_ALL_MESSAGES = "__remove_all__";
|
|
5
10
|
var StreamManager = class {
|
|
6
11
|
abortRef = new AbortController();
|
|
7
12
|
messages;
|
|
@@ -132,10 +137,11 @@ var StreamManager = class {
|
|
|
132
137
|
...options.initialValues,
|
|
133
138
|
...streamValues
|
|
134
139
|
};
|
|
135
|
-
|
|
140
|
+
let messages = options.getMessages(values$1).slice();
|
|
136
141
|
const { chunk, index } = this.messages.get(messageId, messages.length) ?? {};
|
|
137
142
|
if (!chunk || index == null) return values$1;
|
|
138
|
-
if (chunk.getType() === "remove")
|
|
143
|
+
if (chunk.getType() === "remove") if (chunk.id === REMOVE_ALL_MESSAGES) messages = [];
|
|
144
|
+
else messages.splice(index, 1);
|
|
139
145
|
else messages[index] = require_messages.toMessageDict(chunk);
|
|
140
146
|
return options.setMessages(values$1, messages);
|
|
141
147
|
});
|
package/dist/ui/manager.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"manager.cjs","names":["timeoutId: NodeJS.Timeout | number | undefined","streamError: StreamError | undefined","StreamError","values","toMessageDict"],"sources":["../../src/ui/manager.ts"],"sourcesContent":["import type {\n CheckpointsStreamEvent,\n CustomStreamEvent,\n DebugStreamEvent,\n ErrorStreamEvent,\n EventsStreamEvent,\n FeedbackStreamEvent,\n MessagesTupleStreamEvent,\n MetadataStreamEvent,\n TasksStreamEvent,\n UpdatesStreamEvent,\n ValuesStreamEvent,\n} from \"../types.stream.js\";\nimport { MessageTupleManager, toMessageDict } from \"./messages.js\";\nimport { StreamError } from \"./errors.js\";\nimport type { Message } from \"../types.messages.js\";\n\ntype BagTemplate = {\n ConfigurableType?: Record<string, unknown>;\n InterruptType?: unknown;\n CustomEventType?: unknown;\n UpdateType?: unknown;\n};\n\ntype GetUpdateType<\n Bag extends BagTemplate,\n StateType extends Record<string, unknown>\n> = Bag extends { UpdateType: unknown }\n ? Bag[\"UpdateType\"]\n : Partial<StateType>;\n\ntype GetCustomEventType<Bag extends BagTemplate> = Bag extends {\n CustomEventType: unknown;\n}\n ? Bag[\"CustomEventType\"]\n : unknown;\n\ntype EventStreamMap<StateType, UpdateType, CustomType> = {\n values: ValuesStreamEvent<StateType>;\n updates: UpdatesStreamEvent<UpdateType>;\n custom: CustomStreamEvent<CustomType>;\n debug: DebugStreamEvent;\n messages: MessagesTupleStreamEvent;\n events: EventsStreamEvent;\n metadata: MetadataStreamEvent;\n checkpoints: CheckpointsStreamEvent<StateType>;\n tasks: TasksStreamEvent<StateType, UpdateType>;\n error: ErrorStreamEvent;\n feedback: FeedbackStreamEvent;\n};\n\nexport type EventStreamEvent<StateType, UpdateType, CustomType> =\n EventStreamMap<StateType, UpdateType, CustomType>[keyof EventStreamMap<\n StateType,\n UpdateType,\n CustomType\n >];\n\ninterface StreamManagerEventCallbacks<\n StateType extends Record<string, unknown>,\n Bag extends BagTemplate = BagTemplate\n> {\n onUpdateEvent?: (\n data: UpdatesStreamEvent<GetUpdateType<Bag, StateType>>[\"data\"],\n options: {\n namespace: string[] | undefined;\n mutate: (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => void;\n }\n ) => void;\n onCustomEvent?: (\n data: GetCustomEventType<Bag>,\n options: {\n namespace: string[] | undefined;\n mutate: (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => void;\n }\n ) => void;\n onMetadataEvent?: (data: MetadataStreamEvent[\"data\"]) => void;\n onLangChainEvent?: (data: EventsStreamEvent[\"data\"]) => void;\n onDebugEvent?: (\n data: DebugStreamEvent[\"data\"],\n options: { namespace: string[] | undefined }\n ) => void;\n onCheckpointEvent?: (\n data: CheckpointsStreamEvent<StateType>[\"data\"],\n options: { namespace: string[] | undefined }\n ) => void;\n onTaskEvent?: (\n data: TasksStreamEvent<StateType, GetUpdateType<Bag, StateType>>[\"data\"],\n options: { namespace: string[] | undefined }\n ) => void;\n}\n\nexport class StreamManager<\n StateType extends Record<string, unknown>,\n Bag extends BagTemplate = BagTemplate\n> {\n private abortRef = new AbortController();\n\n private messages: MessageTupleManager;\n\n private listeners = new Set<() => void>();\n\n private throttle: number | boolean;\n\n private queue: Promise<unknown> = Promise.resolve();\n\n private queueSize: number = 0;\n\n private state: {\n isLoading: boolean;\n values: [values: StateType, kind: \"stream\" | \"stop\"] | null;\n error: unknown;\n };\n\n constructor(\n messages: MessageTupleManager,\n options: { throttle: number | boolean }\n ) {\n this.messages = messages;\n this.state = { isLoading: false, values: null, error: undefined };\n this.throttle = options.throttle;\n }\n\n private setState = (newState: Partial<typeof this.state>) => {\n this.state = { ...this.state, ...newState };\n this.notifyListeners();\n };\n\n private notifyListeners = () => {\n this.listeners.forEach((listener) => listener());\n };\n\n subscribe = (listener: () => void): (() => void) => {\n if (this.throttle === false) {\n this.listeners.add(listener);\n return () => this.listeners.delete(listener);\n }\n\n const timeoutMs = this.throttle === true ? 0 : this.throttle;\n let timeoutId: NodeJS.Timeout | number | undefined;\n\n const throttledListener = () => {\n clearTimeout(timeoutId);\n timeoutId = setTimeout(() => {\n clearTimeout(timeoutId);\n listener();\n }, timeoutMs);\n };\n\n this.listeners.add(throttledListener);\n return () => {\n clearTimeout(timeoutId);\n this.listeners.delete(throttledListener);\n };\n };\n\n getSnapshot = () => this.state;\n\n get isLoading() {\n return this.state.isLoading;\n }\n\n get values() {\n return this.state.values?.[0] ?? null;\n }\n\n get error() {\n return this.state.error;\n }\n\n setStreamValues = (\n values:\n | (StateType | null)\n | ((prev: StateType | null, kind: \"stream\" | \"stop\") => StateType | null),\n kind: \"stream\" | \"stop\" = \"stream\"\n ) => {\n if (typeof values === \"function\") {\n const [prevValues, prevKind] = this.state.values ?? [null, \"stream\"];\n const nextValues = values(prevValues, prevKind);\n this.setState({ values: nextValues != null ? [nextValues, kind] : null });\n } else {\n const nextValues = values != null ? [values, kind] : null;\n this.setState({ values: nextValues as [StateType, \"stream\" | \"stop\"] });\n }\n };\n\n private getMutateFn = (kind: \"stream\" | \"stop\", historyValues: StateType) => {\n return (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => {\n const prev = {\n ...historyValues,\n ...(this.state.values ?? [null, \"stream\"])[0],\n };\n const next = typeof update === \"function\" ? update(prev) : update;\n this.setStreamValues({ ...prev, ...next }, kind);\n };\n };\n\n private matchEventType = <\n T extends keyof EventStreamMap<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >\n >(\n expected: T,\n actual: EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >[\"event\"],\n _data: EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >[\"data\"]\n ): _data is EventStreamMap<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >[T][\"data\"] => {\n return expected === actual || actual.startsWith(`${expected}|`);\n };\n\n protected enqueue = async (\n action: (\n signal: AbortSignal\n ) => Promise<\n AsyncGenerator<\n EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >\n >\n >,\n options: {\n getMessages: (values: StateType) => Message[];\n\n setMessages: (current: StateType, messages: Message[]) => StateType;\n\n initialValues: StateType;\n\n callbacks: StreamManagerEventCallbacks<StateType, Bag>;\n\n onSuccess: () =>\n | StateType\n | null\n | undefined\n | void\n | Promise<StateType | null | undefined | void>;\n\n onError: (error: unknown) => void | Promise<void>;\n\n onFinish?: () => void;\n }\n ) => {\n try {\n this.queueSize = Math.max(0, this.queueSize - 1);\n this.setState({ isLoading: true, error: undefined });\n this.abortRef = new AbortController();\n\n const run = await action(this.abortRef.signal);\n\n let streamError: StreamError | undefined;\n for await (const { event, data } of run) {\n if (event === \"error\") {\n streamError = new StreamError(data);\n break;\n }\n\n const namespace = event.includes(\"|\")\n ? event.split(\"|\").slice(1)\n : undefined;\n\n const mutate = this.getMutateFn(\"stream\", options.initialValues);\n\n if (event === \"metadata\") options.callbacks.onMetadataEvent?.(data);\n if (event === \"events\") options.callbacks.onLangChainEvent?.(data);\n\n if (this.matchEventType(\"updates\", event, data)) {\n options.callbacks.onUpdateEvent?.(data, { namespace, mutate });\n }\n\n if (this.matchEventType(\"custom\", event, data)) {\n options.callbacks.onCustomEvent?.(data, { namespace, mutate });\n }\n\n if (this.matchEventType(\"checkpoints\", event, data)) {\n options.callbacks.onCheckpointEvent?.(data, { namespace });\n }\n\n if (this.matchEventType(\"tasks\", event, data)) {\n options.callbacks.onTaskEvent?.(data, { namespace });\n }\n\n if (this.matchEventType(\"debug\", event, data)) {\n options.callbacks.onDebugEvent?.(data, { namespace });\n }\n\n if (event === \"values\") {\n if (\"__interrupt__\" in data) {\n this.setStreamValues((prev) => ({ ...prev, ...data }));\n } else {\n this.setStreamValues(data);\n }\n }\n\n if (this.matchEventType(\"messages\", event, data)) {\n const [serialized, metadata] = data;\n\n const messageId = this.messages.add(serialized, metadata);\n if (!messageId) {\n console.warn(\n \"Failed to add message to manager, no message ID found\"\n );\n continue;\n }\n\n this.setStreamValues((streamValues) => {\n const values = { ...options.initialValues, ...streamValues };\n\n // Assumption: we're concatenating the message\n const messages = options.getMessages(values).slice();\n const { chunk, index } =\n this.messages.get(messageId, messages.length) ?? {};\n\n if (!chunk || index == null) return values;\n if (chunk.getType() === \"remove\") {\n messages.splice(index, 1);\n } else {\n messages[index] = toMessageDict(chunk);\n }\n\n return options.setMessages(values, messages);\n });\n }\n }\n\n if (streamError != null) throw streamError;\n\n const values = await options.onSuccess?.();\n if (typeof values !== \"undefined\" && this.queueSize === 0) {\n this.setStreamValues(values);\n }\n } catch (error) {\n if (\n !(\n error instanceof Error && // eslint-disable-line no-instanceof/no-instanceof\n (error.name === \"AbortError\" || error.name === \"TimeoutError\")\n )\n ) {\n console.error(error);\n this.setState({ error });\n await options.onError?.(error);\n }\n } finally {\n this.setState({ isLoading: false });\n this.abortRef = new AbortController();\n options.onFinish?.();\n }\n };\n\n start = async (\n action: (\n signal: AbortSignal\n ) => Promise<\n AsyncGenerator<\n EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >\n >\n >,\n options: {\n getMessages: (values: StateType) => Message[];\n\n setMessages: (current: StateType, messages: Message[]) => StateType;\n\n initialValues: StateType;\n\n callbacks: StreamManagerEventCallbacks<StateType, Bag>;\n\n onSuccess: () =>\n | StateType\n | null\n | undefined\n | void\n | Promise<StateType | null | undefined | void>;\n\n onError: (error: unknown) => void | Promise<void>;\n\n onFinish?: () => void;\n }\n ): Promise<void> => {\n this.queueSize += 1;\n this.queue = this.queue.then(() => this.enqueue(action, options));\n };\n\n stop = async (\n historyValues: StateType,\n options: {\n onStop?: (options: {\n mutate: (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => void;\n }) => void;\n }\n ): Promise<void> => {\n this.abortRef.abort();\n this.abortRef = new AbortController();\n\n options.onStop?.({ mutate: this.getMutateFn(\"stop\", historyValues) });\n };\n\n clear = () => {\n // Cancel any running streams\n this.abortRef.abort();\n this.abortRef = new AbortController();\n\n // Set the stream state to null\n this.setState({ error: undefined, values: null, isLoading: false });\n\n // Clear any pending messages\n this.messages.clear();\n };\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"manager.cjs","names":["StreamError","values","toMessageDict"],"sources":["../../src/ui/manager.ts"],"sourcesContent":["import type {\n CheckpointsStreamEvent,\n CustomStreamEvent,\n DebugStreamEvent,\n ErrorStreamEvent,\n EventsStreamEvent,\n FeedbackStreamEvent,\n MessagesTupleStreamEvent,\n MetadataStreamEvent,\n TasksStreamEvent,\n UpdatesStreamEvent,\n ValuesStreamEvent,\n} from \"../types.stream.js\";\nimport { MessageTupleManager, toMessageDict } from \"./messages.js\";\nimport { StreamError } from \"./errors.js\";\nimport type { Message } from \"../types.messages.js\";\nimport type { BagTemplate } from \"../types.template.js\";\n\n/**\n * Special ID used by LangGraph's messagesStateReducer to signal\n * that all messages should be removed from the state.\n */\nexport const REMOVE_ALL_MESSAGES = \"__remove_all__\";\n\ntype GetUpdateType<\n Bag extends BagTemplate,\n StateType extends Record<string, unknown>\n> = Bag extends { UpdateType: unknown }\n ? Bag[\"UpdateType\"]\n : Partial<StateType>;\n\ntype GetCustomEventType<Bag extends BagTemplate> = Bag extends {\n CustomEventType: unknown;\n}\n ? Bag[\"CustomEventType\"]\n : unknown;\n\ntype EventStreamMap<StateType, UpdateType, CustomType> = {\n values: ValuesStreamEvent<StateType>;\n updates: UpdatesStreamEvent<UpdateType>;\n custom: CustomStreamEvent<CustomType>;\n debug: DebugStreamEvent;\n messages: MessagesTupleStreamEvent;\n events: EventsStreamEvent;\n metadata: MetadataStreamEvent;\n checkpoints: CheckpointsStreamEvent<StateType>;\n tasks: TasksStreamEvent<StateType, UpdateType>;\n error: ErrorStreamEvent;\n feedback: FeedbackStreamEvent;\n};\n\nexport type EventStreamEvent<StateType, UpdateType, CustomType> =\n EventStreamMap<StateType, UpdateType, CustomType>[keyof EventStreamMap<\n StateType,\n UpdateType,\n CustomType\n >];\n\ninterface StreamManagerEventCallbacks<\n StateType extends Record<string, unknown>,\n Bag extends BagTemplate = BagTemplate\n> {\n onUpdateEvent?: (\n data: UpdatesStreamEvent<GetUpdateType<Bag, StateType>>[\"data\"],\n options: {\n namespace: string[] | undefined;\n mutate: (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => void;\n }\n ) => void;\n onCustomEvent?: (\n data: GetCustomEventType<Bag>,\n options: {\n namespace: string[] | undefined;\n mutate: (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => void;\n }\n ) => void;\n onMetadataEvent?: (data: MetadataStreamEvent[\"data\"]) => void;\n onLangChainEvent?: (data: EventsStreamEvent[\"data\"]) => void;\n onDebugEvent?: (\n data: DebugStreamEvent[\"data\"],\n options: { namespace: string[] | undefined }\n ) => void;\n onCheckpointEvent?: (\n data: CheckpointsStreamEvent<StateType>[\"data\"],\n options: { namespace: string[] | undefined }\n ) => void;\n onTaskEvent?: (\n data: TasksStreamEvent<StateType, GetUpdateType<Bag, StateType>>[\"data\"],\n options: { namespace: string[] | undefined }\n ) => void;\n}\n\nexport class StreamManager<\n StateType extends Record<string, unknown>,\n Bag extends BagTemplate = BagTemplate\n> {\n private abortRef = new AbortController();\n\n private messages: MessageTupleManager;\n\n private listeners = new Set<() => void>();\n\n private throttle: number | boolean;\n\n private queue: Promise<unknown> = Promise.resolve();\n\n private queueSize: number = 0;\n\n private state: {\n isLoading: boolean;\n values: [values: StateType, kind: \"stream\" | \"stop\"] | null;\n error: unknown;\n };\n\n constructor(\n messages: MessageTupleManager,\n options: { throttle: number | boolean }\n ) {\n this.messages = messages;\n this.state = { isLoading: false, values: null, error: undefined };\n this.throttle = options.throttle;\n }\n\n private setState = (newState: Partial<typeof this.state>) => {\n this.state = { ...this.state, ...newState };\n this.notifyListeners();\n };\n\n private notifyListeners = () => {\n this.listeners.forEach((listener) => listener());\n };\n\n subscribe = (listener: () => void): (() => void) => {\n if (this.throttle === false) {\n this.listeners.add(listener);\n return () => this.listeners.delete(listener);\n }\n\n const timeoutMs = this.throttle === true ? 0 : this.throttle;\n let timeoutId: NodeJS.Timeout | number | undefined;\n\n const throttledListener = () => {\n clearTimeout(timeoutId);\n timeoutId = setTimeout(() => {\n clearTimeout(timeoutId);\n listener();\n }, timeoutMs);\n };\n\n this.listeners.add(throttledListener);\n return () => {\n clearTimeout(timeoutId);\n this.listeners.delete(throttledListener);\n };\n };\n\n getSnapshot = () => this.state;\n\n get isLoading() {\n return this.state.isLoading;\n }\n\n get values() {\n return this.state.values?.[0] ?? null;\n }\n\n get error() {\n return this.state.error;\n }\n\n setStreamValues = (\n values:\n | (StateType | null)\n | ((prev: StateType | null, kind: \"stream\" | \"stop\") => StateType | null),\n kind: \"stream\" | \"stop\" = \"stream\"\n ) => {\n if (typeof values === \"function\") {\n const [prevValues, prevKind] = this.state.values ?? [null, \"stream\"];\n const nextValues = values(prevValues, prevKind);\n this.setState({ values: nextValues != null ? [nextValues, kind] : null });\n } else {\n const nextValues = values != null ? [values, kind] : null;\n this.setState({ values: nextValues as [StateType, \"stream\" | \"stop\"] });\n }\n };\n\n private getMutateFn = (kind: \"stream\" | \"stop\", historyValues: StateType) => {\n return (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => {\n const prev = {\n ...historyValues,\n ...(this.state.values ?? [null, \"stream\"])[0],\n };\n const next = typeof update === \"function\" ? update(prev) : update;\n this.setStreamValues({ ...prev, ...next }, kind);\n };\n };\n\n private matchEventType = <\n T extends keyof EventStreamMap<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >\n >(\n expected: T,\n actual: EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >[\"event\"],\n _data: EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >[\"data\"]\n ): _data is EventStreamMap<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >[T][\"data\"] => {\n return expected === actual || actual.startsWith(`${expected}|`);\n };\n\n protected enqueue = async (\n action: (\n signal: AbortSignal\n ) => Promise<\n AsyncGenerator<\n EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >\n >\n >,\n options: {\n getMessages: (values: StateType) => Message[];\n\n setMessages: (current: StateType, messages: Message[]) => StateType;\n\n initialValues: StateType;\n\n callbacks: StreamManagerEventCallbacks<StateType, Bag>;\n\n onSuccess: () =>\n | StateType\n | null\n | undefined\n | void\n | Promise<StateType | null | undefined | void>;\n\n onError: (error: unknown) => void | Promise<void>;\n\n onFinish?: () => void;\n }\n ) => {\n try {\n this.queueSize = Math.max(0, this.queueSize - 1);\n this.setState({ isLoading: true, error: undefined });\n this.abortRef = new AbortController();\n\n const run = await action(this.abortRef.signal);\n\n let streamError: StreamError | undefined;\n for await (const { event, data } of run) {\n if (event === \"error\") {\n streamError = new StreamError(data);\n break;\n }\n\n const namespace = event.includes(\"|\")\n ? event.split(\"|\").slice(1)\n : undefined;\n\n const mutate = this.getMutateFn(\"stream\", options.initialValues);\n\n if (event === \"metadata\") options.callbacks.onMetadataEvent?.(data);\n if (event === \"events\") options.callbacks.onLangChainEvent?.(data);\n\n if (this.matchEventType(\"updates\", event, data)) {\n options.callbacks.onUpdateEvent?.(data, { namespace, mutate });\n }\n\n if (this.matchEventType(\"custom\", event, data)) {\n options.callbacks.onCustomEvent?.(data, { namespace, mutate });\n }\n\n if (this.matchEventType(\"checkpoints\", event, data)) {\n options.callbacks.onCheckpointEvent?.(data, { namespace });\n }\n\n if (this.matchEventType(\"tasks\", event, data)) {\n options.callbacks.onTaskEvent?.(data, { namespace });\n }\n\n if (this.matchEventType(\"debug\", event, data)) {\n options.callbacks.onDebugEvent?.(data, { namespace });\n }\n\n if (event === \"values\") {\n if (\"__interrupt__\" in data) {\n this.setStreamValues((prev) => ({ ...prev, ...data }));\n } else {\n this.setStreamValues(data);\n }\n }\n\n if (this.matchEventType(\"messages\", event, data)) {\n const [serialized, metadata] = data;\n\n const messageId = this.messages.add(serialized, metadata);\n if (!messageId) {\n console.warn(\n \"Failed to add message to manager, no message ID found\"\n );\n continue;\n }\n\n this.setStreamValues((streamValues) => {\n const values = { ...options.initialValues, ...streamValues };\n\n // Assumption: we're concatenating the message\n let messages = options.getMessages(values).slice();\n const { chunk, index } =\n this.messages.get(messageId, messages.length) ?? {};\n\n if (!chunk || index == null) return values;\n if (chunk.getType() === \"remove\") {\n // Check for special REMOVE_ALL_MESSAGES sentinel\n if (chunk.id === REMOVE_ALL_MESSAGES) {\n // Clear all messages when __remove_all__ is received\n messages = [];\n } else {\n messages.splice(index, 1);\n }\n } else {\n messages[index] = toMessageDict(chunk);\n }\n\n return options.setMessages(values, messages);\n });\n }\n }\n\n if (streamError != null) throw streamError;\n\n const values = await options.onSuccess?.();\n if (typeof values !== \"undefined\" && this.queueSize === 0) {\n this.setStreamValues(values);\n }\n } catch (error) {\n if (\n !(\n error instanceof Error && // eslint-disable-line no-instanceof/no-instanceof\n (error.name === \"AbortError\" || error.name === \"TimeoutError\")\n )\n ) {\n console.error(error);\n this.setState({ error });\n await options.onError?.(error);\n }\n } finally {\n this.setState({ isLoading: false });\n this.abortRef = new AbortController();\n options.onFinish?.();\n }\n };\n\n start = async (\n action: (\n signal: AbortSignal\n ) => Promise<\n AsyncGenerator<\n EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >\n >\n >,\n options: {\n getMessages: (values: StateType) => Message[];\n\n setMessages: (current: StateType, messages: Message[]) => StateType;\n\n initialValues: StateType;\n\n callbacks: StreamManagerEventCallbacks<StateType, Bag>;\n\n onSuccess: () =>\n | StateType\n | null\n | undefined\n | void\n | Promise<StateType | null | undefined | void>;\n\n onError: (error: unknown) => void | Promise<void>;\n\n onFinish?: () => void;\n }\n ): Promise<void> => {\n this.queueSize += 1;\n this.queue = this.queue.then(() => this.enqueue(action, options));\n };\n\n stop = async (\n historyValues: StateType,\n options: {\n onStop?: (options: {\n mutate: (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => void;\n }) => void;\n }\n ): Promise<void> => {\n this.abortRef.abort();\n this.abortRef = new AbortController();\n\n options.onStop?.({ mutate: this.getMutateFn(\"stop\", historyValues) });\n };\n\n clear = () => {\n // Cancel any running streams\n this.abortRef.abort();\n this.abortRef = new AbortController();\n\n // Set the stream state to null\n this.setState({ error: undefined, values: null, isLoading: false });\n\n // Clear any pending messages\n this.messages.clear();\n };\n}\n"],"mappings":"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"}
|
package/dist/ui/manager.js
CHANGED
|
@@ -2,6 +2,11 @@ import { StreamError } from "./errors.js";
|
|
|
2
2
|
import { toMessageDict } from "./messages.js";
|
|
3
3
|
|
|
4
4
|
//#region src/ui/manager.ts
|
|
5
|
+
/**
|
|
6
|
+
* Special ID used by LangGraph's messagesStateReducer to signal
|
|
7
|
+
* that all messages should be removed from the state.
|
|
8
|
+
*/
|
|
9
|
+
const REMOVE_ALL_MESSAGES = "__remove_all__";
|
|
5
10
|
var StreamManager = class {
|
|
6
11
|
abortRef = new AbortController();
|
|
7
12
|
messages;
|
|
@@ -132,10 +137,11 @@ var StreamManager = class {
|
|
|
132
137
|
...options.initialValues,
|
|
133
138
|
...streamValues
|
|
134
139
|
};
|
|
135
|
-
|
|
140
|
+
let messages = options.getMessages(values$1).slice();
|
|
136
141
|
const { chunk, index } = this.messages.get(messageId, messages.length) ?? {};
|
|
137
142
|
if (!chunk || index == null) return values$1;
|
|
138
|
-
if (chunk.getType() === "remove")
|
|
143
|
+
if (chunk.getType() === "remove") if (chunk.id === REMOVE_ALL_MESSAGES) messages = [];
|
|
144
|
+
else messages.splice(index, 1);
|
|
139
145
|
else messages[index] = toMessageDict(chunk);
|
|
140
146
|
return options.setMessages(values$1, messages);
|
|
141
147
|
});
|
package/dist/ui/manager.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"manager.js","names":["timeoutId: NodeJS.Timeout | number | undefined","streamError: StreamError | undefined","values"],"sources":["../../src/ui/manager.ts"],"sourcesContent":["import type {\n CheckpointsStreamEvent,\n CustomStreamEvent,\n DebugStreamEvent,\n ErrorStreamEvent,\n EventsStreamEvent,\n FeedbackStreamEvent,\n MessagesTupleStreamEvent,\n MetadataStreamEvent,\n TasksStreamEvent,\n UpdatesStreamEvent,\n ValuesStreamEvent,\n} from \"../types.stream.js\";\nimport { MessageTupleManager, toMessageDict } from \"./messages.js\";\nimport { StreamError } from \"./errors.js\";\nimport type { Message } from \"../types.messages.js\";\n\ntype BagTemplate = {\n ConfigurableType?: Record<string, unknown>;\n InterruptType?: unknown;\n CustomEventType?: unknown;\n UpdateType?: unknown;\n};\n\ntype GetUpdateType<\n Bag extends BagTemplate,\n StateType extends Record<string, unknown>\n> = Bag extends { UpdateType: unknown }\n ? Bag[\"UpdateType\"]\n : Partial<StateType>;\n\ntype GetCustomEventType<Bag extends BagTemplate> = Bag extends {\n CustomEventType: unknown;\n}\n ? Bag[\"CustomEventType\"]\n : unknown;\n\ntype EventStreamMap<StateType, UpdateType, CustomType> = {\n values: ValuesStreamEvent<StateType>;\n updates: UpdatesStreamEvent<UpdateType>;\n custom: CustomStreamEvent<CustomType>;\n debug: DebugStreamEvent;\n messages: MessagesTupleStreamEvent;\n events: EventsStreamEvent;\n metadata: MetadataStreamEvent;\n checkpoints: CheckpointsStreamEvent<StateType>;\n tasks: TasksStreamEvent<StateType, UpdateType>;\n error: ErrorStreamEvent;\n feedback: FeedbackStreamEvent;\n};\n\nexport type EventStreamEvent<StateType, UpdateType, CustomType> =\n EventStreamMap<StateType, UpdateType, CustomType>[keyof EventStreamMap<\n StateType,\n UpdateType,\n CustomType\n >];\n\ninterface StreamManagerEventCallbacks<\n StateType extends Record<string, unknown>,\n Bag extends BagTemplate = BagTemplate\n> {\n onUpdateEvent?: (\n data: UpdatesStreamEvent<GetUpdateType<Bag, StateType>>[\"data\"],\n options: {\n namespace: string[] | undefined;\n mutate: (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => void;\n }\n ) => void;\n onCustomEvent?: (\n data: GetCustomEventType<Bag>,\n options: {\n namespace: string[] | undefined;\n mutate: (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => void;\n }\n ) => void;\n onMetadataEvent?: (data: MetadataStreamEvent[\"data\"]) => void;\n onLangChainEvent?: (data: EventsStreamEvent[\"data\"]) => void;\n onDebugEvent?: (\n data: DebugStreamEvent[\"data\"],\n options: { namespace: string[] | undefined }\n ) => void;\n onCheckpointEvent?: (\n data: CheckpointsStreamEvent<StateType>[\"data\"],\n options: { namespace: string[] | undefined }\n ) => void;\n onTaskEvent?: (\n data: TasksStreamEvent<StateType, GetUpdateType<Bag, StateType>>[\"data\"],\n options: { namespace: string[] | undefined }\n ) => void;\n}\n\nexport class StreamManager<\n StateType extends Record<string, unknown>,\n Bag extends BagTemplate = BagTemplate\n> {\n private abortRef = new AbortController();\n\n private messages: MessageTupleManager;\n\n private listeners = new Set<() => void>();\n\n private throttle: number | boolean;\n\n private queue: Promise<unknown> = Promise.resolve();\n\n private queueSize: number = 0;\n\n private state: {\n isLoading: boolean;\n values: [values: StateType, kind: \"stream\" | \"stop\"] | null;\n error: unknown;\n };\n\n constructor(\n messages: MessageTupleManager,\n options: { throttle: number | boolean }\n ) {\n this.messages = messages;\n this.state = { isLoading: false, values: null, error: undefined };\n this.throttle = options.throttle;\n }\n\n private setState = (newState: Partial<typeof this.state>) => {\n this.state = { ...this.state, ...newState };\n this.notifyListeners();\n };\n\n private notifyListeners = () => {\n this.listeners.forEach((listener) => listener());\n };\n\n subscribe = (listener: () => void): (() => void) => {\n if (this.throttle === false) {\n this.listeners.add(listener);\n return () => this.listeners.delete(listener);\n }\n\n const timeoutMs = this.throttle === true ? 0 : this.throttle;\n let timeoutId: NodeJS.Timeout | number | undefined;\n\n const throttledListener = () => {\n clearTimeout(timeoutId);\n timeoutId = setTimeout(() => {\n clearTimeout(timeoutId);\n listener();\n }, timeoutMs);\n };\n\n this.listeners.add(throttledListener);\n return () => {\n clearTimeout(timeoutId);\n this.listeners.delete(throttledListener);\n };\n };\n\n getSnapshot = () => this.state;\n\n get isLoading() {\n return this.state.isLoading;\n }\n\n get values() {\n return this.state.values?.[0] ?? null;\n }\n\n get error() {\n return this.state.error;\n }\n\n setStreamValues = (\n values:\n | (StateType | null)\n | ((prev: StateType | null, kind: \"stream\" | \"stop\") => StateType | null),\n kind: \"stream\" | \"stop\" = \"stream\"\n ) => {\n if (typeof values === \"function\") {\n const [prevValues, prevKind] = this.state.values ?? [null, \"stream\"];\n const nextValues = values(prevValues, prevKind);\n this.setState({ values: nextValues != null ? [nextValues, kind] : null });\n } else {\n const nextValues = values != null ? [values, kind] : null;\n this.setState({ values: nextValues as [StateType, \"stream\" | \"stop\"] });\n }\n };\n\n private getMutateFn = (kind: \"stream\" | \"stop\", historyValues: StateType) => {\n return (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => {\n const prev = {\n ...historyValues,\n ...(this.state.values ?? [null, \"stream\"])[0],\n };\n const next = typeof update === \"function\" ? update(prev) : update;\n this.setStreamValues({ ...prev, ...next }, kind);\n };\n };\n\n private matchEventType = <\n T extends keyof EventStreamMap<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >\n >(\n expected: T,\n actual: EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >[\"event\"],\n _data: EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >[\"data\"]\n ): _data is EventStreamMap<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >[T][\"data\"] => {\n return expected === actual || actual.startsWith(`${expected}|`);\n };\n\n protected enqueue = async (\n action: (\n signal: AbortSignal\n ) => Promise<\n AsyncGenerator<\n EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >\n >\n >,\n options: {\n getMessages: (values: StateType) => Message[];\n\n setMessages: (current: StateType, messages: Message[]) => StateType;\n\n initialValues: StateType;\n\n callbacks: StreamManagerEventCallbacks<StateType, Bag>;\n\n onSuccess: () =>\n | StateType\n | null\n | undefined\n | void\n | Promise<StateType | null | undefined | void>;\n\n onError: (error: unknown) => void | Promise<void>;\n\n onFinish?: () => void;\n }\n ) => {\n try {\n this.queueSize = Math.max(0, this.queueSize - 1);\n this.setState({ isLoading: true, error: undefined });\n this.abortRef = new AbortController();\n\n const run = await action(this.abortRef.signal);\n\n let streamError: StreamError | undefined;\n for await (const { event, data } of run) {\n if (event === \"error\") {\n streamError = new StreamError(data);\n break;\n }\n\n const namespace = event.includes(\"|\")\n ? event.split(\"|\").slice(1)\n : undefined;\n\n const mutate = this.getMutateFn(\"stream\", options.initialValues);\n\n if (event === \"metadata\") options.callbacks.onMetadataEvent?.(data);\n if (event === \"events\") options.callbacks.onLangChainEvent?.(data);\n\n if (this.matchEventType(\"updates\", event, data)) {\n options.callbacks.onUpdateEvent?.(data, { namespace, mutate });\n }\n\n if (this.matchEventType(\"custom\", event, data)) {\n options.callbacks.onCustomEvent?.(data, { namespace, mutate });\n }\n\n if (this.matchEventType(\"checkpoints\", event, data)) {\n options.callbacks.onCheckpointEvent?.(data, { namespace });\n }\n\n if (this.matchEventType(\"tasks\", event, data)) {\n options.callbacks.onTaskEvent?.(data, { namespace });\n }\n\n if (this.matchEventType(\"debug\", event, data)) {\n options.callbacks.onDebugEvent?.(data, { namespace });\n }\n\n if (event === \"values\") {\n if (\"__interrupt__\" in data) {\n this.setStreamValues((prev) => ({ ...prev, ...data }));\n } else {\n this.setStreamValues(data);\n }\n }\n\n if (this.matchEventType(\"messages\", event, data)) {\n const [serialized, metadata] = data;\n\n const messageId = this.messages.add(serialized, metadata);\n if (!messageId) {\n console.warn(\n \"Failed to add message to manager, no message ID found\"\n );\n continue;\n }\n\n this.setStreamValues((streamValues) => {\n const values = { ...options.initialValues, ...streamValues };\n\n // Assumption: we're concatenating the message\n const messages = options.getMessages(values).slice();\n const { chunk, index } =\n this.messages.get(messageId, messages.length) ?? {};\n\n if (!chunk || index == null) return values;\n if (chunk.getType() === \"remove\") {\n messages.splice(index, 1);\n } else {\n messages[index] = toMessageDict(chunk);\n }\n\n return options.setMessages(values, messages);\n });\n }\n }\n\n if (streamError != null) throw streamError;\n\n const values = await options.onSuccess?.();\n if (typeof values !== \"undefined\" && this.queueSize === 0) {\n this.setStreamValues(values);\n }\n } catch (error) {\n if (\n !(\n error instanceof Error && // eslint-disable-line no-instanceof/no-instanceof\n (error.name === \"AbortError\" || error.name === \"TimeoutError\")\n )\n ) {\n console.error(error);\n this.setState({ error });\n await options.onError?.(error);\n }\n } finally {\n this.setState({ isLoading: false });\n this.abortRef = new AbortController();\n options.onFinish?.();\n }\n };\n\n start = async (\n action: (\n signal: AbortSignal\n ) => Promise<\n AsyncGenerator<\n EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >\n >\n >,\n options: {\n getMessages: (values: StateType) => Message[];\n\n setMessages: (current: StateType, messages: Message[]) => StateType;\n\n initialValues: StateType;\n\n callbacks: StreamManagerEventCallbacks<StateType, Bag>;\n\n onSuccess: () =>\n | StateType\n | null\n | undefined\n | void\n | Promise<StateType | null | undefined | void>;\n\n onError: (error: unknown) => void | Promise<void>;\n\n onFinish?: () => void;\n }\n ): Promise<void> => {\n this.queueSize += 1;\n this.queue = this.queue.then(() => this.enqueue(action, options));\n };\n\n stop = async (\n historyValues: StateType,\n options: {\n onStop?: (options: {\n mutate: (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => void;\n }) => void;\n }\n ): Promise<void> => {\n this.abortRef.abort();\n this.abortRef = new AbortController();\n\n options.onStop?.({ mutate: this.getMutateFn(\"stop\", historyValues) });\n };\n\n clear = () => {\n // Cancel any running streams\n this.abortRef.abort();\n this.abortRef = new AbortController();\n\n // Set the stream state to null\n this.setState({ error: undefined, values: null, isLoading: false });\n\n // Clear any pending messages\n this.messages.clear();\n };\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"manager.js","names":["values"],"sources":["../../src/ui/manager.ts"],"sourcesContent":["import type {\n CheckpointsStreamEvent,\n CustomStreamEvent,\n DebugStreamEvent,\n ErrorStreamEvent,\n EventsStreamEvent,\n FeedbackStreamEvent,\n MessagesTupleStreamEvent,\n MetadataStreamEvent,\n TasksStreamEvent,\n UpdatesStreamEvent,\n ValuesStreamEvent,\n} from \"../types.stream.js\";\nimport { MessageTupleManager, toMessageDict } from \"./messages.js\";\nimport { StreamError } from \"./errors.js\";\nimport type { Message } from \"../types.messages.js\";\nimport type { BagTemplate } from \"../types.template.js\";\n\n/**\n * Special ID used by LangGraph's messagesStateReducer to signal\n * that all messages should be removed from the state.\n */\nexport const REMOVE_ALL_MESSAGES = \"__remove_all__\";\n\ntype GetUpdateType<\n Bag extends BagTemplate,\n StateType extends Record<string, unknown>\n> = Bag extends { UpdateType: unknown }\n ? Bag[\"UpdateType\"]\n : Partial<StateType>;\n\ntype GetCustomEventType<Bag extends BagTemplate> = Bag extends {\n CustomEventType: unknown;\n}\n ? Bag[\"CustomEventType\"]\n : unknown;\n\ntype EventStreamMap<StateType, UpdateType, CustomType> = {\n values: ValuesStreamEvent<StateType>;\n updates: UpdatesStreamEvent<UpdateType>;\n custom: CustomStreamEvent<CustomType>;\n debug: DebugStreamEvent;\n messages: MessagesTupleStreamEvent;\n events: EventsStreamEvent;\n metadata: MetadataStreamEvent;\n checkpoints: CheckpointsStreamEvent<StateType>;\n tasks: TasksStreamEvent<StateType, UpdateType>;\n error: ErrorStreamEvent;\n feedback: FeedbackStreamEvent;\n};\n\nexport type EventStreamEvent<StateType, UpdateType, CustomType> =\n EventStreamMap<StateType, UpdateType, CustomType>[keyof EventStreamMap<\n StateType,\n UpdateType,\n CustomType\n >];\n\ninterface StreamManagerEventCallbacks<\n StateType extends Record<string, unknown>,\n Bag extends BagTemplate = BagTemplate\n> {\n onUpdateEvent?: (\n data: UpdatesStreamEvent<GetUpdateType<Bag, StateType>>[\"data\"],\n options: {\n namespace: string[] | undefined;\n mutate: (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => void;\n }\n ) => void;\n onCustomEvent?: (\n data: GetCustomEventType<Bag>,\n options: {\n namespace: string[] | undefined;\n mutate: (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => void;\n }\n ) => void;\n onMetadataEvent?: (data: MetadataStreamEvent[\"data\"]) => void;\n onLangChainEvent?: (data: EventsStreamEvent[\"data\"]) => void;\n onDebugEvent?: (\n data: DebugStreamEvent[\"data\"],\n options: { namespace: string[] | undefined }\n ) => void;\n onCheckpointEvent?: (\n data: CheckpointsStreamEvent<StateType>[\"data\"],\n options: { namespace: string[] | undefined }\n ) => void;\n onTaskEvent?: (\n data: TasksStreamEvent<StateType, GetUpdateType<Bag, StateType>>[\"data\"],\n options: { namespace: string[] | undefined }\n ) => void;\n}\n\nexport class StreamManager<\n StateType extends Record<string, unknown>,\n Bag extends BagTemplate = BagTemplate\n> {\n private abortRef = new AbortController();\n\n private messages: MessageTupleManager;\n\n private listeners = new Set<() => void>();\n\n private throttle: number | boolean;\n\n private queue: Promise<unknown> = Promise.resolve();\n\n private queueSize: number = 0;\n\n private state: {\n isLoading: boolean;\n values: [values: StateType, kind: \"stream\" | \"stop\"] | null;\n error: unknown;\n };\n\n constructor(\n messages: MessageTupleManager,\n options: { throttle: number | boolean }\n ) {\n this.messages = messages;\n this.state = { isLoading: false, values: null, error: undefined };\n this.throttle = options.throttle;\n }\n\n private setState = (newState: Partial<typeof this.state>) => {\n this.state = { ...this.state, ...newState };\n this.notifyListeners();\n };\n\n private notifyListeners = () => {\n this.listeners.forEach((listener) => listener());\n };\n\n subscribe = (listener: () => void): (() => void) => {\n if (this.throttle === false) {\n this.listeners.add(listener);\n return () => this.listeners.delete(listener);\n }\n\n const timeoutMs = this.throttle === true ? 0 : this.throttle;\n let timeoutId: NodeJS.Timeout | number | undefined;\n\n const throttledListener = () => {\n clearTimeout(timeoutId);\n timeoutId = setTimeout(() => {\n clearTimeout(timeoutId);\n listener();\n }, timeoutMs);\n };\n\n this.listeners.add(throttledListener);\n return () => {\n clearTimeout(timeoutId);\n this.listeners.delete(throttledListener);\n };\n };\n\n getSnapshot = () => this.state;\n\n get isLoading() {\n return this.state.isLoading;\n }\n\n get values() {\n return this.state.values?.[0] ?? null;\n }\n\n get error() {\n return this.state.error;\n }\n\n setStreamValues = (\n values:\n | (StateType | null)\n | ((prev: StateType | null, kind: \"stream\" | \"stop\") => StateType | null),\n kind: \"stream\" | \"stop\" = \"stream\"\n ) => {\n if (typeof values === \"function\") {\n const [prevValues, prevKind] = this.state.values ?? [null, \"stream\"];\n const nextValues = values(prevValues, prevKind);\n this.setState({ values: nextValues != null ? [nextValues, kind] : null });\n } else {\n const nextValues = values != null ? [values, kind] : null;\n this.setState({ values: nextValues as [StateType, \"stream\" | \"stop\"] });\n }\n };\n\n private getMutateFn = (kind: \"stream\" | \"stop\", historyValues: StateType) => {\n return (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => {\n const prev = {\n ...historyValues,\n ...(this.state.values ?? [null, \"stream\"])[0],\n };\n const next = typeof update === \"function\" ? update(prev) : update;\n this.setStreamValues({ ...prev, ...next }, kind);\n };\n };\n\n private matchEventType = <\n T extends keyof EventStreamMap<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >\n >(\n expected: T,\n actual: EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >[\"event\"],\n _data: EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >[\"data\"]\n ): _data is EventStreamMap<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >[T][\"data\"] => {\n return expected === actual || actual.startsWith(`${expected}|`);\n };\n\n protected enqueue = async (\n action: (\n signal: AbortSignal\n ) => Promise<\n AsyncGenerator<\n EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >\n >\n >,\n options: {\n getMessages: (values: StateType) => Message[];\n\n setMessages: (current: StateType, messages: Message[]) => StateType;\n\n initialValues: StateType;\n\n callbacks: StreamManagerEventCallbacks<StateType, Bag>;\n\n onSuccess: () =>\n | StateType\n | null\n | undefined\n | void\n | Promise<StateType | null | undefined | void>;\n\n onError: (error: unknown) => void | Promise<void>;\n\n onFinish?: () => void;\n }\n ) => {\n try {\n this.queueSize = Math.max(0, this.queueSize - 1);\n this.setState({ isLoading: true, error: undefined });\n this.abortRef = new AbortController();\n\n const run = await action(this.abortRef.signal);\n\n let streamError: StreamError | undefined;\n for await (const { event, data } of run) {\n if (event === \"error\") {\n streamError = new StreamError(data);\n break;\n }\n\n const namespace = event.includes(\"|\")\n ? event.split(\"|\").slice(1)\n : undefined;\n\n const mutate = this.getMutateFn(\"stream\", options.initialValues);\n\n if (event === \"metadata\") options.callbacks.onMetadataEvent?.(data);\n if (event === \"events\") options.callbacks.onLangChainEvent?.(data);\n\n if (this.matchEventType(\"updates\", event, data)) {\n options.callbacks.onUpdateEvent?.(data, { namespace, mutate });\n }\n\n if (this.matchEventType(\"custom\", event, data)) {\n options.callbacks.onCustomEvent?.(data, { namespace, mutate });\n }\n\n if (this.matchEventType(\"checkpoints\", event, data)) {\n options.callbacks.onCheckpointEvent?.(data, { namespace });\n }\n\n if (this.matchEventType(\"tasks\", event, data)) {\n options.callbacks.onTaskEvent?.(data, { namespace });\n }\n\n if (this.matchEventType(\"debug\", event, data)) {\n options.callbacks.onDebugEvent?.(data, { namespace });\n }\n\n if (event === \"values\") {\n if (\"__interrupt__\" in data) {\n this.setStreamValues((prev) => ({ ...prev, ...data }));\n } else {\n this.setStreamValues(data);\n }\n }\n\n if (this.matchEventType(\"messages\", event, data)) {\n const [serialized, metadata] = data;\n\n const messageId = this.messages.add(serialized, metadata);\n if (!messageId) {\n console.warn(\n \"Failed to add message to manager, no message ID found\"\n );\n continue;\n }\n\n this.setStreamValues((streamValues) => {\n const values = { ...options.initialValues, ...streamValues };\n\n // Assumption: we're concatenating the message\n let messages = options.getMessages(values).slice();\n const { chunk, index } =\n this.messages.get(messageId, messages.length) ?? {};\n\n if (!chunk || index == null) return values;\n if (chunk.getType() === \"remove\") {\n // Check for special REMOVE_ALL_MESSAGES sentinel\n if (chunk.id === REMOVE_ALL_MESSAGES) {\n // Clear all messages when __remove_all__ is received\n messages = [];\n } else {\n messages.splice(index, 1);\n }\n } else {\n messages[index] = toMessageDict(chunk);\n }\n\n return options.setMessages(values, messages);\n });\n }\n }\n\n if (streamError != null) throw streamError;\n\n const values = await options.onSuccess?.();\n if (typeof values !== \"undefined\" && this.queueSize === 0) {\n this.setStreamValues(values);\n }\n } catch (error) {\n if (\n !(\n error instanceof Error && // eslint-disable-line no-instanceof/no-instanceof\n (error.name === \"AbortError\" || error.name === \"TimeoutError\")\n )\n ) {\n console.error(error);\n this.setState({ error });\n await options.onError?.(error);\n }\n } finally {\n this.setState({ isLoading: false });\n this.abortRef = new AbortController();\n options.onFinish?.();\n }\n };\n\n start = async (\n action: (\n signal: AbortSignal\n ) => Promise<\n AsyncGenerator<\n EventStreamEvent<\n StateType,\n GetUpdateType<Bag, StateType>,\n GetCustomEventType<Bag>\n >\n >\n >,\n options: {\n getMessages: (values: StateType) => Message[];\n\n setMessages: (current: StateType, messages: Message[]) => StateType;\n\n initialValues: StateType;\n\n callbacks: StreamManagerEventCallbacks<StateType, Bag>;\n\n onSuccess: () =>\n | StateType\n | null\n | undefined\n | void\n | Promise<StateType | null | undefined | void>;\n\n onError: (error: unknown) => void | Promise<void>;\n\n onFinish?: () => void;\n }\n ): Promise<void> => {\n this.queueSize += 1;\n this.queue = this.queue.then(() => this.enqueue(action, options));\n };\n\n stop = async (\n historyValues: StateType,\n options: {\n onStop?: (options: {\n mutate: (\n update: Partial<StateType> | ((prev: StateType) => Partial<StateType>)\n ) => void;\n }) => void;\n }\n ): Promise<void> => {\n this.abortRef.abort();\n this.abortRef = new AbortController();\n\n options.onStop?.({ mutate: this.getMutateFn(\"stop\", historyValues) });\n };\n\n clear = () => {\n // Cancel any running streams\n this.abortRef.abort();\n this.abortRef = new AbortController();\n\n // Set the stream state to null\n this.setState({ error: undefined, values: null, isLoading: false });\n\n // Clear any pending messages\n this.messages.clear();\n };\n}\n"],"mappings":"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"}
|
package/dist/ui/messages.cjs
CHANGED
|
@@ -1,28 +1,28 @@
|
|
|
1
1
|
const require_rolldown_runtime = require('../_virtual/rolldown_runtime.cjs');
|
|
2
|
-
|
|
2
|
+
let _langchain_core_messages = require("@langchain/core/messages");
|
|
3
3
|
|
|
4
4
|
//#region src/ui/messages.ts
|
|
5
5
|
function tryConvertToChunk(message) {
|
|
6
6
|
try {
|
|
7
|
-
if ((0,
|
|
8
|
-
return (0,
|
|
7
|
+
if ((0, _langchain_core_messages.isBaseMessageChunk)(message)) return message;
|
|
8
|
+
return (0, _langchain_core_messages.convertToChunk)(message);
|
|
9
9
|
} catch {
|
|
10
10
|
return null;
|
|
11
11
|
}
|
|
12
12
|
}
|
|
13
13
|
function tryCoerceMessageLikeToMessage(message) {
|
|
14
|
-
if (message.type === "human" || message.type === "user") return new
|
|
15
|
-
if (message.type === "ai" || message.type === "assistant") return new
|
|
16
|
-
if (message.type === "system") return new
|
|
17
|
-
if (message.type === "tool" && "tool_call_id" in message) return new
|
|
14
|
+
if (message.type === "human" || message.type === "user") return new _langchain_core_messages.HumanMessageChunk(message);
|
|
15
|
+
if (message.type === "ai" || message.type === "assistant") return new _langchain_core_messages.AIMessageChunk(message);
|
|
16
|
+
if (message.type === "system") return new _langchain_core_messages.SystemMessageChunk(message);
|
|
17
|
+
if (message.type === "tool" && "tool_call_id" in message) return new _langchain_core_messages.ToolMessageChunk({
|
|
18
18
|
...message,
|
|
19
19
|
tool_call_id: message.tool_call_id
|
|
20
20
|
});
|
|
21
|
-
if (message.type === "remove" && message.id != null) return new
|
|
21
|
+
if (message.type === "remove" && message.id != null) return new _langchain_core_messages.RemoveMessage({
|
|
22
22
|
...message,
|
|
23
23
|
id: message.id
|
|
24
24
|
});
|
|
25
|
-
return (0,
|
|
25
|
+
return (0, _langchain_core_messages.coerceMessageLikeToMessage)(message);
|
|
26
26
|
}
|
|
27
27
|
var MessageTupleManager = class {
|
|
28
28
|
chunks = {};
|
|
@@ -42,7 +42,7 @@ var MessageTupleManager = class {
|
|
|
42
42
|
this.chunks[id].metadata = metadata ?? this.chunks[id].metadata;
|
|
43
43
|
if (chunk) {
|
|
44
44
|
const prev = this.chunks[id].chunk;
|
|
45
|
-
this.chunks[id].chunk = ((0,
|
|
45
|
+
this.chunks[id].chunk = ((0, _langchain_core_messages.isBaseMessageChunk)(prev) ? prev : null)?.concat(chunk) ?? chunk;
|
|
46
46
|
} else this.chunks[id].chunk = message;
|
|
47
47
|
return id;
|
|
48
48
|
}
|
package/dist/ui/messages.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"messages.cjs","names":["HumanMessageChunk","AIMessageChunk","SystemMessageChunk","ToolMessageChunk","RemoveMessage"],"sources":["../../src/ui/messages.ts"],"sourcesContent":["import {\n type BaseMessage,\n BaseMessageChunk,\n RemoveMessage,\n convertToChunk,\n coerceMessageLikeToMessage,\n isBaseMessageChunk,\n HumanMessageChunk,\n SystemMessageChunk,\n AIMessageChunk,\n ToolMessageChunk,\n} from \"@langchain/core/messages\";\n\nimport type { Message } from \"../types.messages.js\";\n\nexport function tryConvertToChunk(\n message: BaseMessage | BaseMessageChunk\n): BaseMessageChunk | null {\n try {\n if (isBaseMessageChunk(message)) return message;\n return convertToChunk(message);\n } catch {\n return null;\n }\n}\n\nexport function tryCoerceMessageLikeToMessage(\n message: Omit<Message, \"type\"> & { type: string }\n): BaseMessage | BaseMessageChunk {\n if (message.type === \"human\" || message.type === \"user\") {\n return new HumanMessageChunk(message);\n }\n\n if (message.type === \"ai\" || message.type === \"assistant\") {\n return new AIMessageChunk(message);\n }\n\n if (message.type === \"system\") {\n return new SystemMessageChunk(message);\n }\n\n if (message.type === \"tool\" && \"tool_call_id\" in message) {\n return new ToolMessageChunk({\n ...message,\n tool_call_id: message.tool_call_id as string,\n });\n }\n\n if (message.type === \"remove\" && message.id != null) {\n return new RemoveMessage({ ...message, id: message.id });\n }\n\n return coerceMessageLikeToMessage(message);\n}\n\nexport class MessageTupleManager {\n chunks: Record<\n string,\n {\n chunk?: BaseMessageChunk | BaseMessage;\n metadata?: Record<string, unknown>;\n index?: number;\n }\n > = {};\n\n constructor() {\n this.chunks = {};\n }\n\n add(\n serialized: Message,\n metadata: Record<string, unknown> | undefined\n ): string | null {\n // TODO: this is sometimes sent from the API\n // figure out how to prevent this or move this to LC.js\n if (serialized.type.endsWith(\"MessageChunk\")) {\n // eslint-disable-next-line no-param-reassign\n serialized.type = serialized.type\n .slice(0, -\"MessageChunk\".length)\n .toLowerCase() as Message[\"type\"];\n }\n\n const message = tryCoerceMessageLikeToMessage(serialized);\n const chunk = tryConvertToChunk(message);\n\n const { id } = chunk ?? message;\n if (!id) {\n console.warn(\n \"No message ID found for chunk, ignoring in state\",\n serialized\n );\n return null;\n }\n\n this.chunks[id] ??= {};\n this.chunks[id].metadata = metadata ?? this.chunks[id].metadata;\n if (chunk) {\n const prev = this.chunks[id].chunk;\n this.chunks[id].chunk =\n (isBaseMessageChunk(prev) ? prev : null)?.concat(chunk) ?? chunk;\n } else {\n this.chunks[id].chunk = message;\n }\n\n return id;\n }\n\n clear() {\n this.chunks = {};\n }\n\n get(id: string | null | undefined, defaultIndex?: number) {\n if (id == null) return null;\n if (this.chunks[id] == null) return null;\n if (defaultIndex != null) this.chunks[id].index ??= defaultIndex;\n return this.chunks[id];\n }\n}\n\nexport const toMessageDict = (chunk: BaseMessage): Message => {\n const { type, data } = chunk.toDict();\n return { ...data, type } as Message;\n};\n"],"mappings":";;;;AAeA,SAAgB,kBACd,SACyB;AACzB,KAAI;AACF,
|
|
1
|
+
{"version":3,"file":"messages.cjs","names":["HumanMessageChunk","AIMessageChunk","SystemMessageChunk","ToolMessageChunk","RemoveMessage"],"sources":["../../src/ui/messages.ts"],"sourcesContent":["import {\n type BaseMessage,\n BaseMessageChunk,\n RemoveMessage,\n convertToChunk,\n coerceMessageLikeToMessage,\n isBaseMessageChunk,\n HumanMessageChunk,\n SystemMessageChunk,\n AIMessageChunk,\n ToolMessageChunk,\n} from \"@langchain/core/messages\";\n\nimport type { Message } from \"../types.messages.js\";\n\nexport function tryConvertToChunk(\n message: BaseMessage | BaseMessageChunk\n): BaseMessageChunk | null {\n try {\n if (isBaseMessageChunk(message)) return message;\n return convertToChunk(message);\n } catch {\n return null;\n }\n}\n\nexport function tryCoerceMessageLikeToMessage(\n message: Omit<Message, \"type\"> & { type: string }\n): BaseMessage | BaseMessageChunk {\n if (message.type === \"human\" || message.type === \"user\") {\n return new HumanMessageChunk(message);\n }\n\n if (message.type === \"ai\" || message.type === \"assistant\") {\n return new AIMessageChunk(message);\n }\n\n if (message.type === \"system\") {\n return new SystemMessageChunk(message);\n }\n\n if (message.type === \"tool\" && \"tool_call_id\" in message) {\n return new ToolMessageChunk({\n ...message,\n tool_call_id: message.tool_call_id as string,\n });\n }\n\n if (message.type === \"remove\" && message.id != null) {\n return new RemoveMessage({ ...message, id: message.id });\n }\n\n return coerceMessageLikeToMessage(message);\n}\n\nexport class MessageTupleManager {\n chunks: Record<\n string,\n {\n chunk?: BaseMessageChunk | BaseMessage;\n metadata?: Record<string, unknown>;\n index?: number;\n }\n > = {};\n\n constructor() {\n this.chunks = {};\n }\n\n add(\n serialized: Message,\n metadata: Record<string, unknown> | undefined\n ): string | null {\n // TODO: this is sometimes sent from the API\n // figure out how to prevent this or move this to LC.js\n if (serialized.type.endsWith(\"MessageChunk\")) {\n // eslint-disable-next-line no-param-reassign\n serialized.type = serialized.type\n .slice(0, -\"MessageChunk\".length)\n .toLowerCase() as Message[\"type\"];\n }\n\n const message = tryCoerceMessageLikeToMessage(serialized);\n const chunk = tryConvertToChunk(message);\n\n const { id } = chunk ?? message;\n if (!id) {\n console.warn(\n \"No message ID found for chunk, ignoring in state\",\n serialized\n );\n return null;\n }\n\n this.chunks[id] ??= {};\n this.chunks[id].metadata = metadata ?? this.chunks[id].metadata;\n if (chunk) {\n const prev = this.chunks[id].chunk;\n this.chunks[id].chunk =\n (isBaseMessageChunk(prev) ? prev : null)?.concat(chunk) ?? chunk;\n } else {\n this.chunks[id].chunk = message;\n }\n\n return id;\n }\n\n clear() {\n this.chunks = {};\n }\n\n get(id: string | null | undefined, defaultIndex?: number) {\n if (id == null) return null;\n if (this.chunks[id] == null) return null;\n if (defaultIndex != null) this.chunks[id].index ??= defaultIndex;\n return this.chunks[id];\n }\n}\n\nexport const toMessageDict = (chunk: BaseMessage): Message => {\n const { type, data } = chunk.toDict();\n return { ...data, type } as Message;\n};\n"],"mappings":";;;;AAeA,SAAgB,kBACd,SACyB;AACzB,KAAI;AACF,uDAAuB,QAAQ,CAAE,QAAO;AACxC,sDAAsB,QAAQ;SACxB;AACN,SAAO;;;AAIX,SAAgB,8BACd,SACgC;AAChC,KAAI,QAAQ,SAAS,WAAW,QAAQ,SAAS,OAC/C,QAAO,IAAIA,2CAAkB,QAAQ;AAGvC,KAAI,QAAQ,SAAS,QAAQ,QAAQ,SAAS,YAC5C,QAAO,IAAIC,wCAAe,QAAQ;AAGpC,KAAI,QAAQ,SAAS,SACnB,QAAO,IAAIC,4CAAmB,QAAQ;AAGxC,KAAI,QAAQ,SAAS,UAAU,kBAAkB,QAC/C,QAAO,IAAIC,0CAAiB;EAC1B,GAAG;EACH,cAAc,QAAQ;EACvB,CAAC;AAGJ,KAAI,QAAQ,SAAS,YAAY,QAAQ,MAAM,KAC7C,QAAO,IAAIC,uCAAc;EAAE,GAAG;EAAS,IAAI,QAAQ;EAAI,CAAC;AAG1D,iEAAkC,QAAQ;;AAG5C,IAAa,sBAAb,MAAiC;CAC/B,SAOI,EAAE;CAEN,cAAc;AACZ,OAAK,SAAS,EAAE;;CAGlB,IACE,YACA,UACe;AAGf,MAAI,WAAW,KAAK,SAAS,eAAe,CAE1C,YAAW,OAAO,WAAW,KAC1B,MAAM,GAAG,IAAuB,CAChC,aAAa;EAGlB,MAAM,UAAU,8BAA8B,WAAW;EACzD,MAAM,QAAQ,kBAAkB,QAAQ;EAExC,MAAM,EAAE,OAAO,SAAS;AACxB,MAAI,CAAC,IAAI;AACP,WAAQ,KACN,oDACA,WACD;AACD,UAAO;;AAGT,OAAK,OAAO,QAAQ,EAAE;AACtB,OAAK,OAAO,IAAI,WAAW,YAAY,KAAK,OAAO,IAAI;AACvD,MAAI,OAAO;GACT,MAAM,OAAO,KAAK,OAAO,IAAI;AAC7B,QAAK,OAAO,IAAI,0DACM,KAAK,GAAG,OAAO,OAAO,OAAO,MAAM,IAAI;QAE7D,MAAK,OAAO,IAAI,QAAQ;AAG1B,SAAO;;CAGT,QAAQ;AACN,OAAK,SAAS,EAAE;;CAGlB,IAAI,IAA+B,cAAuB;AACxD,MAAI,MAAM,KAAM,QAAO;AACvB,MAAI,KAAK,OAAO,OAAO,KAAM,QAAO;AACpC,MAAI,gBAAgB,KAAM,MAAK,OAAO,IAAI,UAAU;AACpD,SAAO,KAAK,OAAO;;;AAIvB,MAAa,iBAAiB,UAAgC;CAC5D,MAAM,EAAE,MAAM,SAAS,MAAM,QAAQ;AACrC,QAAO;EAAE,GAAG;EAAM;EAAM"}
|
package/dist/ui/messages.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"messages.js","names":[],"sources":["../../src/ui/messages.ts"],"sourcesContent":["import {\n type BaseMessage,\n BaseMessageChunk,\n RemoveMessage,\n convertToChunk,\n coerceMessageLikeToMessage,\n isBaseMessageChunk,\n HumanMessageChunk,\n SystemMessageChunk,\n AIMessageChunk,\n ToolMessageChunk,\n} from \"@langchain/core/messages\";\n\nimport type { Message } from \"../types.messages.js\";\n\nexport function tryConvertToChunk(\n message: BaseMessage | BaseMessageChunk\n): BaseMessageChunk | null {\n try {\n if (isBaseMessageChunk(message)) return message;\n return convertToChunk(message);\n } catch {\n return null;\n }\n}\n\nexport function tryCoerceMessageLikeToMessage(\n message: Omit<Message, \"type\"> & { type: string }\n): BaseMessage | BaseMessageChunk {\n if (message.type === \"human\" || message.type === \"user\") {\n return new HumanMessageChunk(message);\n }\n\n if (message.type === \"ai\" || message.type === \"assistant\") {\n return new AIMessageChunk(message);\n }\n\n if (message.type === \"system\") {\n return new SystemMessageChunk(message);\n }\n\n if (message.type === \"tool\" && \"tool_call_id\" in message) {\n return new ToolMessageChunk({\n ...message,\n tool_call_id: message.tool_call_id as string,\n });\n }\n\n if (message.type === \"remove\" && message.id != null) {\n return new RemoveMessage({ ...message, id: message.id });\n }\n\n return coerceMessageLikeToMessage(message);\n}\n\nexport class MessageTupleManager {\n chunks: Record<\n string,\n {\n chunk?: BaseMessageChunk | BaseMessage;\n metadata?: Record<string, unknown>;\n index?: number;\n }\n > = {};\n\n constructor() {\n this.chunks = {};\n }\n\n add(\n serialized: Message,\n metadata: Record<string, unknown> | undefined\n ): string | null {\n // TODO: this is sometimes sent from the API\n // figure out how to prevent this or move this to LC.js\n if (serialized.type.endsWith(\"MessageChunk\")) {\n // eslint-disable-next-line no-param-reassign\n serialized.type = serialized.type\n .slice(0, -\"MessageChunk\".length)\n .toLowerCase() as Message[\"type\"];\n }\n\n const message = tryCoerceMessageLikeToMessage(serialized);\n const chunk = tryConvertToChunk(message);\n\n const { id } = chunk ?? message;\n if (!id) {\n console.warn(\n \"No message ID found for chunk, ignoring in state\",\n serialized\n );\n return null;\n }\n\n this.chunks[id] ??= {};\n this.chunks[id].metadata = metadata ?? this.chunks[id].metadata;\n if (chunk) {\n const prev = this.chunks[id].chunk;\n this.chunks[id].chunk =\n (isBaseMessageChunk(prev) ? prev : null)?.concat(chunk) ?? chunk;\n } else {\n this.chunks[id].chunk = message;\n }\n\n return id;\n }\n\n clear() {\n this.chunks = {};\n }\n\n get(id: string | null | undefined, defaultIndex?: number) {\n if (id == null) return null;\n if (this.chunks[id] == null) return null;\n if (defaultIndex != null) this.chunks[id].index ??= defaultIndex;\n return this.chunks[id];\n }\n}\n\nexport const toMessageDict = (chunk: BaseMessage): Message => {\n const { type, data } = chunk.toDict();\n return { ...data, type } as Message;\n};\n"],"mappings":";;;AAeA,SAAgB,kBACd,SACyB;AACzB,KAAI;AACF,MAAI,mBAAmB,
|
|
1
|
+
{"version":3,"file":"messages.js","names":[],"sources":["../../src/ui/messages.ts"],"sourcesContent":["import {\n type BaseMessage,\n BaseMessageChunk,\n RemoveMessage,\n convertToChunk,\n coerceMessageLikeToMessage,\n isBaseMessageChunk,\n HumanMessageChunk,\n SystemMessageChunk,\n AIMessageChunk,\n ToolMessageChunk,\n} from \"@langchain/core/messages\";\n\nimport type { Message } from \"../types.messages.js\";\n\nexport function tryConvertToChunk(\n message: BaseMessage | BaseMessageChunk\n): BaseMessageChunk | null {\n try {\n if (isBaseMessageChunk(message)) return message;\n return convertToChunk(message);\n } catch {\n return null;\n }\n}\n\nexport function tryCoerceMessageLikeToMessage(\n message: Omit<Message, \"type\"> & { type: string }\n): BaseMessage | BaseMessageChunk {\n if (message.type === \"human\" || message.type === \"user\") {\n return new HumanMessageChunk(message);\n }\n\n if (message.type === \"ai\" || message.type === \"assistant\") {\n return new AIMessageChunk(message);\n }\n\n if (message.type === \"system\") {\n return new SystemMessageChunk(message);\n }\n\n if (message.type === \"tool\" && \"tool_call_id\" in message) {\n return new ToolMessageChunk({\n ...message,\n tool_call_id: message.tool_call_id as string,\n });\n }\n\n if (message.type === \"remove\" && message.id != null) {\n return new RemoveMessage({ ...message, id: message.id });\n }\n\n return coerceMessageLikeToMessage(message);\n}\n\nexport class MessageTupleManager {\n chunks: Record<\n string,\n {\n chunk?: BaseMessageChunk | BaseMessage;\n metadata?: Record<string, unknown>;\n index?: number;\n }\n > = {};\n\n constructor() {\n this.chunks = {};\n }\n\n add(\n serialized: Message,\n metadata: Record<string, unknown> | undefined\n ): string | null {\n // TODO: this is sometimes sent from the API\n // figure out how to prevent this or move this to LC.js\n if (serialized.type.endsWith(\"MessageChunk\")) {\n // eslint-disable-next-line no-param-reassign\n serialized.type = serialized.type\n .slice(0, -\"MessageChunk\".length)\n .toLowerCase() as Message[\"type\"];\n }\n\n const message = tryCoerceMessageLikeToMessage(serialized);\n const chunk = tryConvertToChunk(message);\n\n const { id } = chunk ?? message;\n if (!id) {\n console.warn(\n \"No message ID found for chunk, ignoring in state\",\n serialized\n );\n return null;\n }\n\n this.chunks[id] ??= {};\n this.chunks[id].metadata = metadata ?? this.chunks[id].metadata;\n if (chunk) {\n const prev = this.chunks[id].chunk;\n this.chunks[id].chunk =\n (isBaseMessageChunk(prev) ? prev : null)?.concat(chunk) ?? chunk;\n } else {\n this.chunks[id].chunk = message;\n }\n\n return id;\n }\n\n clear() {\n this.chunks = {};\n }\n\n get(id: string | null | undefined, defaultIndex?: number) {\n if (id == null) return null;\n if (this.chunks[id] == null) return null;\n if (defaultIndex != null) this.chunks[id].index ??= defaultIndex;\n return this.chunks[id];\n }\n}\n\nexport const toMessageDict = (chunk: BaseMessage): Message => {\n const { type, data } = chunk.toDict();\n return { ...data, type } as Message;\n};\n"],"mappings":";;;AAeA,SAAgB,kBACd,SACyB;AACzB,KAAI;AACF,MAAI,mBAAmB,QAAQ,CAAE,QAAO;AACxC,SAAO,eAAe,QAAQ;SACxB;AACN,SAAO;;;AAIX,SAAgB,8BACd,SACgC;AAChC,KAAI,QAAQ,SAAS,WAAW,QAAQ,SAAS,OAC/C,QAAO,IAAI,kBAAkB,QAAQ;AAGvC,KAAI,QAAQ,SAAS,QAAQ,QAAQ,SAAS,YAC5C,QAAO,IAAI,eAAe,QAAQ;AAGpC,KAAI,QAAQ,SAAS,SACnB,QAAO,IAAI,mBAAmB,QAAQ;AAGxC,KAAI,QAAQ,SAAS,UAAU,kBAAkB,QAC/C,QAAO,IAAI,iBAAiB;EAC1B,GAAG;EACH,cAAc,QAAQ;EACvB,CAAC;AAGJ,KAAI,QAAQ,SAAS,YAAY,QAAQ,MAAM,KAC7C,QAAO,IAAI,cAAc;EAAE,GAAG;EAAS,IAAI,QAAQ;EAAI,CAAC;AAG1D,QAAO,2BAA2B,QAAQ;;AAG5C,IAAa,sBAAb,MAAiC;CAC/B,SAOI,EAAE;CAEN,cAAc;AACZ,OAAK,SAAS,EAAE;;CAGlB,IACE,YACA,UACe;AAGf,MAAI,WAAW,KAAK,SAAS,eAAe,CAE1C,YAAW,OAAO,WAAW,KAC1B,MAAM,GAAG,IAAuB,CAChC,aAAa;EAGlB,MAAM,UAAU,8BAA8B,WAAW;EACzD,MAAM,QAAQ,kBAAkB,QAAQ;EAExC,MAAM,EAAE,OAAO,SAAS;AACxB,MAAI,CAAC,IAAI;AACP,WAAQ,KACN,oDACA,WACD;AACD,UAAO;;AAGT,OAAK,OAAO,QAAQ,EAAE;AACtB,OAAK,OAAO,IAAI,WAAW,YAAY,KAAK,OAAO,IAAI;AACvD,MAAI,OAAO;GACT,MAAM,OAAO,KAAK,OAAO,IAAI;AAC7B,QAAK,OAAO,IAAI,SACb,mBAAmB,KAAK,GAAG,OAAO,OAAO,OAAO,MAAM,IAAI;QAE7D,MAAK,OAAO,IAAI,QAAQ;AAG1B,SAAO;;CAGT,QAAQ;AACN,OAAK,SAAS,EAAE;;CAGlB,IAAI,IAA+B,cAAuB;AACxD,MAAI,MAAM,KAAM,QAAO;AACvB,MAAI,KAAK,OAAO,OAAO,KAAM,QAAO;AACpC,MAAI,gBAAgB,KAAM,MAAK,OAAO,IAAI,UAAU;AACpD,SAAO,KAAK,OAAO;;;AAIvB,MAAa,iBAAiB,UAAgC;CAC5D,MAAM,EAAE,MAAM,SAAS,MAAM,QAAQ;AACrC,QAAO;EAAE,GAAG;EAAM;EAAM"}
|