diff --git a/libs/langgraph/src/prebuilt/chat_agent_executor.ts b/libs/langgraph/src/prebuilt/chat_agent_executor.ts index b4fd4c35..861d7f68 100644 --- a/libs/langgraph/src/prebuilt/chat_agent_executor.ts +++ b/libs/langgraph/src/prebuilt/chat_agent_executor.ts @@ -15,10 +15,10 @@ import { } from "../graph/state.js"; import { END, START } from "../graph/index.js"; -/** @ignore */ +/** @deprecated Use {@link createReactAgent} instead with tool calling. */ export type FunctionCallingExecutorState = { messages: Array }; -/** @ignore */ +/** @deprecated Use {@link createReactAgent} instead with tool calling. */ export function createFunctionCallingExecutor({ model, tools, diff --git a/libs/langgraph/src/prebuilt/react_agent_executor.ts b/libs/langgraph/src/prebuilt/react_agent_executor.ts index 743b1b40..89d4bf56 100644 --- a/libs/langgraph/src/prebuilt/react_agent_executor.ts +++ b/libs/langgraph/src/prebuilt/react_agent_executor.ts @@ -20,7 +20,12 @@ import { } from "@langchain/core/language_models/base"; import { ChatPromptTemplate } from "@langchain/core/prompts"; import { BaseCheckpointSaver } from "@langchain/langgraph-checkpoint"; -import { END, START, StateGraph } from "../graph/index.js"; +import { + END, + messagesStateReducer, + START, + StateGraph, +} from "../graph/index.js"; import { MessagesAnnotation } from "../graph/messages_annotation.js"; import { CompiledStateGraph, StateGraphArgs } from "../graph/state.js"; import { All } from "../pregel/types.js"; @@ -81,7 +86,7 @@ export function createReactAgent( } = props; const schema: StateGraphArgs["channels"] = { messages: { - value: (left: BaseMessage[], right: BaseMessage[]) => left.concat(right), + value: messagesStateReducer, default: () => [], }, }; diff --git a/libs/langgraph/src/tests/prebuilt.test.ts b/libs/langgraph/src/tests/prebuilt.test.ts index c38d1309..ccfd3cd9 100644 --- a/libs/langgraph/src/tests/prebuilt.test.ts +++ b/libs/langgraph/src/tests/prebuilt.test.ts @@ -1,4 +1,5 @@ /* eslint-disable no-process-env */ +/* eslint-disable no-param-reassign */ import { beforeAll, describe, expect, it } from "@jest/globals"; import { PromptTemplate } from "@langchain/core/prompts"; import { StructuredTool, Tool } from "@langchain/core/tools"; @@ -275,7 +276,7 @@ describe("createReactAgent", () => { messages: [new HumanMessage("Hello Input!")], }); - expect(result.messages).toEqual([ + const expected = [ new HumanMessage("Hello Input!"), new AIMessage({ content: "result1", @@ -287,9 +288,14 @@ describe("createReactAgent", () => { name: "search_api", content: "result for foo", tool_call_id: "tool_abcd123", + artifact: undefined, }), new AIMessage("result2"), - ]); + ].map((message, i) => { + message.id = result.messages[i].id; + return message; + }); + expect(result.messages).toEqual(expected); }); it("Can use SystemMessage message modifier", async () => { @@ -314,7 +320,7 @@ describe("createReactAgent", () => { const result = await agent.invoke({ messages: [], }); - expect(result.messages).toEqual([ + const expected = [ new AIMessage({ content: "result1", tool_calls: [ @@ -325,9 +331,14 @@ describe("createReactAgent", () => { name: "search_api", content: "result for foo", tool_call_id: "tool_abcd123", + artifact: undefined, }), new AIMessage("result2"), - ]); + ].map((message, i) => { + message.id = result.messages[i].id; + return message; + }); + expect(result.messages).toEqual(expected); }); it("Should respect a passed signal", async () => { @@ -389,7 +400,7 @@ describe("createReactAgent", () => { messages: [new HumanMessage("Hello Input!")], }); - expect(result.messages).toEqual([ + const expected = [ new HumanMessage("Hello Input!"), new AIMessage({ content: "result1", @@ -404,7 +415,11 @@ describe("createReactAgent", () => { artifact: Buffer.from("123"), }), new AIMessage("result2"), - ]); + ].map((message, i) => { + message.id = result.messages[i].id; + return message; + }); + expect(result.messages).toEqual(expected); }); it("Can accept RunnableToolLike", async () => { @@ -442,7 +457,7 @@ describe("createReactAgent", () => { messages: [new HumanMessage("Hello Input!")], }); - expect(result.messages).toEqual([ + const expected = [ new HumanMessage("Hello Input!"), new AIMessage({ content: "result1", @@ -456,7 +471,11 @@ describe("createReactAgent", () => { tool_call_id: "tool_abcd123", }), new AIMessage("result2"), - ]); + ].map((message, i) => { + message.id = result.messages[i].id; + return message; + }); + expect(result.messages).toEqual(expected); }); });