{"version":3,"file":"interrupt.cjs","names":["AsyncLocalStorageProviderSingleton","GraphValueError","CONFIG_KEY_SCRATCHPAD","CONFIG_KEY_SEND","RESUME","CONFIG_KEY_CHECKPOINT_NS","GraphInterrupt","XXH3"],"sources":["../src/interrupt.ts"],"sourcesContent":["import { AsyncLocalStorageProviderSingleton } from \"@langchain/core/singletons\";\nimport { RunnableConfig } from \"@langchain/core/runnables\";\nimport {\n  BaseCheckpointSaver,\n  type PendingWrite,\n} from \"@langchain/langgraph-checkpoint\";\nimport { GraphInterrupt, GraphValueError } from \"./errors.js\";\nimport {\n  CONFIG_KEY_CHECKPOINT_NS,\n  CONFIG_KEY_SCRATCHPAD,\n  CONFIG_KEY_SEND,\n  CONFIG_KEY_CHECKPOINTER,\n  CHECKPOINT_NAMESPACE_SEPARATOR,\n  RESUME,\n} from \"./constants.js\";\nimport { PregelScratchpad } from \"./pregel/types.js\";\nimport { XXH3 } from \"./hash.js\";\n\n/**\n * Interrupts the execution of a graph node.\n * This function can be used to pause execution of a node, and return the value of the `resume`\n * input when the graph is re-invoked using `Command`.\n * Multiple interrupts can be called within a single node, and each will be handled sequentially.\n *\n * When an interrupt is called:\n * 1. If there's a `resume` value available (from a previous `Command`), it returns that value.\n * 2. Otherwise, it throws a `GraphInterrupt` with the provided value\n * 3. The graph can be resumed by passing a `Command` with a `resume` value\n *\n * Because the `interrupt` function propagates by throwing a special `GraphInterrupt` error,\n * you should avoid using `try/catch` blocks around the `interrupt` function,\n * or if you do, ensure that the `GraphInterrupt` error is thrown again within your `catch` block.\n *\n * @param value - The value to include in the interrupt. This will be available in task.interrupts[].value\n * @returns The `resume` value provided when the graph is re-invoked with a Command\n *\n * @example\n * ```typescript\n * // Define a node that uses multiple interrupts\n * const nodeWithInterrupts = () => {\n *   // First interrupt - will pause execution and include {value: 1} in task values\n *   const answer1 = interrupt({ value: 1 });\n *\n *   // Second interrupt - only called after first interrupt is resumed\n *   const answer2 = interrupt({ value: 2 });\n *\n *   // Use the resume values\n *   return { myKey: answer1 + \" \" + answer2 };\n * };\n *\n * // Resume the graph after first interrupt\n * await graph.stream(new Command({ resume: \"answer 1\" }));\n *\n * // Resume the graph after second interrupt\n * await graph.stream(new Command({ resume: \"answer 2\" }));\n * // Final result: { myKey: \"answer 1 answer 2\" }\n * ```\n *\n * @throws {Error} If called outside the context of a graph\n * @throws {GraphInterrupt} When no resume value is available\n */\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\nexport function interrupt<I = unknown, R = any>(value: I): R {\n  const config: RunnableConfig | undefined =\n    AsyncLocalStorageProviderSingleton.getRunnableConfig();\n  if (!config) {\n    throw new Error(\"Called interrupt() outside the context of a graph.\");\n  }\n\n  const conf = config.configurable;\n  if (!conf) {\n    throw new Error(\"No configurable found in config\");\n  }\n\n  const checkpointer: BaseCheckpointSaver = conf[CONFIG_KEY_CHECKPOINTER];\n  if (!checkpointer) {\n    throw new GraphValueError(\"No checkpointer set\", {\n      lc_error_code: \"MISSING_CHECKPOINTER\",\n    });\n  }\n\n  // Track interrupt index\n  const scratchpad: PregelScratchpad = conf[CONFIG_KEY_SCRATCHPAD];\n  scratchpad.interruptCounter += 1;\n  const idx = scratchpad.interruptCounter;\n\n  // Find previous resume values\n  if (scratchpad.resume.length > 0 && idx < scratchpad.resume.length) {\n    conf[CONFIG_KEY_SEND]?.([[RESUME, scratchpad.resume] as PendingWrite]);\n    return scratchpad.resume[idx] as R;\n  }\n\n  // Find current resume value\n  if (scratchpad.nullResume !== undefined) {\n    if (scratchpad.resume.length !== idx) {\n      throw new Error(\n        `Resume length mismatch: ${scratchpad.resume.length} !== ${idx}`\n      );\n    }\n    const v = scratchpad.consumeNullResume();\n    scratchpad.resume.push(v);\n    conf[CONFIG_KEY_SEND]?.([[RESUME, scratchpad.resume] as PendingWrite]);\n    return v as R;\n  }\n\n  // No resume value found\n  const ns: string[] | undefined = conf[CONFIG_KEY_CHECKPOINT_NS]?.split(\n    CHECKPOINT_NAMESPACE_SEPARATOR\n  );\n\n  const id = ns ? XXH3(ns.join(CHECKPOINT_NAMESPACE_SEPARATOR)) : undefined;\n  throw new GraphInterrupt([{ id, value }]);\n}\n\ntype FilterAny<X> =\n  (<T>() => T extends X ? 1 : 2) extends <\n    T,\n    // eslint-disable-next-line @typescript-eslint/no-explicit-any\n  >() => T extends any ? 1 : 2\n    ? never\n    : X;\n\nexport type InferInterruptInputType<T> = T extends typeof interrupt<\n  infer I,\n  unknown\n>\n  ? I\n  : // eslint-disable-next-line @typescript-eslint/no-explicit-any\n    T extends { [key: string]: typeof interrupt<any, any> }\n    ? { [K in keyof T]: InferInterruptInputType<T[K]> }[keyof T]\n    : unknown;\n\nexport type InferInterruptResumeType<\n  T,\n  TInner = false,\n> = T extends typeof interrupt<never, infer R>\n  ? TInner extends true\n    ? FilterAny<R>\n    : R\n  : // eslint-disable-next-line @typescript-eslint/no-explicit-any\n    T extends { [key: string]: typeof interrupt<any, any> }\n    ? { [K in keyof T]: InferInterruptResumeType<T[K], true> }[keyof T]\n    : unknown;\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AA8DA,SAAgB,UAAgC,OAAa;CAC3D,MAAM,SACJA,2BAAAA,mCAAmC,mBAAmB;AACxD,KAAI,CAAC,OACH,OAAM,IAAI,MAAM,qDAAqD;CAGvE,MAAM,OAAO,OAAO;AACpB,KAAI,CAAC,KACH,OAAM,IAAI,MAAM,kCAAkC;AAIpD,KAAI,CADsC,KAAA,yBAExC,OAAM,IAAIC,eAAAA,gBAAgB,uBAAuB,EAC/C,eAAe,wBAChB,CAAC;CAIJ,MAAM,aAA+B,KAAKC,kBAAAA;AAC1C,YAAW,oBAAoB;CAC/B,MAAM,MAAM,WAAW;AAGvB,KAAI,WAAW,OAAO,SAAS,KAAK,MAAM,WAAW,OAAO,QAAQ;AAClE,OAAKC,kBAAAA,mBAAmB,CAAC,CAACC,kBAAAA,QAAQ,WAAW,OAAO,CAAiB,CAAC;AACtE,SAAO,WAAW,OAAO;;AAI3B,KAAI,WAAW,eAAe,KAAA,GAAW;AACvC,MAAI,WAAW,OAAO,WAAW,IAC/B,OAAM,IAAI,MACR,2BAA2B,WAAW,OAAO,OAAO,OAAO,MAC5D;EAEH,MAAM,IAAI,WAAW,mBAAmB;AACxC,aAAW,OAAO,KAAK,EAAE;AACzB,OAAKD,kBAAAA,mBAAmB,CAAC,CAACC,kBAAAA,QAAQ,WAAW,OAAO,CAAiB,CAAC;AACtE,SAAO;;CAIT,MAAM,KAA2B,KAAKC,kBAAAA,2BAA2B,MAAA,IAEhE;AAGD,OAAM,IAAIC,eAAAA,eAAe,CAAC;EAAE,IADjB,KAAKC,aAAAA,KAAK,GAAG,KAAA,IAAoC,CAAC,GAAG,KAAA;EAChC;EAAO,CAAC,CAAC"}