@langchain/langgraph 0.2.16 → 0.2.18-rc.0

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.
@@ -13,6 +13,7 @@ const write_js_1 = require("../pregel/write.cjs");
13
13
  const constants_js_1 = require("../constants.cjs");
14
14
  const utils_js_1 = require("../utils.cjs");
15
15
  const errors_js_1 = require("../errors.cjs");
16
+ const subgraph_js_1 = require("../pregel/utils/subgraph.cjs");
16
17
  /** Special reserved node name denoting the start of a graph. */
17
18
  exports.START = "__start__";
18
19
  /** Special reserved node name denoting the end of a graph. */
@@ -41,6 +42,7 @@ class Branch {
41
42
  }
42
43
  compile(writer, reader) {
43
44
  return write_js_1.ChannelWrite.registerWriter(new utils_js_1.RunnableCallable({
45
+ trace: false,
44
46
  func: async (input, config) => {
45
47
  try {
46
48
  return await this._route(input, config, writer, reader);
@@ -140,11 +142,13 @@ class Graph {
140
142
  if (key === exports.END) {
141
143
  throw new Error(`Node \`${key}\` is reserved.`);
142
144
  }
145
+ const runnable = (0, runnables_1._coerceToRunnable)(
146
+ // Account for arbitrary state due to Send API
147
+ action);
143
148
  this.nodes[key] = {
144
- runnable: (0, runnables_1._coerceToRunnable)(
145
- // Account for arbitrary state due to Send API
146
- action),
149
+ runnable,
147
150
  metadata: options?.metadata,
151
+ subgraphs: (0, subgraph_js_1.isPregelLike)(runnable) ? [runnable] : options?.subgraphs,
148
152
  };
149
153
  return this;
150
154
  }
@@ -300,6 +304,7 @@ class CompiledGraph extends index_js_1.Pregel {
300
304
  channels: [],
301
305
  triggers: [],
302
306
  metadata: node.metadata,
307
+ subgraphs: node.subgraphs,
303
308
  })
304
309
  .pipe(node.runnable)
305
310
  .pipe(new write_js_1.ChannelWrite([{ channel: key, value: write_js_1.PASSTHROUGH }], [constants_js_1.TAG_HIDDEN]));
@@ -28,9 +28,11 @@ export declare class Branch<IO, N extends string, CallOptions extends LangGraphR
28
28
  export type NodeSpec<RunInput, RunOutput> = {
29
29
  runnable: Runnable<RunInput, RunOutput>;
30
30
  metadata?: Record<string, unknown>;
31
+ subgraphs?: Pregel<any, any>[];
31
32
  };
32
33
  export type AddNodeOptions = {
33
34
  metadata?: Record<string, unknown>;
35
+ subgraphs?: Pregel<any, any>[];
34
36
  };
35
37
  export declare class Graph<N extends string = typeof END, RunInput = any, RunOutput = any, NodeSpecType extends NodeSpec<RunInput, RunOutput> = NodeSpec<RunInput, RunOutput>, C extends StateDefinition = StateDefinition> {
36
38
  nodes: Record<N, NodeSpecType>;
@@ -10,6 +10,7 @@ import { ChannelWrite, PASSTHROUGH } from "../pregel/write.js";
10
10
  import { _isSend, CHECKPOINT_NAMESPACE_END, CHECKPOINT_NAMESPACE_SEPARATOR, TAG_HIDDEN, } from "../constants.js";
11
11
  import { gatherIteratorSync, RunnableCallable } from "../utils.js";
12
12
  import { InvalidUpdateError, NodeInterrupt } from "../errors.js";
13
+ import { isPregelLike } from "../pregel/utils/subgraph.js";
13
14
  /** Special reserved node name denoting the start of a graph. */
14
15
  export const START = "__start__";
15
16
  /** Special reserved node name denoting the end of a graph. */
@@ -38,6 +39,7 @@ export class Branch {
38
39
  }
39
40
  compile(writer, reader) {
40
41
  return ChannelWrite.registerWriter(new RunnableCallable({
42
+ trace: false,
41
43
  func: async (input, config) => {
42
44
  try {
43
45
  return await this._route(input, config, writer, reader);
@@ -136,11 +138,13 @@ export class Graph {
136
138
  if (key === END) {
137
139
  throw new Error(`Node \`${key}\` is reserved.`);
138
140
  }
141
+ const runnable = _coerceToRunnable(
142
+ // Account for arbitrary state due to Send API
143
+ action);
139
144
  this.nodes[key] = {
140
- runnable: _coerceToRunnable(
141
- // Account for arbitrary state due to Send API
142
- action),
145
+ runnable,
143
146
  metadata: options?.metadata,
147
+ subgraphs: isPregelLike(runnable) ? [runnable] : options?.subgraphs,
144
148
  };
145
149
  return this;
146
150
  }
@@ -295,6 +299,7 @@ export class CompiledGraph extends Pregel {
295
299
  channels: [],
296
300
  triggers: [],
297
301
  metadata: node.metadata,
302
+ subgraphs: node.subgraphs,
298
303
  })
299
304
  .pipe(node.runnable)
300
305
  .pipe(new ChannelWrite([{ channel: key, value: PASSTHROUGH }], [TAG_HIDDEN]));
@@ -14,6 +14,7 @@ const constants_js_1 = require("../constants.cjs");
14
14
  const errors_js_1 = require("../errors.cjs");
15
15
  const annotation_js_1 = require("./annotation.cjs");
16
16
  const base_js_2 = require("../managed/base.cjs");
17
+ const subgraph_js_1 = require("../pregel/utils/subgraph.cjs");
17
18
  const ROOT = "__root__";
18
19
  /**
19
20
  * A graph whose nodes communicate by reading and writing to a shared state.
@@ -216,11 +217,29 @@ class StateGraph extends graph_js_1.Graph {
216
217
  if (options?.input !== undefined) {
217
218
  this._addSchema(options.input.spec);
218
219
  }
220
+ let runnable;
221
+ if (runnables_1.Runnable.isRunnable(action)) {
222
+ runnable = action;
223
+ }
224
+ else if (typeof action === "function") {
225
+ runnable = new utils_js_1.RunnableCallable({
226
+ func: action,
227
+ name: key,
228
+ trace: false,
229
+ });
230
+ }
231
+ else {
232
+ runnable = (0, runnables_1._coerceToRunnable)(action);
233
+ }
219
234
  const nodeSpec = {
220
- runnable: (0, runnables_1._coerceToRunnable)(action),
235
+ runnable: runnable,
221
236
  retryPolicy: options?.retryPolicy,
222
237
  metadata: options?.metadata,
223
238
  input: options?.input?.spec ?? this._schemaDefinition,
239
+ subgraphs: (0, subgraph_js_1.isPregelLike)(runnable)
240
+ ? // eslint-disable-next-line @typescript-eslint/no-explicit-any
241
+ [runnable]
242
+ : options?.subgraphs,
224
243
  };
225
244
  this.nodes[key] = nodeSpec;
226
245
  return this;
@@ -377,6 +396,7 @@ class CompiledStateGraph extends graph_js_1.CompiledGraph {
377
396
  bound: node?.runnable,
378
397
  metadata: node?.metadata,
379
398
  retryPolicy: node?.retryPolicy,
399
+ subgraphs: node?.subgraphs,
380
400
  });
381
401
  }
382
402
  }
@@ -1,5 +1,5 @@
1
1
  /* eslint-disable @typescript-eslint/no-use-before-define */
2
- import { _coerceToRunnable, } from "@langchain/core/runnables";
2
+ import { _coerceToRunnable, Runnable, } from "@langchain/core/runnables";
3
3
  import { isBaseChannel } from "../channels/base.js";
4
4
  import { END, CompiledGraph, Graph, START, } from "./graph.js";
5
5
  import { ChannelWrite, PASSTHROUGH, SKIP_WRITE, } from "../pregel/write.js";
@@ -11,6 +11,7 @@ import { _isSend, CHECKPOINT_NAMESPACE_END, CHECKPOINT_NAMESPACE_SEPARATOR, TAG_
11
11
  import { InvalidUpdateError } from "../errors.js";
12
12
  import { getChannel, } from "./annotation.js";
13
13
  import { isConfiguredManagedValue } from "../managed/base.js";
14
+ import { isPregelLike } from "../pregel/utils/subgraph.js";
14
15
  const ROOT = "__root__";
15
16
  /**
16
17
  * A graph whose nodes communicate by reading and writing to a shared state.
@@ -213,11 +214,29 @@ export class StateGraph extends Graph {
213
214
  if (options?.input !== undefined) {
214
215
  this._addSchema(options.input.spec);
215
216
  }
217
+ let runnable;
218
+ if (Runnable.isRunnable(action)) {
219
+ runnable = action;
220
+ }
221
+ else if (typeof action === "function") {
222
+ runnable = new RunnableCallable({
223
+ func: action,
224
+ name: key,
225
+ trace: false,
226
+ });
227
+ }
228
+ else {
229
+ runnable = _coerceToRunnable(action);
230
+ }
216
231
  const nodeSpec = {
217
- runnable: _coerceToRunnable(action),
232
+ runnable: runnable,
218
233
  retryPolicy: options?.retryPolicy,
219
234
  metadata: options?.metadata,
220
235
  input: options?.input?.spec ?? this._schemaDefinition,
236
+ subgraphs: isPregelLike(runnable)
237
+ ? // eslint-disable-next-line @typescript-eslint/no-explicit-any
238
+ [runnable]
239
+ : options?.subgraphs,
221
240
  };
222
241
  this.nodes[key] = nodeSpec;
223
242
  return this;
@@ -373,6 +392,7 @@ export class CompiledStateGraph extends CompiledGraph {
373
392
  bound: node?.runnable,
374
393
  metadata: node?.metadata,
375
394
  retryPolicy: node?.retryPolicy,
395
+ subgraphs: node?.subgraphs,
376
396
  });
377
397
  }
378
398
  }
@@ -2,4 +2,4 @@ export { type AgentExecutorState, createAgentExecutor, } from "./agent_executor.
2
2
  export { type FunctionCallingExecutorState, createFunctionCallingExecutor, } from "./chat_agent_executor.js";
3
3
  export { type AgentState, createReactAgent } from "./react_agent_executor.js";
4
4
  export { type ToolExecutorArgs, type ToolInvocationInterface, ToolExecutor, } from "./tool_executor.js";
5
- export { ToolNode, toolsCondition } from "./tool_node.js";
5
+ export { ToolNode, toolsCondition, type ToolNodeOptions } from "./tool_node.js";
@@ -95,7 +95,7 @@ function createReactAgent(params) {
95
95
  const workflow = new index_js_1.StateGraph({
96
96
  channels: schema,
97
97
  })
98
- .addNode("agent", runnables_1.RunnableLambda.from(callModel).withConfig({ runName: "agent" }))
98
+ .addNode("agent", callModel)
99
99
  .addNode("tools", new tool_node_js_1.ToolNode(toolClasses))
100
100
  .addEdge(index_js_1.START, "agent")
101
101
  .addConditionalEdges("agent", shouldContinue, {
@@ -92,7 +92,7 @@ export function createReactAgent(params) {
92
92
  const workflow = new StateGraph({
93
93
  channels: schema,
94
94
  })
95
- .addNode("agent", RunnableLambda.from(callModel).withConfig({ runName: "agent" }))
95
+ .addNode("agent", callModel)
96
96
  .addNode("tools", new ToolNode(toolClasses))
97
97
  .addEdge(START, "agent")
98
98
  .addConditionalEdges("agent", shouldContinue, {
@@ -138,6 +138,12 @@ class ToolNode extends utils_js_1.RunnableCallable {
138
138
  writable: true,
139
139
  value: true
140
140
  });
141
+ Object.defineProperty(this, "trace", {
142
+ enumerable: true,
143
+ configurable: true,
144
+ writable: true,
145
+ value: false
146
+ });
141
147
  this.tools = tools;
142
148
  this.handleToolErrors = handleToolErrors ?? this.handleToolErrors;
143
149
  }
@@ -1,5 +1,5 @@
1
1
  import { BaseMessage } from "@langchain/core/messages";
2
- import { RunnableToolLike } from "@langchain/core/runnables";
2
+ import { RunnableConfig, RunnableToolLike } from "@langchain/core/runnables";
3
3
  import { StructuredToolInterface } from "@langchain/core/tools";
4
4
  import { RunnableCallable } from "../utils.js";
5
5
  import { END } from "../graph/graph.js";
@@ -129,7 +129,8 @@ export type ToolNodeOptions = {
129
129
  export declare class ToolNode<T = any> extends RunnableCallable<T, T> {
130
130
  tools: (StructuredToolInterface | RunnableToolLike)[];
131
131
  handleToolErrors: boolean;
132
+ trace: boolean;
132
133
  constructor(tools: (StructuredToolInterface | RunnableToolLike)[], options?: ToolNodeOptions);
133
- private run;
134
+ protected run(input: any, config: RunnableConfig): Promise<T>;
134
135
  }
135
136
  export declare function toolsCondition(state: BaseMessage[] | typeof MessagesAnnotation.State): "tools" | typeof END;
@@ -135,6 +135,12 @@ export class ToolNode extends RunnableCallable {
135
135
  writable: true,
136
136
  value: true
137
137
  });
138
+ Object.defineProperty(this, "trace", {
139
+ enumerable: true,
140
+ configurable: true,
141
+ writable: true,
142
+ value: false
143
+ });
138
144
  this.tools = tools;
139
145
  this.handleToolErrors = handleToolErrors ?? this.handleToolErrors;
140
146
  }
@@ -275,6 +275,7 @@ function _prepareSingleTask(taskPath, checkpoint, processes, channels, managed,
275
275
  name: packet.node,
276
276
  input: packet.args,
277
277
  proc: node,
278
+ subgraphs: proc.subgraphs,
278
279
  writes,
279
280
  config: (0, runnables_1.patchConfig)((0, runnables_1.mergeConfigs)(config, {
280
281
  metadata,
@@ -371,6 +372,7 @@ function _prepareSingleTask(taskPath, checkpoint, processes, channels, managed,
371
372
  name,
372
373
  input: val,
373
374
  proc: node,
375
+ subgraphs: proc.subgraphs,
374
376
  writes,
375
377
  config: (0, runnables_1.patchConfig)((0, runnables_1.mergeConfigs)(config, {
376
378
  metadata,
@@ -266,6 +266,7 @@ export function _prepareSingleTask(taskPath, checkpoint, processes, channels, ma
266
266
  name: packet.node,
267
267
  input: packet.args,
268
268
  proc: node,
269
+ subgraphs: proc.subgraphs,
269
270
  writes,
270
271
  config: patchConfig(mergeConfigs(config, {
271
272
  metadata,
@@ -362,6 +363,7 @@ export function _prepareSingleTask(taskPath, checkpoint, processes, channels, ma
362
363
  name,
363
364
  input: val,
364
365
  proc: node,
366
+ subgraphs: proc.subgraphs,
365
367
  writes,
366
368
  config: patchConfig(mergeConfigs(config, {
367
369
  metadata,
@@ -127,7 +127,8 @@ function* mapDebugCheckpoint(step, config, channels, streamChannels, metadata, t
127
127
  const parentNs = config.configurable?.checkpoint_ns;
128
128
  const taskStates = {};
129
129
  for (const task of tasks) {
130
- if (!(0, subgraph_js_1.findSubgraphPregel)(task.proc))
130
+ const candidates = task.subgraphs?.length ? task.subgraphs : [task.proc];
131
+ if (!candidates.find(subgraph_js_1.findSubgraphPregel))
131
132
  continue;
132
133
  let taskNs = `${task.name}:${task.id}`;
133
134
  if (parentNs)
@@ -121,7 +121,8 @@ export function* mapDebugCheckpoint(step, config, channels, streamChannels, meta
121
121
  const parentNs = config.configurable?.checkpoint_ns;
122
122
  const taskStates = {};
123
123
  for (const task of tasks) {
124
- if (!findSubgraphPregel(task.proc))
124
+ const candidates = task.subgraphs?.length ? task.subgraphs : [task.proc];
125
+ if (!candidates.find(findSubgraphPregel))
125
126
  continue;
126
127
  let taskNs = `${task.name}:${task.id}`;
127
128
  if (parentNs)
@@ -255,26 +255,28 @@ class Pregel extends runnables_1.Runnable {
255
255
  continue;
256
256
  }
257
257
  }
258
- const graph = (0, subgraph_js_1.findSubgraphPregel)(node.bound);
259
- // if found, yield recursively
260
- if (graph !== undefined) {
261
- if (name === namespace) {
262
- yield [name, graph];
263
- return;
264
- }
265
- if (namespace === undefined) {
266
- yield [name, graph];
267
- }
268
- if (recurse) {
269
- let newNamespace = namespace;
270
- if (namespace !== undefined) {
271
- newNamespace = namespace.slice(name.length + 1);
258
+ const candidates = node.subgraphs?.length ? node.subgraphs : [node.bound];
259
+ for (const candidate of candidates) {
260
+ const graph = (0, subgraph_js_1.findSubgraphPregel)(candidate);
261
+ if (graph !== undefined) {
262
+ if (name === namespace) {
263
+ yield [name, graph];
264
+ return;
272
265
  }
273
- for (const [subgraphName, subgraph] of graph.getSubgraphs(newNamespace, recurse)) {
274
- yield [
275
- `${name}${constants_js_1.CHECKPOINT_NAMESPACE_SEPARATOR}${subgraphName}`,
276
- subgraph,
277
- ];
266
+ if (namespace === undefined) {
267
+ yield [name, graph];
268
+ }
269
+ if (recurse) {
270
+ let newNamespace = namespace;
271
+ if (namespace !== undefined) {
272
+ newNamespace = namespace.slice(name.length + 1);
273
+ }
274
+ for (const [subgraphName, subgraph] of graph.getSubgraphs(newNamespace, recurse)) {
275
+ yield [
276
+ `${name}${constants_js_1.CHECKPOINT_NAMESPACE_SEPARATOR}${subgraphName}`,
277
+ subgraph,
278
+ ];
279
+ }
278
280
  }
279
281
  }
280
282
  }
@@ -522,9 +524,10 @@ class Pregel extends runnables_1.Runnable {
522
524
  const task = {
523
525
  name: asNode,
524
526
  input: values,
525
- proc:
526
- // eslint-disable-next-line @typescript-eslint/no-explicit-any
527
- writers.length > 1 ? runnables_1.RunnableSequence.from(writers) : writers[0],
527
+ proc: writers.length > 1
528
+ ? // eslint-disable-next-line @typescript-eslint/no-explicit-any
529
+ runnables_1.RunnableSequence.from(writers, { omitSequenceTags: true })
530
+ : writers[0],
528
531
  writes: [],
529
532
  triggers: [constants_js_1.INTERRUPT],
530
533
  id: (0, langgraph_checkpoint_1.uuid5)(constants_js_1.INTERRUPT, checkpoint.id),
@@ -248,26 +248,28 @@ export class Pregel extends Runnable {
248
248
  continue;
249
249
  }
250
250
  }
251
- const graph = findSubgraphPregel(node.bound);
252
- // if found, yield recursively
253
- if (graph !== undefined) {
254
- if (name === namespace) {
255
- yield [name, graph];
256
- return;
257
- }
258
- if (namespace === undefined) {
259
- yield [name, graph];
260
- }
261
- if (recurse) {
262
- let newNamespace = namespace;
263
- if (namespace !== undefined) {
264
- newNamespace = namespace.slice(name.length + 1);
251
+ const candidates = node.subgraphs?.length ? node.subgraphs : [node.bound];
252
+ for (const candidate of candidates) {
253
+ const graph = findSubgraphPregel(candidate);
254
+ if (graph !== undefined) {
255
+ if (name === namespace) {
256
+ yield [name, graph];
257
+ return;
265
258
  }
266
- for (const [subgraphName, subgraph] of graph.getSubgraphs(newNamespace, recurse)) {
267
- yield [
268
- `${name}${CHECKPOINT_NAMESPACE_SEPARATOR}${subgraphName}`,
269
- subgraph,
270
- ];
259
+ if (namespace === undefined) {
260
+ yield [name, graph];
261
+ }
262
+ if (recurse) {
263
+ let newNamespace = namespace;
264
+ if (namespace !== undefined) {
265
+ newNamespace = namespace.slice(name.length + 1);
266
+ }
267
+ for (const [subgraphName, subgraph] of graph.getSubgraphs(newNamespace, recurse)) {
268
+ yield [
269
+ `${name}${CHECKPOINT_NAMESPACE_SEPARATOR}${subgraphName}`,
270
+ subgraph,
271
+ ];
272
+ }
271
273
  }
272
274
  }
273
275
  }
@@ -515,9 +517,10 @@ export class Pregel extends Runnable {
515
517
  const task = {
516
518
  name: asNode,
517
519
  input: values,
518
- proc:
519
- // eslint-disable-next-line @typescript-eslint/no-explicit-any
520
- writers.length > 1 ? RunnableSequence.from(writers) : writers[0],
520
+ proc: writers.length > 1
521
+ ? // eslint-disable-next-line @typescript-eslint/no-explicit-any
522
+ RunnableSequence.from(writers, { omitSequenceTags: true })
523
+ : writers[0],
521
524
  writes: [],
522
525
  triggers: [INTERRUPT],
523
526
  id: uuid5(INTERRUPT, checkpoint.id),
@@ -63,7 +63,7 @@ const defaultRunnableBound =
63
63
  /* #__PURE__ */ new runnables_1.RunnablePassthrough();
64
64
  class PregelNode extends runnables_1.RunnableBinding {
65
65
  constructor(fields) {
66
- const { channels, triggers, mapper, writers, bound, kwargs, metadata, retryPolicy, tags, } = fields;
66
+ const { channels, triggers, mapper, writers, bound, kwargs, metadata, retryPolicy, tags, subgraphs, } = fields;
67
67
  const mergedTags = [
68
68
  ...(fields.config?.tags ? fields.config.tags : []),
69
69
  ...(tags ?? []),
@@ -139,6 +139,12 @@ class PregelNode extends runnables_1.RunnableBinding {
139
139
  writable: true,
140
140
  value: void 0
141
141
  });
142
+ Object.defineProperty(this, "subgraphs", {
143
+ enumerable: true,
144
+ configurable: true,
145
+ writable: true,
146
+ value: void 0
147
+ });
142
148
  this.channels = channels;
143
149
  this.triggers = triggers;
144
150
  this.mapper = mapper;
@@ -148,6 +154,7 @@ class PregelNode extends runnables_1.RunnableBinding {
148
154
  this.metadata = metadata ?? this.metadata;
149
155
  this.tags = mergedTags;
150
156
  this.retryPolicy = retryPolicy;
157
+ this.subgraphs = subgraphs;
151
158
  }
152
159
  getWriters() {
153
160
  const newWriters = [...this.writers];
@@ -178,6 +185,7 @@ class PregelNode extends runnables_1.RunnableBinding {
178
185
  first: writers[0],
179
186
  middle: writers.slice(1, writers.length - 1),
180
187
  last: writers[writers.length - 1],
188
+ omitSequenceTags: true,
181
189
  });
182
190
  }
183
191
  else if (writers.length > 0) {
@@ -185,6 +193,7 @@ class PregelNode extends runnables_1.RunnableBinding {
185
193
  first: this.bound,
186
194
  middle: writers.slice(0, writers.length - 1),
187
195
  last: writers[writers.length - 1],
196
+ omitSequenceTags: true,
188
197
  });
189
198
  }
190
199
  else {
@@ -20,6 +20,7 @@ interface PregelNodeArgs<RunInput, RunOutput> extends Partial<RunnableBindingArg
20
20
  config?: RunnableConfig;
21
21
  metadata?: Record<string, unknown>;
22
22
  retryPolicy?: RetryPolicy;
23
+ subgraphs?: Runnable[];
23
24
  }
24
25
  export type PregelNodeInputType = any;
25
26
  export type PregelNodeOutputType = any;
@@ -34,6 +35,7 @@ export declare class PregelNode<RunInput = PregelNodeInputType, RunOutput = Preg
34
35
  metadata: Record<string, unknown>;
35
36
  tags: string[];
36
37
  retryPolicy?: RetryPolicy;
38
+ subgraphs?: Runnable[];
37
39
  constructor(fields: PregelNodeArgs<RunInput, RunOutput>);
38
40
  getWriters(): Array<Runnable>;
39
41
  getNode(): Runnable<RunInput, RunOutput> | undefined;
@@ -59,7 +59,7 @@ const defaultRunnableBound =
59
59
  /* #__PURE__ */ new RunnablePassthrough();
60
60
  export class PregelNode extends RunnableBinding {
61
61
  constructor(fields) {
62
- const { channels, triggers, mapper, writers, bound, kwargs, metadata, retryPolicy, tags, } = fields;
62
+ const { channels, triggers, mapper, writers, bound, kwargs, metadata, retryPolicy, tags, subgraphs, } = fields;
63
63
  const mergedTags = [
64
64
  ...(fields.config?.tags ? fields.config.tags : []),
65
65
  ...(tags ?? []),
@@ -135,6 +135,12 @@ export class PregelNode extends RunnableBinding {
135
135
  writable: true,
136
136
  value: void 0
137
137
  });
138
+ Object.defineProperty(this, "subgraphs", {
139
+ enumerable: true,
140
+ configurable: true,
141
+ writable: true,
142
+ value: void 0
143
+ });
138
144
  this.channels = channels;
139
145
  this.triggers = triggers;
140
146
  this.mapper = mapper;
@@ -144,6 +150,7 @@ export class PregelNode extends RunnableBinding {
144
150
  this.metadata = metadata ?? this.metadata;
145
151
  this.tags = mergedTags;
146
152
  this.retryPolicy = retryPolicy;
153
+ this.subgraphs = subgraphs;
147
154
  }
148
155
  getWriters() {
149
156
  const newWriters = [...this.writers];
@@ -174,6 +181,7 @@ export class PregelNode extends RunnableBinding {
174
181
  first: writers[0],
175
182
  middle: writers.slice(1, writers.length - 1),
176
183
  last: writers[writers.length - 1],
184
+ omitSequenceTags: true,
177
185
  });
178
186
  }
179
187
  else if (writers.length > 0) {
@@ -181,6 +189,7 @@ export class PregelNode extends RunnableBinding {
181
189
  first: this.bound,
182
190
  middle: writers.slice(0, writers.length - 1),
183
191
  last: writers[writers.length - 1],
192
+ omitSequenceTags: true,
184
193
  });
185
194
  }
186
195
  else {
@@ -71,6 +71,7 @@ export interface PregelExecutableTask<N extends PropertyKey, C extends PropertyK
71
71
  readonly retry_policy?: RetryPolicy;
72
72
  readonly id: string;
73
73
  readonly path?: [string, ...(string | number)[]];
74
+ readonly subgraphs?: Runnable[];
74
75
  }
75
76
  export interface StateSnapshot {
76
77
  /**
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.findSubgraphPregel = void 0;
3
+ exports.findSubgraphPregel = exports.isPregelLike = void 0;
4
4
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
5
5
  function isRunnableSequence(x) {
6
6
  return "steps" in x && Array.isArray(x.steps);
@@ -15,6 +15,7 @@ x
15
15
  "outputChannels" &&
16
16
  x.outputChannels !== undefined);
17
17
  }
18
+ exports.isPregelLike = isPregelLike;
18
19
  function findSubgraphPregel(candidate
19
20
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
20
21
  ) {
@@ -1,3 +1,4 @@
1
- import { Runnable } from "@langchain/core/runnables";
1
+ import { Runnable, RunnableLike } from "@langchain/core/runnables";
2
2
  import type { PregelInterface } from "../types.js";
3
+ export declare function isPregelLike(x: PregelInterface<any, any> | RunnableLike<any, any, any>): x is PregelInterface<any, any>;
3
4
  export declare function findSubgraphPregel(candidate: Runnable): PregelInterface<any, any> | undefined;
@@ -2,7 +2,7 @@
2
2
  function isRunnableSequence(x) {
3
3
  return "steps" in x && Array.isArray(x.steps);
4
4
  }
5
- function isPregelLike(
5
+ export function isPregelLike(
6
6
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
7
7
  x
8
8
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
@@ -88,6 +88,7 @@ class ChannelWrite extends utils_js_1.RunnableCallable {
88
88
  async _write(input, config) {
89
89
  const values = await this._getWriteValues(input, config);
90
90
  ChannelWrite.doWrite(config, values);
91
+ return input;
91
92
  }
92
93
  // TODO: Support requireAtLeastOneOf
93
94
  static doWrite(config, values) {
@@ -15,9 +15,9 @@ export declare class ChannelWrite<RunInput = any> extends RunnableCallable {
15
15
  writes: Array<ChannelWriteEntry | Send>;
16
16
  constructor(writes: Array<ChannelWriteEntry | Send>, tags?: string[]);
17
17
  _getWriteValues(input: unknown, config: RunnableConfig): Promise<[string, unknown][]>;
18
- _write(input: unknown, config: RunnableConfig): Promise<void>;
18
+ _write(input: unknown, config: RunnableConfig): Promise<unknown>;
19
19
  static doWrite(config: RunnableConfig, values: [string, unknown][]): void;
20
- static isWriter(runnable: RunnableLike): boolean;
20
+ static isWriter(runnable: RunnableLike): runnable is ChannelWrite;
21
21
  static registerWriter<T extends Runnable>(runnable: T): T;
22
22
  }
23
23
  export interface ChannelWriteEntry {
@@ -85,6 +85,7 @@ export class ChannelWrite extends RunnableCallable {
85
85
  async _write(input, config) {
86
86
  const values = await this._getWriteValues(input, config);
87
87
  ChannelWrite.doWrite(config, values);
88
+ return input;
88
89
  }
89
90
  // TODO: Support requireAtLeastOneOf
90
91
  static doWrite(config, values) {
package/dist/utils.cjs CHANGED
@@ -74,14 +74,15 @@ class RunnableCallable extends runnables_1.Runnable {
74
74
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
75
75
  let returnValue;
76
76
  const config = (0, config_js_1.ensureLangGraphConfig)(options);
77
+ const mergedConfig = (0, runnables_1.mergeConfigs)(this.config, config);
77
78
  if (this.trace) {
78
- returnValue = await this._callWithConfig(this._tracedInvoke, input, (0, runnables_1.mergeConfigs)(this.config, config));
79
+ returnValue = await this._callWithConfig(this._tracedInvoke, input, mergedConfig);
79
80
  }
80
81
  else {
81
- returnValue = await this.func(input, (0, runnables_1.mergeConfigs)(this.config, config));
82
+ returnValue = await singletons_1.AsyncLocalStorageProviderSingleton.runWithConfig(mergedConfig, async () => this.func(input, mergedConfig));
82
83
  }
83
84
  if (runnables_1.Runnable.isRunnable(returnValue) && this.recurse) {
84
- return await returnValue.invoke(input, config);
85
+ return await singletons_1.AsyncLocalStorageProviderSingleton.runWithConfig(mergedConfig, async () => returnValue.invoke(input, mergedConfig));
85
86
  }
86
87
  return returnValue;
87
88
  }
package/dist/utils.js CHANGED
@@ -71,14 +71,15 @@ export class RunnableCallable extends Runnable {
71
71
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
72
72
  let returnValue;
73
73
  const config = ensureLangGraphConfig(options);
74
+ const mergedConfig = mergeConfigs(this.config, config);
74
75
  if (this.trace) {
75
- returnValue = await this._callWithConfig(this._tracedInvoke, input, mergeConfigs(this.config, config));
76
+ returnValue = await this._callWithConfig(this._tracedInvoke, input, mergedConfig);
76
77
  }
77
78
  else {
78
- returnValue = await this.func(input, mergeConfigs(this.config, config));
79
+ returnValue = await AsyncLocalStorageProviderSingleton.runWithConfig(mergedConfig, async () => this.func(input, mergedConfig));
79
80
  }
80
81
  if (Runnable.isRunnable(returnValue) && this.recurse) {
81
- return await returnValue.invoke(input, config);
82
+ return await AsyncLocalStorageProviderSingleton.runWithConfig(mergedConfig, async () => returnValue.invoke(input, mergedConfig));
82
83
  }
83
84
  return returnValue;
84
85
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@langchain/langgraph",
3
- "version": "0.2.16",
3
+ "version": "0.2.18-rc.0",
4
4
  "description": "LangGraph",
5
5
  "type": "module",
6
6
  "engines": {
@@ -43,7 +43,7 @@
43
43
  "@jest/globals": "^29.5.0",
44
44
  "@langchain/anthropic": "^0.3.0",
45
45
  "@langchain/community": "^0.3.0",
46
- "@langchain/core": "^0.3.10",
46
+ "@langchain/core": "^0.3.14",
47
47
  "@langchain/langgraph-checkpoint-postgres": "workspace:*",
48
48
  "@langchain/langgraph-checkpoint-sqlite": "workspace:*",
49
49
  "@langchain/openai": "^0.3.0",