UNPKG

@langchain/langgraph

Version:

LangGraph

147 lines 5.35 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.ChannelWrite = exports.PASSTHROUGH = exports.SKIP_WRITE = void 0; const runnables_1 = require("@langchain/core/runnables"); const constants_js_1 = require("../constants.cjs"); const utils_js_1 = require("../utils.cjs"); const errors_js_1 = require("../errors.cjs"); exports.SKIP_WRITE = { [Symbol.for("LG_SKIP_WRITE")]: true, }; function _isSkipWrite(x) { return (typeof x === "object" && // eslint-disable-next-line @typescript-eslint/no-explicit-any x?.[Symbol.for("LG_SKIP_WRITE")] !== undefined); } exports.PASSTHROUGH = { [Symbol.for("LG_PASSTHROUGH")]: true, }; function _isPassthrough(x) { return (typeof x === "object" && // eslint-disable-next-line @typescript-eslint/no-explicit-any x?.[Symbol.for("LG_PASSTHROUGH")] !== undefined); } const IS_WRITER = Symbol("IS_WRITER"); /** * Mapping of write channels to Runnables that return the value to be written, * or None to skip writing. */ class ChannelWrite extends utils_js_1.RunnableCallable { constructor(writes, tags) { const name = `ChannelWrite<${writes .map((packet) => { if ((0, constants_js_1._isSend)(packet)) { return packet.node; } else if ("channel" in packet) { return packet.channel; } return "..."; }) .join(",")}>`; super({ ...{ writes, name, tags }, func: async (input, config) => { return this._write(input, config ?? {}); }, }); Object.defineProperty(this, "writes", { enumerable: true, configurable: true, writable: true, value: void 0 }); this.writes = writes; } async _write(input, config) { const writes = this.writes.map((write) => { if (_isChannelWriteTupleEntry(write) && _isPassthrough(write.value)) { return { mapper: write.mapper, value: input, }; } else if (_isChannelWriteEntry(write) && _isPassthrough(write.value)) { return { channel: write.channel, value: input, skipNone: write.skipNone, mapper: write.mapper, }; } else { return write; } }); await ChannelWrite.doWrite(config, writes); return input; } // TODO: Support requireAtLeastOneOf static async doWrite(config, writes) { // validate for (const w of writes) { if (_isChannelWriteEntry(w)) { if (w.channel === constants_js_1.TASKS) { throw new errors_js_1.InvalidUpdateError("Cannot write to the reserved channel TASKS"); } if (_isPassthrough(w.value)) { throw new errors_js_1.InvalidUpdateError("PASSTHROUGH value must be replaced"); } } if (_isChannelWriteTupleEntry(w)) { if (_isPassthrough(w.value)) { throw new errors_js_1.InvalidUpdateError("PASSTHROUGH value must be replaced"); } } } // eslint-disable-next-line @typescript-eslint/no-explicit-any const writeEntries = []; for (const w of writes) { if ((0, constants_js_1._isSend)(w)) { writeEntries.push([constants_js_1.TASKS, w]); } else if (_isChannelWriteTupleEntry(w)) { const mappedResult = await w.mapper.invoke(w.value, config); if (mappedResult != null && mappedResult.length > 0) { writeEntries.push(...mappedResult); } } else if (_isChannelWriteEntry(w)) { const mappedValue = w.mapper !== undefined ? await w.mapper.invoke(w.value, config) : w.value; if (_isSkipWrite(mappedValue)) { continue; } if (w.skipNone && mappedValue === undefined) { continue; } writeEntries.push([w.channel, mappedValue]); } else { throw new Error(`Invalid write entry: ${JSON.stringify(w)}`); } } const write = config.configurable?.[constants_js_1.CONFIG_KEY_SEND]; write(writeEntries); } static isWriter(runnable) { return ( // eslint-disable-next-line no-instanceof/no-instanceof runnable instanceof ChannelWrite || (IS_WRITER in runnable && !!runnable[IS_WRITER])); } static registerWriter(runnable) { return Object.defineProperty(runnable, IS_WRITER, { value: true }); } } exports.ChannelWrite = ChannelWrite; function _isChannelWriteEntry(x) { return (x !== undefined && typeof x.channel === "string"); } function _isChannelWriteTupleEntry(x) { return (x !== undefined && !_isChannelWriteEntry(x) && runnables_1.Runnable.isRunnable(x.mapper)); } //# sourceMappingURL=write.js.map