01. Runnable 封装记忆组件思路

在 Runnable 链应用中,可以考虑将 memory 通过 config+configurable 的形式传递给链,在链的执行函数(invoke、stream 等)中可以通过第 2 个参数获取到对应的 memory 实例,从而获取到记忆历史,并且为链添加 on_end 函数,即可获取到整个链的输入与输出,在 on_end 生命周期中将对话信息存储到记忆系统中。

运行流程如下

后端优化后的核心代码

@classmethod

def _load_memory_variables(cls, input: Dict[str, Any], config: RunnableConfig) -> Dict[str, Any]:

    """加载记忆变量"""

    configurable = config.get("configurable", {})

    configurable_memory = configurable.get("memory", None)

    if configurable_memory is not None and isinstance(configurable_memory, BaseMemory):

        return configurable_memory.load_memory_variables(input)

    return {"history": []}

@classmethod

def _save_context(cls, run: Run, config: RunnableConfig) -> None:

    configurable = config.get("configurable", {})

    configurable_memory = configurable.get("memory", None)

    if configurable_memory is not None and isinstance(configurable_memory, BaseMemory):

        configurable_memory.save_context(run.inputs, run.outputs)

def debug(self, app_id: UUID):

    """聊天接口"""

    ...

    chain = (

        (RunnablePassthrough.assign(

            history=RunnableLambda(self._load_memory_variables) | itemgetter("history")

        ) | prompt | llm | StrOutputParser()).

        with_listeners(on_end=self._save_context)

    )

    # 5.调用链生成内容

    chain_input = {"query": req.query.data}

    content = chain.invoke(chain_input, config={"configurable": {"memory": memory}})

...

02. Runnable 其他细节功能探索

LCEL 表达式与 Runnable 其他细节功能:

  1. 官方文档:LangChain Expression Language Cheatsheet | 🦜️🔗 LangChain

Logo

Agent 垂直技术社区,欢迎活跃、内容共建。

更多推荐