@langchain/langgraph 0.2.72 → 0.2.74
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/channels/any_value.cjs +1 -1
- package/dist/channels/any_value.js +1 -1
- package/dist/channels/any_value.js.map +1 -1
- package/dist/channels/base.cjs +4 -4
- package/dist/channels/base.js.map +1 -1
- package/dist/channels/binop.cjs +1 -1
- package/dist/channels/binop.js +1 -1
- package/dist/channels/binop.js.map +1 -1
- package/dist/channels/dynamic_barrier_value.cjs +1 -1
- package/dist/channels/dynamic_barrier_value.js +1 -1
- package/dist/channels/dynamic_barrier_value.js.map +1 -1
- package/dist/channels/ephemeral_value.cjs +1 -1
- package/dist/channels/ephemeral_value.js +1 -1
- package/dist/channels/ephemeral_value.js.map +1 -1
- package/dist/channels/last_value.cjs +1 -1
- package/dist/channels/last_value.js +1 -1
- package/dist/channels/last_value.js.map +1 -1
- package/dist/channels/named_barrier_value.cjs +1 -1
- package/dist/channels/named_barrier_value.js +1 -1
- package/dist/channels/named_barrier_value.js.map +1 -1
- package/dist/channels/topic.cjs +1 -1
- package/dist/channels/topic.js +1 -1
- package/dist/channels/topic.js.map +1 -1
- package/dist/constants.cjs +5 -5
- package/dist/constants.d.ts +2 -2
- package/dist/constants.js.map +1 -1
- package/dist/errors.cjs +5 -5
- package/dist/errors.d.ts +1 -1
- package/dist/errors.js +1 -1
- package/dist/errors.js.map +1 -1
- package/dist/func/index.cjs +3 -3
- package/dist/func/index.js.map +1 -1
- package/dist/func/types.cjs +1 -2
- package/dist/graph/annotation.cjs +2 -2
- package/dist/graph/annotation.js.map +1 -1
- package/dist/graph/graph.cjs +46 -40
- package/dist/graph/graph.d.ts +10 -2
- package/dist/graph/graph.js +46 -40
- package/dist/graph/graph.js.map +1 -1
- package/dist/graph/index.cjs +2 -1
- package/dist/graph/index.d.ts +1 -1
- package/dist/graph/index.js +1 -1
- package/dist/graph/index.js.map +1 -1
- package/dist/graph/message.cjs +43 -5
- package/dist/graph/message.d.ts +5 -0
- package/dist/graph/message.js +40 -3
- package/dist/graph/message.js.map +1 -1
- package/dist/graph/message.test.cjs +196 -0
- package/dist/graph/message.test.d.ts +1 -0
- package/dist/graph/message.test.js +194 -0
- package/dist/graph/message.test.js.map +1 -0
- package/dist/graph/messages_annotation.cjs +51 -1
- package/dist/graph/messages_annotation.d.ts +47 -0
- package/dist/graph/messages_annotation.js +50 -0
- package/dist/graph/messages_annotation.js.map +1 -1
- package/dist/graph/state.cjs +102 -89
- package/dist/graph/state.d.ts +16 -3
- package/dist/graph/state.js +102 -89
- package/dist/graph/state.js.map +1 -1
- package/dist/graph/zod/plugin.js.map +1 -1
- package/dist/graph/zod/schema.cjs +5 -6
- package/dist/graph/zod/schema.js.map +1 -1
- package/dist/graph/zod/state.cjs +6 -7
- package/dist/graph/zod/state.js.map +1 -1
- package/dist/interrupt.cjs +1 -2
- package/dist/interrupt.js.map +1 -1
- package/dist/managed/base.cjs +3 -3
- package/dist/managed/base.js.map +1 -1
- package/dist/managed/shared_value.js.map +1 -1
- package/dist/prebuilt/agentName.cjs +3 -4
- package/dist/prebuilt/agentName.js.map +1 -1
- package/dist/prebuilt/agent_executor.cjs +1 -2
- package/dist/prebuilt/agent_executor.d.ts +1 -1
- package/dist/prebuilt/agent_executor.js.map +1 -1
- package/dist/prebuilt/chat_agent_executor.cjs +1 -2
- package/dist/prebuilt/chat_agent_executor.js.map +1 -1
- package/dist/prebuilt/react_agent_executor.cjs +4 -4
- package/dist/prebuilt/react_agent_executor.d.ts +2 -2
- package/dist/prebuilt/react_agent_executor.js.map +1 -1
- package/dist/prebuilt/tool_executor.js.map +1 -1
- package/dist/prebuilt/tool_node.cjs +2 -2
- package/dist/prebuilt/tool_node.js.map +1 -1
- package/dist/pregel/algo.cjs +8 -7
- package/dist/pregel/algo.js +1 -0
- package/dist/pregel/algo.js.map +1 -1
- package/dist/pregel/call.cjs +3 -4
- package/dist/pregel/call.js.map +1 -1
- package/dist/pregel/debug.cjs +10 -10
- package/dist/pregel/debug.d.ts +3 -3
- package/dist/pregel/debug.js.map +1 -1
- package/dist/pregel/debug.test.cjs +31 -31
- package/dist/pregel/debug.test.js +12 -12
- package/dist/pregel/debug.test.js.map +1 -1
- package/dist/pregel/index.js.map +1 -1
- package/dist/pregel/io.cjs +8 -9
- package/dist/pregel/io.js +2 -2
- package/dist/pregel/io.js.map +1 -1
- package/dist/pregel/io.mapCommand.test.cjs +29 -29
- package/dist/pregel/io.mapCommand.test.js +5 -5
- package/dist/pregel/io.mapCommand.test.js.map +1 -1
- package/dist/pregel/loop.js.map +1 -1
- package/dist/pregel/messages.cjs +15 -13
- package/dist/pregel/messages.d.ts +1 -1
- package/dist/pregel/messages.js +15 -13
- package/dist/pregel/messages.js.map +1 -1
- package/dist/pregel/messages.test.cjs +105 -105
- package/dist/pregel/messages.test.js +31 -31
- package/dist/pregel/messages.test.js.map +1 -1
- package/dist/pregel/read.js.map +1 -1
- package/dist/pregel/read.test.cjs +35 -35
- package/dist/pregel/read.test.js +4 -4
- package/dist/pregel/read.test.js.map +1 -1
- package/dist/pregel/remote.js.map +1 -1
- package/dist/pregel/retry.cjs +10 -10
- package/dist/pregel/retry.js +8 -8
- package/dist/pregel/retry.js.map +1 -1
- package/dist/pregel/runner.cjs +91 -118
- package/dist/pregel/runner.js +92 -119
- package/dist/pregel/runner.js.map +1 -1
- package/dist/pregel/runner.test.cjs +14 -14
- package/dist/pregel/runner.test.js +4 -4
- package/dist/pregel/runner.test.js.map +1 -1
- package/dist/pregel/stream.js.map +1 -1
- package/dist/pregel/types.cjs +2 -2
- package/dist/pregel/types.js.map +1 -1
- package/dist/pregel/utils/config.cjs +40 -22
- package/dist/pregel/utils/config.d.ts +8 -5
- package/dist/pregel/utils/config.js +33 -14
- package/dist/pregel/utils/config.js.map +1 -1
- package/dist/pregel/utils/config.test.cjs +58 -58
- package/dist/pregel/utils/config.test.js +12 -12
- package/dist/pregel/utils/config.test.js.map +1 -1
- package/dist/pregel/utils/index.cjs +12 -11
- package/dist/pregel/utils/index.js +6 -4
- package/dist/pregel/utils/index.js.map +1 -1
- package/dist/pregel/utils/subgraph.cjs +2 -3
- package/dist/pregel/utils/subgraph.js.map +1 -1
- package/dist/pregel/utils/subgraph.test.cjs +18 -18
- package/dist/pregel/utils/subgraph.test.js +1 -1
- package/dist/pregel/utils/subgraph.test.js.map +1 -1
- package/dist/pregel/validate.cjs +3 -3
- package/dist/pregel/validate.js.map +1 -1
- package/dist/pregel/validate.test.cjs +43 -43
- package/dist/pregel/validate.test.js +3 -3
- package/dist/pregel/validate.test.js.map +1 -1
- package/dist/pregel/write.js.map +1 -1
- package/dist/pregel/write.test.cjs +30 -30
- package/dist/pregel/write.test.js +8 -8
- package/dist/pregel/write.test.js.map +1 -1
- package/dist/setup/async_local_storage.cjs +1 -2
- package/dist/utils.cjs +7 -7
- package/dist/utils.js.map +1 -1
- package/dist/web.cjs +3 -1
- package/dist/web.d.ts +2 -2
- package/dist/web.js +2 -2
- package/dist/web.js.map +1 -1
- package/package.json +11 -11
|
@@ -1,27 +1,27 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
const
|
|
3
|
+
const vitest_1 = require("vitest");
|
|
4
4
|
const messages_1 = require("@langchain/core/messages");
|
|
5
5
|
const outputs_1 = require("@langchain/core/outputs");
|
|
6
6
|
const messages_js_1 = require("./messages.cjs");
|
|
7
7
|
const constants_js_1 = require("../constants.cjs");
|
|
8
|
-
(0,
|
|
9
|
-
(0,
|
|
10
|
-
(0,
|
|
11
|
-
const streamFn =
|
|
8
|
+
(0, vitest_1.describe)("StreamMessagesHandler", () => {
|
|
9
|
+
(0, vitest_1.describe)("constructor", () => {
|
|
10
|
+
(0, vitest_1.it)("should properly initialize the handler", () => {
|
|
11
|
+
const streamFn = vitest_1.vi.fn();
|
|
12
12
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
13
|
-
(0,
|
|
14
|
-
(0,
|
|
15
|
-
(0,
|
|
16
|
-
(0,
|
|
17
|
-
(0,
|
|
18
|
-
(0,
|
|
19
|
-
(0,
|
|
13
|
+
(0, vitest_1.expect)(handler.name).toBe("StreamMessagesHandler");
|
|
14
|
+
(0, vitest_1.expect)(handler.streamFn).toBe(streamFn);
|
|
15
|
+
(0, vitest_1.expect)(handler.metadatas).toEqual({});
|
|
16
|
+
(0, vitest_1.expect)(handler.seen).toEqual({});
|
|
17
|
+
(0, vitest_1.expect)(handler.emittedChatModelRunIds).toEqual({});
|
|
18
|
+
(0, vitest_1.expect)(handler.stableMessageIdMap).toEqual({});
|
|
19
|
+
(0, vitest_1.expect)(handler.lc_prefer_streaming).toBe(true);
|
|
20
20
|
});
|
|
21
21
|
});
|
|
22
|
-
(0,
|
|
23
|
-
(0,
|
|
24
|
-
const streamFn =
|
|
22
|
+
(0, vitest_1.describe)("_emit", () => {
|
|
23
|
+
(0, vitest_1.it)("should emit a message with metadata", () => {
|
|
24
|
+
const streamFn = vitest_1.vi.fn();
|
|
25
25
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
26
26
|
const meta = [
|
|
27
27
|
["ns1", "ns2"],
|
|
@@ -30,7 +30,7 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
30
30
|
const message = new messages_1.AIMessage({ content: "Hello world" });
|
|
31
31
|
const runId = "run-123";
|
|
32
32
|
handler._emit(meta, message, runId);
|
|
33
|
-
(0,
|
|
33
|
+
(0, vitest_1.expect)(streamFn).toHaveBeenCalledWith([
|
|
34
34
|
["ns1", "ns2"],
|
|
35
35
|
"messages",
|
|
36
36
|
[message, { name: "test", tags: [] }],
|
|
@@ -38,10 +38,10 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
38
38
|
// Should store the message in seen if it has an ID
|
|
39
39
|
message.id = "msg-123";
|
|
40
40
|
handler._emit(meta, message, runId);
|
|
41
|
-
(0,
|
|
41
|
+
(0, vitest_1.expect)(handler.seen["msg-123"]).toBe(message);
|
|
42
42
|
});
|
|
43
|
-
(0,
|
|
44
|
-
const streamFn =
|
|
43
|
+
(0, vitest_1.it)("should deduplicate messages when dedupe=true and message has been seen", () => {
|
|
44
|
+
const streamFn = vitest_1.vi.fn();
|
|
45
45
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
46
46
|
const meta = [
|
|
47
47
|
["ns1"],
|
|
@@ -51,14 +51,14 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
51
51
|
const runId = "run-123";
|
|
52
52
|
// First emit should work
|
|
53
53
|
handler._emit(meta, message, runId);
|
|
54
|
-
(0,
|
|
54
|
+
(0, vitest_1.expect)(streamFn).toHaveBeenCalledTimes(1);
|
|
55
55
|
// Second emit with same ID and dedupe=true should be ignored
|
|
56
56
|
streamFn.mockClear();
|
|
57
57
|
handler._emit(meta, message, runId, true);
|
|
58
|
-
(0,
|
|
58
|
+
(0, vitest_1.expect)(streamFn).not.toHaveBeenCalled();
|
|
59
59
|
});
|
|
60
|
-
(0,
|
|
61
|
-
const streamFn =
|
|
60
|
+
(0, vitest_1.it)("should assign proper ID to tool messages", () => {
|
|
61
|
+
const streamFn = vitest_1.vi.fn();
|
|
62
62
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
63
63
|
const meta = [
|
|
64
64
|
["ns1"],
|
|
@@ -71,11 +71,11 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
71
71
|
const runId = "run-456";
|
|
72
72
|
handler._emit(meta, toolMessage, runId);
|
|
73
73
|
// Should assign an ID based on the tool call ID
|
|
74
|
-
(0,
|
|
75
|
-
(0,
|
|
74
|
+
(0, vitest_1.expect)(toolMessage.id).toBe(`run-${runId}-tool-tc-123`);
|
|
75
|
+
(0, vitest_1.expect)(streamFn).toHaveBeenCalled();
|
|
76
76
|
});
|
|
77
|
-
(0,
|
|
78
|
-
const streamFn =
|
|
77
|
+
(0, vitest_1.it)("should maintain stable message IDs for the same run", () => {
|
|
78
|
+
const streamFn = vitest_1.vi.fn();
|
|
79
79
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
80
80
|
const meta = [
|
|
81
81
|
["ns1"],
|
|
@@ -89,13 +89,13 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
89
89
|
// Second message with no ID should get the same stable ID
|
|
90
90
|
const message2 = new messages_1.AIMessage({ content: "Second chunk" });
|
|
91
91
|
handler._emit(meta, message2, runId);
|
|
92
|
-
(0,
|
|
93
|
-
(0,
|
|
92
|
+
(0, vitest_1.expect)(message2.id).toBe(stableId);
|
|
93
|
+
(0, vitest_1.expect)(handler.stableMessageIdMap[runId]).toBe(stableId);
|
|
94
94
|
});
|
|
95
95
|
});
|
|
96
|
-
(0,
|
|
97
|
-
(0,
|
|
98
|
-
const handler = new messages_js_1.StreamMessagesHandler(
|
|
96
|
+
(0, vitest_1.describe)("handleChatModelStart", () => {
|
|
97
|
+
(0, vitest_1.it)("should store metadata when provided", () => {
|
|
98
|
+
const handler = new messages_js_1.StreamMessagesHandler(vitest_1.vi.fn());
|
|
99
99
|
const runId = "run-123";
|
|
100
100
|
const metadata = {
|
|
101
101
|
langgraph_checkpoint_ns: "ns1|ns2",
|
|
@@ -109,13 +109,13 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
109
109
|
metadata, // metadata
|
|
110
110
|
"ModelName" // name
|
|
111
111
|
);
|
|
112
|
-
(0,
|
|
112
|
+
(0, vitest_1.expect)(handler.metadatas[runId]).toEqual([
|
|
113
113
|
["ns1", "ns2"],
|
|
114
114
|
{ tags: [], name: "ModelName", ...metadata },
|
|
115
115
|
]);
|
|
116
116
|
});
|
|
117
|
-
(0,
|
|
118
|
-
const handler = new messages_js_1.StreamMessagesHandler(
|
|
117
|
+
(0, vitest_1.it)("should not store metadata when TAG_NOSTREAM is present", () => {
|
|
118
|
+
const handler = new messages_js_1.StreamMessagesHandler(vitest_1.vi.fn());
|
|
119
119
|
const runId = "run-123";
|
|
120
120
|
const metadata = {
|
|
121
121
|
langgraph_checkpoint_ns: "ns1|ns2",
|
|
@@ -123,32 +123,32 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
123
123
|
handler.handleChatModelStart({}, [], runId, undefined, {}, [constants_js_1.TAG_NOSTREAM], // nostream tag
|
|
124
124
|
metadata, "ModelName");
|
|
125
125
|
// Should not store metadata due to TAG_NOSTREAM
|
|
126
|
-
(0,
|
|
126
|
+
(0, vitest_1.expect)(handler.metadatas[runId]).toBeUndefined();
|
|
127
127
|
});
|
|
128
128
|
});
|
|
129
|
-
(0,
|
|
130
|
-
(0,
|
|
131
|
-
const streamFn =
|
|
129
|
+
(0, vitest_1.describe)("handleLLMNewToken", () => {
|
|
130
|
+
(0, vitest_1.it)("should emit message chunk when metadata exists", () => {
|
|
131
|
+
const streamFn = vitest_1.vi.fn();
|
|
132
132
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
133
133
|
const runId = "run-123";
|
|
134
134
|
handler.metadatas[runId] = [["ns1", "ns2"], { name: "test" }];
|
|
135
135
|
// Spy on _emit
|
|
136
|
-
const emitSpy =
|
|
136
|
+
const emitSpy = vitest_1.vi.spyOn(handler, "_emit");
|
|
137
137
|
handler.handleLLMNewToken("token", { prompt: 0, completion: 0 }, // idx
|
|
138
138
|
runId);
|
|
139
139
|
// Should mark run as emitted
|
|
140
|
-
(0,
|
|
140
|
+
(0, vitest_1.expect)(handler.emittedChatModelRunIds[runId]).toBe(true);
|
|
141
141
|
// Should emit AIMessageChunk when no chunk is provided
|
|
142
|
-
(0,
|
|
143
|
-
(0,
|
|
142
|
+
(0, vitest_1.expect)(emitSpy).toHaveBeenCalledWith(handler.metadatas[runId], vitest_1.expect.any(messages_1.AIMessageChunk), runId);
|
|
143
|
+
(0, vitest_1.expect)(emitSpy.mock.calls[0][1].content).toBe("token");
|
|
144
144
|
});
|
|
145
|
-
(0,
|
|
146
|
-
const streamFn =
|
|
145
|
+
(0, vitest_1.it)("should emit provided chunk when available", () => {
|
|
146
|
+
const streamFn = vitest_1.vi.fn();
|
|
147
147
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
148
148
|
const runId = "run-123";
|
|
149
149
|
handler.metadatas[runId] = [["ns1"], { name: "test" }];
|
|
150
150
|
// Spy on _emit
|
|
151
|
-
const emitSpy =
|
|
151
|
+
const emitSpy = vitest_1.vi.spyOn(handler, "_emit");
|
|
152
152
|
// Create a chunk
|
|
153
153
|
const chunk = new outputs_1.ChatGenerationChunk({
|
|
154
154
|
message: new messages_1.AIMessageChunk({ content: "chunk content" }),
|
|
@@ -157,49 +157,49 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
157
157
|
handler.handleLLMNewToken("token", { prompt: 0, completion: 0 }, runId, undefined, undefined, { chunk } // provide the chunk
|
|
158
158
|
);
|
|
159
159
|
// Should emit the chunk's message
|
|
160
|
-
(0,
|
|
160
|
+
(0, vitest_1.expect)(emitSpy).toHaveBeenCalledWith(handler.metadatas[runId], chunk.message, runId);
|
|
161
161
|
});
|
|
162
|
-
(0,
|
|
163
|
-
const streamFn =
|
|
162
|
+
(0, vitest_1.it)("should not emit when metadata is missing", () => {
|
|
163
|
+
const streamFn = vitest_1.vi.fn();
|
|
164
164
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
165
165
|
const runId = "run-123";
|
|
166
166
|
// No metadata for this runId
|
|
167
167
|
// Spy on _emit
|
|
168
|
-
const emitSpy =
|
|
168
|
+
const emitSpy = vitest_1.vi.spyOn(handler, "_emit");
|
|
169
169
|
handler.handleLLMNewToken("token", { prompt: 0, completion: 0 }, runId);
|
|
170
170
|
// Should mark run as emitted
|
|
171
|
-
(0,
|
|
171
|
+
(0, vitest_1.expect)(handler.emittedChatModelRunIds[runId]).toBe(true);
|
|
172
172
|
// But should not call _emit
|
|
173
|
-
(0,
|
|
173
|
+
(0, vitest_1.expect)(emitSpy).not.toHaveBeenCalled();
|
|
174
174
|
});
|
|
175
175
|
});
|
|
176
|
-
(0,
|
|
177
|
-
(0,
|
|
178
|
-
const streamFn =
|
|
176
|
+
(0, vitest_1.describe)("handleLLMEnd", () => {
|
|
177
|
+
(0, vitest_1.it)("should emit message from non-streaming run", () => {
|
|
178
|
+
const streamFn = vitest_1.vi.fn();
|
|
179
179
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
180
180
|
const runId = "run-123";
|
|
181
181
|
handler.metadatas[runId] = [["ns1"], { name: "test" }];
|
|
182
182
|
// Not marked as emitted yet
|
|
183
183
|
// Mock _emit directly instead of spying
|
|
184
|
-
handler._emit =
|
|
184
|
+
handler._emit = vitest_1.vi.fn();
|
|
185
185
|
const message = new messages_1.AIMessage({ content: "final result" });
|
|
186
186
|
handler.handleLLMEnd({
|
|
187
187
|
generations: [[{ text: "test output", message }]],
|
|
188
188
|
}, runId);
|
|
189
189
|
// Should emit the message with dedupe=true
|
|
190
|
-
(0,
|
|
190
|
+
(0, vitest_1.expect)(handler._emit).toHaveBeenCalledWith(vitest_1.expect.anything(), vitest_1.expect.objectContaining({ content: "final result" }), runId, true);
|
|
191
191
|
// Should clean up
|
|
192
|
-
(0,
|
|
192
|
+
(0, vitest_1.expect)(handler.metadatas[runId]).toBeUndefined();
|
|
193
193
|
});
|
|
194
|
-
(0,
|
|
195
|
-
const streamFn =
|
|
194
|
+
(0, vitest_1.it)("should not emit for streaming runs that already emitted", () => {
|
|
195
|
+
const streamFn = vitest_1.vi.fn();
|
|
196
196
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
197
197
|
const runId = "run-123";
|
|
198
198
|
handler.metadatas[runId] = [["ns1"], { name: "test" }];
|
|
199
199
|
// Mark as already emitted
|
|
200
200
|
handler.emittedChatModelRunIds[runId] = true;
|
|
201
201
|
// Mock _emit directly
|
|
202
|
-
handler._emit =
|
|
202
|
+
handler._emit = vitest_1.vi.fn();
|
|
203
203
|
handler.handleLLMEnd({
|
|
204
204
|
generations: [
|
|
205
205
|
[
|
|
@@ -211,24 +211,24 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
211
211
|
],
|
|
212
212
|
}, runId);
|
|
213
213
|
// Should not emit anything
|
|
214
|
-
(0,
|
|
214
|
+
(0, vitest_1.expect)(handler._emit).not.toHaveBeenCalled();
|
|
215
215
|
// Should clean up metadata
|
|
216
|
-
(0,
|
|
216
|
+
(0, vitest_1.expect)(handler.metadatas[runId]).toBeUndefined();
|
|
217
217
|
});
|
|
218
218
|
});
|
|
219
|
-
(0,
|
|
220
|
-
(0,
|
|
221
|
-
const handler = new messages_js_1.StreamMessagesHandler(
|
|
219
|
+
(0, vitest_1.describe)("handleLLMError", () => {
|
|
220
|
+
(0, vitest_1.it)("should clean up metadata on error", () => {
|
|
221
|
+
const handler = new messages_js_1.StreamMessagesHandler(vitest_1.vi.fn());
|
|
222
222
|
const runId = "run-123";
|
|
223
223
|
handler.metadatas[runId] = [["ns1"], { name: "test" }];
|
|
224
224
|
handler.handleLLMError(new Error("Test error"), runId);
|
|
225
225
|
// Should clean up metadata
|
|
226
|
-
(0,
|
|
226
|
+
(0, vitest_1.expect)(handler.metadatas[runId]).toBeUndefined();
|
|
227
227
|
});
|
|
228
228
|
});
|
|
229
|
-
(0,
|
|
230
|
-
(0,
|
|
231
|
-
const handler = new messages_js_1.StreamMessagesHandler(
|
|
229
|
+
(0, vitest_1.describe)("handleChainStart", () => {
|
|
230
|
+
(0, vitest_1.it)("should store metadata for matching node name", () => {
|
|
231
|
+
const handler = new messages_js_1.StreamMessagesHandler(vitest_1.vi.fn());
|
|
232
232
|
const runId = "chain-123";
|
|
233
233
|
const metadata = {
|
|
234
234
|
langgraph_checkpoint_ns: "ns1|ns2",
|
|
@@ -236,13 +236,13 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
236
236
|
};
|
|
237
237
|
handler.handleChainStart({}, {}, runId, undefined, [], metadata, undefined, "NodeName" // Name matches langgraph_node
|
|
238
238
|
);
|
|
239
|
-
(0,
|
|
239
|
+
(0, vitest_1.expect)(handler.metadatas[runId]).toEqual([
|
|
240
240
|
["ns1", "ns2"],
|
|
241
241
|
{ tags: [], name: "NodeName", ...metadata },
|
|
242
242
|
]);
|
|
243
243
|
});
|
|
244
|
-
(0,
|
|
245
|
-
const handler = new messages_js_1.StreamMessagesHandler(
|
|
244
|
+
(0, vitest_1.it)("should not store metadata when node name doesn't match", () => {
|
|
245
|
+
const handler = new messages_js_1.StreamMessagesHandler(vitest_1.vi.fn());
|
|
246
246
|
const runId = "chain-123";
|
|
247
247
|
const metadata = {
|
|
248
248
|
langgraph_checkpoint_ns: "ns1|ns2",
|
|
@@ -250,10 +250,10 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
250
250
|
};
|
|
251
251
|
handler.handleChainStart({}, {}, runId, undefined, [], metadata, undefined, "DifferentName" // Different from langgraph_node
|
|
252
252
|
);
|
|
253
|
-
(0,
|
|
253
|
+
(0, vitest_1.expect)(handler.metadatas[runId]).toBeUndefined();
|
|
254
254
|
});
|
|
255
|
-
(0,
|
|
256
|
-
const handler = new messages_js_1.StreamMessagesHandler(
|
|
255
|
+
(0, vitest_1.it)("should not store metadata when TAG_HIDDEN is present", () => {
|
|
256
|
+
const handler = new messages_js_1.StreamMessagesHandler(vitest_1.vi.fn());
|
|
257
257
|
const runId = "chain-123";
|
|
258
258
|
const metadata = {
|
|
259
259
|
langgraph_checkpoint_ns: "ns1|ns2",
|
|
@@ -261,52 +261,52 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
261
261
|
};
|
|
262
262
|
handler.handleChainStart({}, {}, runId, undefined, [constants_js_1.TAG_HIDDEN], // Hidden tag
|
|
263
263
|
metadata, undefined, "NodeName");
|
|
264
|
-
(0,
|
|
264
|
+
(0, vitest_1.expect)(handler.metadatas[runId]).toBeUndefined();
|
|
265
265
|
});
|
|
266
266
|
});
|
|
267
|
-
(0,
|
|
268
|
-
(0,
|
|
269
|
-
const streamFn =
|
|
267
|
+
(0, vitest_1.describe)("handleChainEnd", () => {
|
|
268
|
+
(0, vitest_1.it)("should emit a single message output", () => {
|
|
269
|
+
const streamFn = vitest_1.vi.fn();
|
|
270
270
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
271
271
|
const runId = "chain-123";
|
|
272
272
|
handler.metadatas[runId] = [["ns1"], { name: "test" }];
|
|
273
273
|
// Mock _emit directly
|
|
274
|
-
handler._emit =
|
|
274
|
+
handler._emit = vitest_1.vi.fn();
|
|
275
275
|
const message = new messages_1.AIMessage({ content: "chain result" });
|
|
276
276
|
handler.handleChainEnd(message, runId);
|
|
277
277
|
// Should emit the message with dedupe=true
|
|
278
|
-
(0,
|
|
278
|
+
(0, vitest_1.expect)(handler._emit).toHaveBeenCalledWith(vitest_1.expect.anything(), vitest_1.expect.objectContaining({ content: "chain result" }), runId, true);
|
|
279
279
|
// Should clean up
|
|
280
|
-
(0,
|
|
280
|
+
(0, vitest_1.expect)(handler.metadatas[runId]).toBeUndefined();
|
|
281
281
|
});
|
|
282
|
-
(0,
|
|
283
|
-
const streamFn =
|
|
282
|
+
(0, vitest_1.it)("should emit messages from an array output", () => {
|
|
283
|
+
const streamFn = vitest_1.vi.fn();
|
|
284
284
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
285
285
|
const runId = "chain-123";
|
|
286
286
|
handler.metadatas[runId] = [["ns1"], { name: "test" }];
|
|
287
287
|
// Mock _emit directly
|
|
288
|
-
handler._emit =
|
|
288
|
+
handler._emit = vitest_1.vi.fn();
|
|
289
289
|
const message1 = new messages_1.AIMessage({ content: "result 1" });
|
|
290
290
|
const message2 = new messages_1.AIMessage({ content: "result 2" });
|
|
291
291
|
const notAMessage = "not a message";
|
|
292
292
|
handler.handleChainEnd([message1, message2, notAMessage], runId);
|
|
293
293
|
// Should emit both messages
|
|
294
|
-
(0,
|
|
294
|
+
(0, vitest_1.expect)(handler._emit).toHaveBeenCalledTimes(2);
|
|
295
295
|
// Verify calls in a way that's less brittle
|
|
296
296
|
const callArgs = handler._emit.mock.calls;
|
|
297
297
|
const emittedContents = callArgs.map((args) => args[1].content);
|
|
298
|
-
(0,
|
|
299
|
-
(0,
|
|
298
|
+
(0, vitest_1.expect)(emittedContents).toContain("result 1");
|
|
299
|
+
(0, vitest_1.expect)(emittedContents).toContain("result 2");
|
|
300
300
|
// Should clean up
|
|
301
|
-
(0,
|
|
301
|
+
(0, vitest_1.expect)(handler.metadatas[runId]).toBeUndefined();
|
|
302
302
|
});
|
|
303
|
-
(0,
|
|
304
|
-
const streamFn =
|
|
303
|
+
(0, vitest_1.it)("should emit messages from object output properties", () => {
|
|
304
|
+
const streamFn = vitest_1.vi.fn();
|
|
305
305
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
306
306
|
const runId = "chain-123";
|
|
307
307
|
handler.metadatas[runId] = [["ns1"], { name: "test" }];
|
|
308
308
|
// Mock _emit directly
|
|
309
|
-
handler._emit =
|
|
309
|
+
handler._emit = vitest_1.vi.fn();
|
|
310
310
|
const message = new messages_1.AIMessage({ content: "direct result" });
|
|
311
311
|
const arrayMessage = new messages_1.AIMessage({ content: "array result" });
|
|
312
312
|
handler.handleChainEnd({
|
|
@@ -315,36 +315,36 @@ const constants_js_1 = require("../constants.cjs");
|
|
|
315
315
|
otherProp: "something else",
|
|
316
316
|
}, runId);
|
|
317
317
|
// Should emit both messages
|
|
318
|
-
(0,
|
|
318
|
+
(0, vitest_1.expect)(handler._emit).toHaveBeenCalledTimes(2);
|
|
319
319
|
// Verify calls in a way that's less brittle
|
|
320
320
|
const callArgs = handler._emit.mock.calls;
|
|
321
321
|
const emittedContents = callArgs.map((args) => args[1].content);
|
|
322
|
-
(0,
|
|
323
|
-
(0,
|
|
322
|
+
(0, vitest_1.expect)(emittedContents).toContain("direct result");
|
|
323
|
+
(0, vitest_1.expect)(emittedContents).toContain("array result");
|
|
324
324
|
// Should clean up
|
|
325
|
-
(0,
|
|
325
|
+
(0, vitest_1.expect)(handler.metadatas[runId]).toBeUndefined();
|
|
326
326
|
});
|
|
327
|
-
(0,
|
|
328
|
-
const streamFn =
|
|
327
|
+
(0, vitest_1.it)("should do nothing when metadata is missing", () => {
|
|
328
|
+
const streamFn = vitest_1.vi.fn();
|
|
329
329
|
const handler = new messages_js_1.StreamMessagesHandler(streamFn);
|
|
330
330
|
const runId = "chain-123";
|
|
331
331
|
// No metadata for this runId
|
|
332
332
|
// Spy on _emit
|
|
333
|
-
const emitSpy =
|
|
333
|
+
const emitSpy = vitest_1.vi.spyOn(handler, "_emit");
|
|
334
334
|
const message = new messages_1.AIMessage({ content: "result" });
|
|
335
335
|
handler.handleChainEnd(message, runId);
|
|
336
336
|
// Should not emit anything
|
|
337
|
-
(0,
|
|
337
|
+
(0, vitest_1.expect)(emitSpy).not.toHaveBeenCalled();
|
|
338
338
|
});
|
|
339
339
|
});
|
|
340
|
-
(0,
|
|
341
|
-
(0,
|
|
342
|
-
const handler = new messages_js_1.StreamMessagesHandler(
|
|
340
|
+
(0, vitest_1.describe)("handleChainError", () => {
|
|
341
|
+
(0, vitest_1.it)("should clean up metadata on error", () => {
|
|
342
|
+
const handler = new messages_js_1.StreamMessagesHandler(vitest_1.vi.fn());
|
|
343
343
|
const runId = "chain-123";
|
|
344
344
|
handler.metadatas[runId] = [["ns1"], { name: "test" }];
|
|
345
345
|
handler.handleChainError(new Error("Test error"), runId);
|
|
346
346
|
// Should clean up metadata
|
|
347
|
-
(0,
|
|
347
|
+
(0, vitest_1.expect)(handler.metadatas[runId]).toBeUndefined();
|
|
348
348
|
});
|
|
349
349
|
});
|
|
350
350
|
});
|