@langchain/langgraph 0.0.28 → 0.0.30
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/graph/index.cjs +2 -1
- package/dist/graph/index.d.ts +1 -1
- package/dist/graph/index.js +1 -1
- package/dist/graph/message.cjs +42 -4
- package/dist/graph/message.d.ts +3 -2
- package/dist/graph/message.js +40 -3
- package/dist/prebuilt/tool_node.cjs +32 -11
- package/dist/prebuilt/tool_node.d.ts +7 -1
- package/dist/prebuilt/tool_node.js +32 -11
- package/dist/tests/prebuilt.test.js +80 -69
- package/dist/tests/pregel.test.js +3 -3
- package/dist/utils.cjs +1 -1
- package/dist/utils.js +1 -1
- package/dist/web.cjs +2 -1
- package/dist/web.d.ts +1 -1
- package/dist/web.js +1 -1
- package/package.json +6 -6
package/dist/graph/index.cjs
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.MessageGraph = exports.StateGraph = exports.Graph = exports.START = exports.END = void 0;
|
|
3
|
+
exports.messagesStateReducer = exports.MessageGraph = exports.StateGraph = exports.Graph = exports.START = exports.END = void 0;
|
|
4
4
|
var graph_js_1 = require("./graph.cjs");
|
|
5
5
|
Object.defineProperty(exports, "END", { enumerable: true, get: function () { return graph_js_1.END; } });
|
|
6
6
|
Object.defineProperty(exports, "START", { enumerable: true, get: function () { return graph_js_1.START; } });
|
|
@@ -9,3 +9,4 @@ var state_js_1 = require("./state.cjs");
|
|
|
9
9
|
Object.defineProperty(exports, "StateGraph", { enumerable: true, get: function () { return state_js_1.StateGraph; } });
|
|
10
10
|
var message_js_1 = require("./message.cjs");
|
|
11
11
|
Object.defineProperty(exports, "MessageGraph", { enumerable: true, get: function () { return message_js_1.MessageGraph; } });
|
|
12
|
+
Object.defineProperty(exports, "messagesStateReducer", { enumerable: true, get: function () { return message_js_1.messagesStateReducer; } });
|
package/dist/graph/index.d.ts
CHANGED
package/dist/graph/index.js
CHANGED
package/dist/graph/message.cjs
CHANGED
|
@@ -1,18 +1,56 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.MessageGraph = void 0;
|
|
3
|
+
exports.MessageGraph = exports.messagesStateReducer = void 0;
|
|
4
|
+
const messages_1 = require("@langchain/core/messages");
|
|
5
|
+
const uuid_1 = require("uuid");
|
|
4
6
|
const state_js_1 = require("./state.cjs");
|
|
5
|
-
function
|
|
7
|
+
function messagesStateReducer(left, right) {
|
|
6
8
|
const leftArray = Array.isArray(left) ? left : [left];
|
|
7
9
|
const rightArray = Array.isArray(right) ? right : [right];
|
|
8
|
-
|
|
10
|
+
// coerce to message
|
|
11
|
+
const leftMessages = leftArray.map(messages_1.coerceMessageLikeToMessage);
|
|
12
|
+
const rightMessages = rightArray.map(messages_1.coerceMessageLikeToMessage);
|
|
13
|
+
// assign missing ids
|
|
14
|
+
for (const m of leftMessages) {
|
|
15
|
+
if (m.id === null || m.id === undefined) {
|
|
16
|
+
m.id = (0, uuid_1.v4)();
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
for (const m of rightMessages) {
|
|
20
|
+
if (m.id === null || m.id === undefined) {
|
|
21
|
+
m.id = (0, uuid_1.v4)();
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
// merge
|
|
25
|
+
const leftIdxById = new Map(leftMessages.map((m, i) => [m.id, i]));
|
|
26
|
+
const merged = [...leftMessages];
|
|
27
|
+
const idsToRemove = new Set();
|
|
28
|
+
for (const m of rightMessages) {
|
|
29
|
+
const existingIdx = leftIdxById.get(m.id);
|
|
30
|
+
if (existingIdx !== undefined) {
|
|
31
|
+
if (m._getType() === "remove") {
|
|
32
|
+
idsToRemove.add(m.id);
|
|
33
|
+
}
|
|
34
|
+
else {
|
|
35
|
+
merged[existingIdx] = m;
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
else {
|
|
39
|
+
if (m._getType() === "remove") {
|
|
40
|
+
throw new Error(`Attempting to delete a message with an ID that doesn't exist ('${m.id}')`);
|
|
41
|
+
}
|
|
42
|
+
merged.push(m);
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
return merged.filter((m) => !idsToRemove.has(m.id));
|
|
9
46
|
}
|
|
47
|
+
exports.messagesStateReducer = messagesStateReducer;
|
|
10
48
|
class MessageGraph extends state_js_1.StateGraph {
|
|
11
49
|
constructor() {
|
|
12
50
|
super({
|
|
13
51
|
channels: {
|
|
14
52
|
__root__: {
|
|
15
|
-
reducer:
|
|
53
|
+
reducer: messagesStateReducer,
|
|
16
54
|
default: () => [],
|
|
17
55
|
},
|
|
18
56
|
},
|
package/dist/graph/message.d.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
|
-
import { BaseMessage } from "@langchain/core/messages";
|
|
1
|
+
import { BaseMessage, BaseMessageLike } from "@langchain/core/messages";
|
|
2
2
|
import { StateGraph } from "./state.js";
|
|
3
|
-
type Messages = Array<BaseMessage> | BaseMessage;
|
|
3
|
+
type Messages = Array<BaseMessage | BaseMessageLike> | BaseMessage | BaseMessageLike;
|
|
4
|
+
export declare function messagesStateReducer(left: Messages, right: Messages): BaseMessage[];
|
|
4
5
|
export declare class MessageGraph extends StateGraph<BaseMessage[], Messages> {
|
|
5
6
|
constructor();
|
|
6
7
|
}
|
package/dist/graph/message.js
CHANGED
|
@@ -1,15 +1,52 @@
|
|
|
1
|
+
import { coerceMessageLikeToMessage, } from "@langchain/core/messages";
|
|
2
|
+
import { v4 } from "uuid";
|
|
1
3
|
import { StateGraph } from "./state.js";
|
|
2
|
-
function
|
|
4
|
+
export function messagesStateReducer(left, right) {
|
|
3
5
|
const leftArray = Array.isArray(left) ? left : [left];
|
|
4
6
|
const rightArray = Array.isArray(right) ? right : [right];
|
|
5
|
-
|
|
7
|
+
// coerce to message
|
|
8
|
+
const leftMessages = leftArray.map(coerceMessageLikeToMessage);
|
|
9
|
+
const rightMessages = rightArray.map(coerceMessageLikeToMessage);
|
|
10
|
+
// assign missing ids
|
|
11
|
+
for (const m of leftMessages) {
|
|
12
|
+
if (m.id === null || m.id === undefined) {
|
|
13
|
+
m.id = v4();
|
|
14
|
+
}
|
|
15
|
+
}
|
|
16
|
+
for (const m of rightMessages) {
|
|
17
|
+
if (m.id === null || m.id === undefined) {
|
|
18
|
+
m.id = v4();
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
// merge
|
|
22
|
+
const leftIdxById = new Map(leftMessages.map((m, i) => [m.id, i]));
|
|
23
|
+
const merged = [...leftMessages];
|
|
24
|
+
const idsToRemove = new Set();
|
|
25
|
+
for (const m of rightMessages) {
|
|
26
|
+
const existingIdx = leftIdxById.get(m.id);
|
|
27
|
+
if (existingIdx !== undefined) {
|
|
28
|
+
if (m._getType() === "remove") {
|
|
29
|
+
idsToRemove.add(m.id);
|
|
30
|
+
}
|
|
31
|
+
else {
|
|
32
|
+
merged[existingIdx] = m;
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
else {
|
|
36
|
+
if (m._getType() === "remove") {
|
|
37
|
+
throw new Error(`Attempting to delete a message with an ID that doesn't exist ('${m.id}')`);
|
|
38
|
+
}
|
|
39
|
+
merged.push(m);
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
return merged.filter((m) => !idsToRemove.has(m.id));
|
|
6
43
|
}
|
|
7
44
|
export class MessageGraph extends StateGraph {
|
|
8
45
|
constructor() {
|
|
9
46
|
super({
|
|
10
47
|
channels: {
|
|
11
48
|
__root__: {
|
|
12
|
-
reducer:
|
|
49
|
+
reducer: messagesStateReducer,
|
|
13
50
|
default: () => [],
|
|
14
51
|
},
|
|
15
52
|
},
|
|
@@ -5,7 +5,8 @@ const messages_1 = require("@langchain/core/messages");
|
|
|
5
5
|
const utils_js_1 = require("../utils.cjs");
|
|
6
6
|
const graph_js_1 = require("../graph/graph.cjs");
|
|
7
7
|
class ToolNode extends utils_js_1.RunnableCallable {
|
|
8
|
-
constructor(tools,
|
|
8
|
+
constructor(tools, options) {
|
|
9
|
+
const { name, tags, handleToolErrors } = options ?? {};
|
|
9
10
|
super({ name, tags, func: (input, config) => this.run(input, config) });
|
|
10
11
|
/**
|
|
11
12
|
A node that runs the tools requested in the last AIMessage. It can be used
|
|
@@ -19,7 +20,14 @@ class ToolNode extends utils_js_1.RunnableCallable {
|
|
|
19
20
|
writable: true,
|
|
20
21
|
value: void 0
|
|
21
22
|
});
|
|
23
|
+
Object.defineProperty(this, "handleToolErrors", {
|
|
24
|
+
enumerable: true,
|
|
25
|
+
configurable: true,
|
|
26
|
+
writable: true,
|
|
27
|
+
value: true
|
|
28
|
+
});
|
|
22
29
|
this.tools = tools;
|
|
30
|
+
this.handleToolErrors = handleToolErrors ?? this.handleToolErrors;
|
|
23
31
|
}
|
|
24
32
|
async run(input, config) {
|
|
25
33
|
const message = Array.isArray(input)
|
|
@@ -30,18 +38,31 @@ class ToolNode extends utils_js_1.RunnableCallable {
|
|
|
30
38
|
}
|
|
31
39
|
const outputs = await Promise.all(message.tool_calls?.map(async (call) => {
|
|
32
40
|
const tool = this.tools.find((tool) => tool.name === call.name);
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
41
|
+
try {
|
|
42
|
+
if (tool === undefined) {
|
|
43
|
+
throw new Error(`Tool "${call.name}" not found.`);
|
|
44
|
+
}
|
|
45
|
+
const output = await tool.invoke({ ...call, type: "tool_call" }, config);
|
|
46
|
+
if ((0, messages_1.isBaseMessage)(output) && output._getType() === "tool") {
|
|
47
|
+
return output;
|
|
48
|
+
}
|
|
49
|
+
else {
|
|
50
|
+
return new messages_1.ToolMessage({
|
|
51
|
+
name: tool.name,
|
|
52
|
+
content: typeof output === "string" ? output : JSON.stringify(output),
|
|
53
|
+
tool_call_id: call.id,
|
|
54
|
+
});
|
|
55
|
+
}
|
|
56
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
39
57
|
}
|
|
40
|
-
|
|
58
|
+
catch (e) {
|
|
59
|
+
if (!this.handleToolErrors) {
|
|
60
|
+
throw e;
|
|
61
|
+
}
|
|
41
62
|
return new messages_1.ToolMessage({
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
tool_call_id: call.id,
|
|
63
|
+
content: `Error: ${e.message}\n Please fix your mistakes.`,
|
|
64
|
+
name: call.name,
|
|
65
|
+
tool_call_id: call.id ?? "",
|
|
45
66
|
});
|
|
46
67
|
}
|
|
47
68
|
}) ?? []);
|
|
@@ -4,6 +4,11 @@ import { StructuredToolInterface } from "@langchain/core/tools";
|
|
|
4
4
|
import { RunnableCallable } from "../utils.js";
|
|
5
5
|
import { END } from "../graph/graph.js";
|
|
6
6
|
import { MessagesState } from "../graph/message.js";
|
|
7
|
+
export type ToolNodeOptions = {
|
|
8
|
+
name?: string;
|
|
9
|
+
tags?: string[];
|
|
10
|
+
handleToolErrors?: boolean;
|
|
11
|
+
};
|
|
7
12
|
export declare class ToolNode<T extends BaseMessage[] | MessagesState> extends RunnableCallable<T, T> {
|
|
8
13
|
/**
|
|
9
14
|
A node that runs the tools requested in the last AIMessage. It can be used
|
|
@@ -12,7 +17,8 @@ export declare class ToolNode<T extends BaseMessage[] | MessagesState> extends R
|
|
|
12
17
|
a list of ToolMessages, one for each tool call.
|
|
13
18
|
*/
|
|
14
19
|
tools: (StructuredToolInterface | RunnableToolLike)[];
|
|
15
|
-
|
|
20
|
+
handleToolErrors: boolean;
|
|
21
|
+
constructor(tools: (StructuredToolInterface | RunnableToolLike)[], options?: ToolNodeOptions);
|
|
16
22
|
private run;
|
|
17
23
|
}
|
|
18
24
|
export declare function toolsCondition(state: BaseMessage[] | MessagesState): "tools" | typeof END;
|
|
@@ -2,7 +2,8 @@ import { ToolMessage, isBaseMessage, } from "@langchain/core/messages";
|
|
|
2
2
|
import { RunnableCallable } from "../utils.js";
|
|
3
3
|
import { END } from "../graph/graph.js";
|
|
4
4
|
export class ToolNode extends RunnableCallable {
|
|
5
|
-
constructor(tools,
|
|
5
|
+
constructor(tools, options) {
|
|
6
|
+
const { name, tags, handleToolErrors } = options ?? {};
|
|
6
7
|
super({ name, tags, func: (input, config) => this.run(input, config) });
|
|
7
8
|
/**
|
|
8
9
|
A node that runs the tools requested in the last AIMessage. It can be used
|
|
@@ -16,7 +17,14 @@ export class ToolNode extends RunnableCallable {
|
|
|
16
17
|
writable: true,
|
|
17
18
|
value: void 0
|
|
18
19
|
});
|
|
20
|
+
Object.defineProperty(this, "handleToolErrors", {
|
|
21
|
+
enumerable: true,
|
|
22
|
+
configurable: true,
|
|
23
|
+
writable: true,
|
|
24
|
+
value: true
|
|
25
|
+
});
|
|
19
26
|
this.tools = tools;
|
|
27
|
+
this.handleToolErrors = handleToolErrors ?? this.handleToolErrors;
|
|
20
28
|
}
|
|
21
29
|
async run(input, config) {
|
|
22
30
|
const message = Array.isArray(input)
|
|
@@ -27,18 +35,31 @@ export class ToolNode extends RunnableCallable {
|
|
|
27
35
|
}
|
|
28
36
|
const outputs = await Promise.all(message.tool_calls?.map(async (call) => {
|
|
29
37
|
const tool = this.tools.find((tool) => tool.name === call.name);
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
38
|
+
try {
|
|
39
|
+
if (tool === undefined) {
|
|
40
|
+
throw new Error(`Tool "${call.name}" not found.`);
|
|
41
|
+
}
|
|
42
|
+
const output = await tool.invoke({ ...call, type: "tool_call" }, config);
|
|
43
|
+
if (isBaseMessage(output) && output._getType() === "tool") {
|
|
44
|
+
return output;
|
|
45
|
+
}
|
|
46
|
+
else {
|
|
47
|
+
return new ToolMessage({
|
|
48
|
+
name: tool.name,
|
|
49
|
+
content: typeof output === "string" ? output : JSON.stringify(output),
|
|
50
|
+
tool_call_id: call.id,
|
|
51
|
+
});
|
|
52
|
+
}
|
|
53
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
36
54
|
}
|
|
37
|
-
|
|
55
|
+
catch (e) {
|
|
56
|
+
if (!this.handleToolErrors) {
|
|
57
|
+
throw e;
|
|
58
|
+
}
|
|
38
59
|
return new ToolMessage({
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
tool_call_id: call.id,
|
|
60
|
+
content: `Error: ${e.message}\n Please fix your mistakes.`,
|
|
61
|
+
name: call.name,
|
|
62
|
+
tool_call_id: call.id ?? "",
|
|
42
63
|
});
|
|
43
64
|
}
|
|
44
65
|
}) ?? []);
|
|
@@ -7,7 +7,7 @@ import { AIMessage, HumanMessage, SystemMessage, ToolMessage, } from "@langchain
|
|
|
7
7
|
import { z } from "zod";
|
|
8
8
|
import { RunnableLambda } from "@langchain/core/runnables";
|
|
9
9
|
import { FakeToolCallingChatModel } from "./utils.js";
|
|
10
|
-
import { createAgentExecutor, createReactAgent } from "../prebuilt/index.js";
|
|
10
|
+
import { ToolNode, createAgentExecutor, createReactAgent, } from "../prebuilt/index.js";
|
|
11
11
|
// Tracing slows down the tests
|
|
12
12
|
beforeAll(() => {
|
|
13
13
|
process.env.LANGCHAIN_TRACING_V2 = "false";
|
|
@@ -16,6 +16,67 @@ beforeAll(() => {
|
|
|
16
16
|
process.env.LANGCHAIN_API_KEY = "";
|
|
17
17
|
process.env.LANGCHAIN_PROJECT = "";
|
|
18
18
|
});
|
|
19
|
+
const searchSchema = z.object({
|
|
20
|
+
query: z.string().describe("The query to search for."),
|
|
21
|
+
});
|
|
22
|
+
class SearchAPI extends StructuredTool {
|
|
23
|
+
constructor() {
|
|
24
|
+
super(...arguments);
|
|
25
|
+
Object.defineProperty(this, "name", {
|
|
26
|
+
enumerable: true,
|
|
27
|
+
configurable: true,
|
|
28
|
+
writable: true,
|
|
29
|
+
value: "search_api"
|
|
30
|
+
});
|
|
31
|
+
Object.defineProperty(this, "description", {
|
|
32
|
+
enumerable: true,
|
|
33
|
+
configurable: true,
|
|
34
|
+
writable: true,
|
|
35
|
+
value: "A simple API that returns the input string."
|
|
36
|
+
});
|
|
37
|
+
Object.defineProperty(this, "schema", {
|
|
38
|
+
enumerable: true,
|
|
39
|
+
configurable: true,
|
|
40
|
+
writable: true,
|
|
41
|
+
value: searchSchema
|
|
42
|
+
});
|
|
43
|
+
}
|
|
44
|
+
async _call(input) {
|
|
45
|
+
return `result for ${input?.query}`;
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
class SearchAPIWithArtifact extends StructuredTool {
|
|
49
|
+
constructor() {
|
|
50
|
+
super(...arguments);
|
|
51
|
+
Object.defineProperty(this, "name", {
|
|
52
|
+
enumerable: true,
|
|
53
|
+
configurable: true,
|
|
54
|
+
writable: true,
|
|
55
|
+
value: "search_api"
|
|
56
|
+
});
|
|
57
|
+
Object.defineProperty(this, "description", {
|
|
58
|
+
enumerable: true,
|
|
59
|
+
configurable: true,
|
|
60
|
+
writable: true,
|
|
61
|
+
value: "A simple API that returns the input string."
|
|
62
|
+
});
|
|
63
|
+
Object.defineProperty(this, "schema", {
|
|
64
|
+
enumerable: true,
|
|
65
|
+
configurable: true,
|
|
66
|
+
writable: true,
|
|
67
|
+
value: searchSchema
|
|
68
|
+
});
|
|
69
|
+
Object.defineProperty(this, "responseFormat", {
|
|
70
|
+
enumerable: true,
|
|
71
|
+
configurable: true,
|
|
72
|
+
writable: true,
|
|
73
|
+
value: "content_and_artifact"
|
|
74
|
+
});
|
|
75
|
+
}
|
|
76
|
+
async _call(_) {
|
|
77
|
+
return ["some response format", Buffer.from("123")];
|
|
78
|
+
}
|
|
79
|
+
}
|
|
19
80
|
describe("PreBuilt", () => {
|
|
20
81
|
class SearchAPI extends Tool {
|
|
21
82
|
constructor() {
|
|
@@ -198,67 +259,6 @@ describe("PreBuilt", () => {
|
|
|
198
259
|
});
|
|
199
260
|
});
|
|
200
261
|
describe("createReactAgent", () => {
|
|
201
|
-
const searchSchema = z.object({
|
|
202
|
-
query: z.string().describe("The query to search for."),
|
|
203
|
-
});
|
|
204
|
-
class SearchAPI extends StructuredTool {
|
|
205
|
-
constructor() {
|
|
206
|
-
super(...arguments);
|
|
207
|
-
Object.defineProperty(this, "name", {
|
|
208
|
-
enumerable: true,
|
|
209
|
-
configurable: true,
|
|
210
|
-
writable: true,
|
|
211
|
-
value: "search_api"
|
|
212
|
-
});
|
|
213
|
-
Object.defineProperty(this, "description", {
|
|
214
|
-
enumerable: true,
|
|
215
|
-
configurable: true,
|
|
216
|
-
writable: true,
|
|
217
|
-
value: "A simple API that returns the input string."
|
|
218
|
-
});
|
|
219
|
-
Object.defineProperty(this, "schema", {
|
|
220
|
-
enumerable: true,
|
|
221
|
-
configurable: true,
|
|
222
|
-
writable: true,
|
|
223
|
-
value: searchSchema
|
|
224
|
-
});
|
|
225
|
-
}
|
|
226
|
-
async _call(input) {
|
|
227
|
-
return `result for ${input?.query}`;
|
|
228
|
-
}
|
|
229
|
-
}
|
|
230
|
-
class SearchAPIWithArtifact extends StructuredTool {
|
|
231
|
-
constructor() {
|
|
232
|
-
super(...arguments);
|
|
233
|
-
Object.defineProperty(this, "name", {
|
|
234
|
-
enumerable: true,
|
|
235
|
-
configurable: true,
|
|
236
|
-
writable: true,
|
|
237
|
-
value: "search_api"
|
|
238
|
-
});
|
|
239
|
-
Object.defineProperty(this, "description", {
|
|
240
|
-
enumerable: true,
|
|
241
|
-
configurable: true,
|
|
242
|
-
writable: true,
|
|
243
|
-
value: "A simple API that returns the input string."
|
|
244
|
-
});
|
|
245
|
-
Object.defineProperty(this, "schema", {
|
|
246
|
-
enumerable: true,
|
|
247
|
-
configurable: true,
|
|
248
|
-
writable: true,
|
|
249
|
-
value: searchSchema
|
|
250
|
-
});
|
|
251
|
-
Object.defineProperty(this, "responseFormat", {
|
|
252
|
-
enumerable: true,
|
|
253
|
-
configurable: true,
|
|
254
|
-
writable: true,
|
|
255
|
-
value: "content_and_artifact"
|
|
256
|
-
});
|
|
257
|
-
}
|
|
258
|
-
async _call(_) {
|
|
259
|
-
return ["some response format", Buffer.from("123")];
|
|
260
|
-
}
|
|
261
|
-
}
|
|
262
262
|
const tools = [new SearchAPI()];
|
|
263
263
|
it("Can use string message modifier", async () => {
|
|
264
264
|
const llm = new FakeToolCallingChatModel({
|
|
@@ -382,11 +382,11 @@ describe("createReactAgent", () => {
|
|
|
382
382
|
});
|
|
383
383
|
// Instead of re-implementing the tool, wrap it in a RunnableLambda and
|
|
384
384
|
// call `asTool` to create a RunnableToolLike.
|
|
385
|
-
const
|
|
386
|
-
const runnableToolLikeTool = RunnableLambda.from(async (input, config) =>
|
|
387
|
-
name:
|
|
388
|
-
description:
|
|
389
|
-
schema:
|
|
385
|
+
const searchApiTool = new SearchAPI();
|
|
386
|
+
const runnableToolLikeTool = RunnableLambda.from(async (input, config) => searchApiTool.invoke(input, config)).asTool({
|
|
387
|
+
name: searchApiTool.name,
|
|
388
|
+
description: searchApiTool.description,
|
|
389
|
+
schema: searchApiTool.schema,
|
|
390
390
|
});
|
|
391
391
|
const agent = createReactAgent({
|
|
392
392
|
llm,
|
|
@@ -406,11 +406,22 @@ describe("createReactAgent", () => {
|
|
|
406
406
|
}),
|
|
407
407
|
new ToolMessage({
|
|
408
408
|
name: "search_api",
|
|
409
|
-
content: "
|
|
409
|
+
content: "result for foo",
|
|
410
410
|
tool_call_id: "tool_abcd123",
|
|
411
|
-
artifact: Buffer.from("123"),
|
|
412
411
|
}),
|
|
413
412
|
new AIMessage("result2"),
|
|
414
413
|
]);
|
|
415
414
|
});
|
|
416
415
|
});
|
|
416
|
+
describe("ToolNode", () => {
|
|
417
|
+
it("Should support graceful error handling", async () => {
|
|
418
|
+
const toolNode = new ToolNode([new SearchAPI()]);
|
|
419
|
+
const res = await toolNode.invoke([
|
|
420
|
+
new AIMessage({
|
|
421
|
+
content: "",
|
|
422
|
+
tool_calls: [{ name: "badtool", args: {}, id: "testid" }],
|
|
423
|
+
}),
|
|
424
|
+
]);
|
|
425
|
+
expect(res[0].content).toEqual(`Error: Tool "badtool" not found.\n Please fix your mistakes.`);
|
|
426
|
+
});
|
|
427
|
+
});
|
|
@@ -1652,7 +1652,7 @@ describe("MessageGraph", () => {
|
|
|
1652
1652
|
.compile();
|
|
1653
1653
|
const result = await app.invoke(new HumanMessage("what is the weather in sf?"));
|
|
1654
1654
|
expect(result).toHaveLength(6);
|
|
1655
|
-
expect(result).
|
|
1655
|
+
expect(JSON.stringify(result)).toEqual(JSON.stringify([
|
|
1656
1656
|
new HumanMessage("what is the weather in sf?"),
|
|
1657
1657
|
new AIMessage({
|
|
1658
1658
|
content: "",
|
|
@@ -1681,7 +1681,7 @@ describe("MessageGraph", () => {
|
|
|
1681
1681
|
name: "search_api",
|
|
1682
1682
|
}),
|
|
1683
1683
|
new AIMessage("answer"),
|
|
1684
|
-
]);
|
|
1684
|
+
]));
|
|
1685
1685
|
});
|
|
1686
1686
|
it("can stream a list of messages", async () => {
|
|
1687
1687
|
const model = new FakeChatModel({
|
|
@@ -1752,7 +1752,7 @@ describe("MessageGraph", () => {
|
|
|
1752
1752
|
}
|
|
1753
1753
|
const lastItem = streamItems[streamItems.length - 1];
|
|
1754
1754
|
expect(Object.keys(lastItem)).toEqual(["agent"]);
|
|
1755
|
-
expect(Object.values(lastItem)[0]).toEqual(new AIMessage("answer"));
|
|
1755
|
+
expect(JSON.stringify(Object.values(lastItem)[0])).toEqual(JSON.stringify(new AIMessage("answer")));
|
|
1756
1756
|
});
|
|
1757
1757
|
});
|
|
1758
1758
|
it("StateGraph start branch then end", async () => {
|
package/dist/utils.cjs
CHANGED
|
@@ -54,7 +54,7 @@ class RunnableCallable extends runnables_1.Runnable {
|
|
|
54
54
|
const childConfig = (0, runnables_1.patchConfig)(config, {
|
|
55
55
|
callbacks: runManager?.getChild(),
|
|
56
56
|
});
|
|
57
|
-
void singletons_1.AsyncLocalStorageProviderSingleton.
|
|
57
|
+
void singletons_1.AsyncLocalStorageProviderSingleton.runWithConfig(childConfig, async () => {
|
|
58
58
|
try {
|
|
59
59
|
const output = await this.func(input, childConfig);
|
|
60
60
|
resolve(output);
|
package/dist/utils.js
CHANGED
|
@@ -51,7 +51,7 @@ export class RunnableCallable extends Runnable {
|
|
|
51
51
|
const childConfig = patchConfig(config, {
|
|
52
52
|
callbacks: runManager?.getChild(),
|
|
53
53
|
});
|
|
54
|
-
void AsyncLocalStorageProviderSingleton.
|
|
54
|
+
void AsyncLocalStorageProviderSingleton.runWithConfig(childConfig, async () => {
|
|
55
55
|
try {
|
|
56
56
|
const output = await this.func(input, childConfig);
|
|
57
57
|
resolve(output);
|
package/dist/web.cjs
CHANGED
|
@@ -1,12 +1,13 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.EmptyChannelError = exports.InvalidUpdateError = exports.GraphValueError = exports.GraphRecursionError = exports.BaseCheckpointSaver = exports.emptyCheckpoint = exports.copyCheckpoint = exports.MemorySaver = exports.MessageGraph = exports.StateGraph = exports.START = exports.Graph = exports.END = void 0;
|
|
3
|
+
exports.EmptyChannelError = exports.InvalidUpdateError = exports.GraphValueError = exports.GraphRecursionError = exports.BaseCheckpointSaver = exports.emptyCheckpoint = exports.copyCheckpoint = exports.MemorySaver = exports.messagesStateReducer = exports.MessageGraph = exports.StateGraph = exports.START = exports.Graph = exports.END = void 0;
|
|
4
4
|
var index_js_1 = require("./graph/index.cjs");
|
|
5
5
|
Object.defineProperty(exports, "END", { enumerable: true, get: function () { return index_js_1.END; } });
|
|
6
6
|
Object.defineProperty(exports, "Graph", { enumerable: true, get: function () { return index_js_1.Graph; } });
|
|
7
7
|
Object.defineProperty(exports, "START", { enumerable: true, get: function () { return index_js_1.START; } });
|
|
8
8
|
Object.defineProperty(exports, "StateGraph", { enumerable: true, get: function () { return index_js_1.StateGraph; } });
|
|
9
9
|
Object.defineProperty(exports, "MessageGraph", { enumerable: true, get: function () { return index_js_1.MessageGraph; } });
|
|
10
|
+
Object.defineProperty(exports, "messagesStateReducer", { enumerable: true, get: function () { return index_js_1.messagesStateReducer; } });
|
|
10
11
|
var memory_js_1 = require("./checkpoint/memory.cjs");
|
|
11
12
|
Object.defineProperty(exports, "MemorySaver", { enumerable: true, get: function () { return memory_js_1.MemorySaver; } });
|
|
12
13
|
var base_js_1 = require("./checkpoint/base.cjs");
|
package/dist/web.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
export { END, Graph, type StateGraphArgs, START, StateGraph, type CompiledStateGraph, MessageGraph, } from "./graph/index.js";
|
|
1
|
+
export { END, Graph, type StateGraphArgs, START, StateGraph, type CompiledStateGraph, MessageGraph, messagesStateReducer, } from "./graph/index.js";
|
|
2
2
|
export { MemorySaver } from "./checkpoint/memory.js";
|
|
3
3
|
export { type Checkpoint, type CheckpointMetadata, type CheckpointTuple, copyCheckpoint, emptyCheckpoint, BaseCheckpointSaver, } from "./checkpoint/base.js";
|
|
4
4
|
export { GraphRecursionError, GraphValueError, InvalidUpdateError, EmptyChannelError, } from "./errors.js";
|
package/dist/web.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
export { END, Graph, START, StateGraph, MessageGraph, } from "./graph/index.js";
|
|
1
|
+
export { END, Graph, START, StateGraph, MessageGraph, messagesStateReducer, } from "./graph/index.js";
|
|
2
2
|
export { MemorySaver } from "./checkpoint/memory.js";
|
|
3
3
|
export { copyCheckpoint, emptyCheckpoint, BaseCheckpointSaver, } from "./checkpoint/base.js";
|
|
4
4
|
export { GraphRecursionError, GraphValueError, InvalidUpdateError, EmptyChannelError, } from "./errors.js";
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@langchain/langgraph",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.30",
|
|
4
4
|
"description": "LangGraph",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"engines": {
|
|
@@ -37,15 +37,15 @@
|
|
|
37
37
|
"author": "LangChain",
|
|
38
38
|
"license": "MIT",
|
|
39
39
|
"dependencies": {
|
|
40
|
-
"@langchain/core": ">=0.2.
|
|
40
|
+
"@langchain/core": ">=0.2.18 <0.3.0",
|
|
41
41
|
"uuid": "^10.0.0",
|
|
42
42
|
"zod": "^3.23.8"
|
|
43
43
|
},
|
|
44
44
|
"devDependencies": {
|
|
45
45
|
"@jest/globals": "^29.5.0",
|
|
46
|
-
"@langchain/anthropic": "^0.2.
|
|
47
|
-
"@langchain/community": "^0.2.
|
|
48
|
-
"@langchain/openai": "^0.
|
|
46
|
+
"@langchain/anthropic": "^0.2.6",
|
|
47
|
+
"@langchain/community": "^0.2.19",
|
|
48
|
+
"@langchain/openai": "^0.2.4",
|
|
49
49
|
"@langchain/scripts": "^0.0.13",
|
|
50
50
|
"@swc/core": "^1.3.90",
|
|
51
51
|
"@swc/jest": "^0.2.29",
|
|
@@ -67,7 +67,7 @@
|
|
|
67
67
|
"eslint-plugin-prettier": "^4.2.1",
|
|
68
68
|
"jest": "^29.5.0",
|
|
69
69
|
"jest-environment-node": "^29.6.4",
|
|
70
|
-
"langchain": "^0.2.
|
|
70
|
+
"langchain": "^0.2.10",
|
|
71
71
|
"prettier": "^2.8.3",
|
|
72
72
|
"release-it": "^15.10.1",
|
|
73
73
|
"rollup": "^4.5.2",
|