LangChain V1.1 & V1.2 双版本深度解读:看 Profile 抽象如何重塑中间件生态
📅 2025 年 11 月 25 日 V1.1 发布,2025 年 12 月 15 日 V1.2 紧随其后。两个月两次发版,LangChain 团队究竟在下怎样一盘棋?
LangChain 在 V1.0 正式版发布后的短短两个月内,密集推出了 V1.1 和 V1.2 两个版本。与其说是"功能更新",不如说是一次设计哲学的落地——围绕"模型 Profile"这一核心抽象,把原本散落在各处的中间件、策略、能力开关统统串了起来。
如果你最近打开 LangChain 文档,可能会发现一些熟悉又陌生的 API:.profile、ProviderStrategy、tool(extras=...)、strict=True……它们都不是凭空出现的,而是同一套思路在不同位置的体现。
这篇文章会带你:
- 用一张图看清新版本之间的脉络;
- 拆解 Profile 抽象到底解决了什么问题;
- 逐项解读 V1.1 的 6 个更新与 V1.2 的 2 个更新;
- 总结 LangChain 团队在这次迭代中体现的设计原则;
- 给出可落地的迁移建议。
一、先看整体:版本迭代脉络
我们用一张时间线图把这次迭代的节奏拉直:
从节奏上能看出,V1.1 是结构性更新(引入核心抽象),V1.2 是能力性更新(在新抽象基础上做适配)。这种"先立骨架、再填血肉"的发版节奏,是非常健康的开源协作模式。
如果再用一张思维导图把两个版本的所有更新点铺开,就更直观了:
看完这两张图,你应该已经能在脑子里勾勒出这次更新的主干——所有更新都围绕"模型能力"这条线展开。下面我们逐个拆解。
二、核心抽象:什么是"模型 Profile"?
V1.1 最重要的变化,是引入了Profile——一个用来描述"当前模型能做到什么"的统一数据结构。
2.1 为什么需要 Profile?
在 V1.0 时代,框架要做"上下文感知"的相关功能时,往往需要开发者手动指定模型的上下文窗口、是否支持图像输入、是否支持结构化输出等等。这带来了两个问题:
- 硬编码满天飞:换模型就要改代码;
- 能力判断不准:框架并不知道你用的模型到底支不支持某个特性,只能"乐观尝试",出错再补救。
Profile 的引入正是为了把"能力声明"和"模型调用"解耦。来看一个最小例子:
from langchain import init_chat_model
model = init_chat_model(
"claude-sonnet-4-5-20250929",
temperature=0.7,
)
print(model.profile)
输出大致如下:
{
"max_input_tokens": 200000,
"max_output_tokens": 64000,
"image_inputs": True,
"audio_inputs": False,
"video_inputs": False,
"image_outputs": False,
"audio_outputs": False,
"video_outputs": False,
"reasoning_output": True,
"tool_calling": True,
"image_url_inputs": True,
"pdf_inputs": True,
"pdf_tool_message": True,
"image_tool_message": True,
"structured_output": False,
}
想看全行业的模型能力数据?官方推荐 https://models.dev。
2.2 Profile 的类图视角
用一张 UML 类图把 Profile 在框架里的位置画出来:
可以看到,ChatModel 始终持有一个 Profile,框架其他模块只需要问"你 profile 里有什么",就能决定该用什么策略。
2.3 自定义 Profile
当你使用本地部署或私有模型时,官方不一定收录了你的 profile,可以手动指定:
custom_profile = {
"max_input_tokens": 200000,
"max_output_tokens": 64000,
"structured_output": True,
# ...
}
model = init_chat_model(
"...", # provider:model 形式
profile=custom_profile
)
2.4 Profile 驱动的能力闭环
Profile 出现后,中间件、策略、模态控制等模块都从"硬编码参数"变成了"读 profile":
一句话总结:Profile 是模型能力的"身份证",框架里的所有智能决策都靠它做。
三、LangChain V1.1 的 6 项更新
V1.1 一口气带来了 6 个重要变化,下面按"使用频率"由高到低排序。
3.1 Summarization 中间件:上下文感知的智能摘要
老版本里的 SummarizationMiddleware 触发条件相对固定,V1.1 改成了灵活触发点,完全依据 profile 中的 max_input_tokens 决定何时该"压缩历史"。
from langchain.agents import create_agent
from langchain.agents.middleware import SummarizationMiddleware
agent = create_agent(
model=model,
tools=[internet_search, calculate],
middleware=[
SummarizationMiddleware(
model="gpt-4o-mini",
trigger=("fraction", 0.8), # 占用 80% 窗口时触发
keep=("fraction", 0.3), # 摘要后保留 30% 最新消息
),
],
)
把它画成流程图更清晰:
对于长会话场景,这是质的提升——你不再需要写复杂的"自定义消息裁剪"逻辑。
3.2 Structured Output:自动推断策略
这是 V1.1 最香的功能之一。结构化输出不再是"调用方自己挑 strategy",而是根据 profile 自动推断。
第一步:定义格式
from pydantic import BaseModel, Field
class ContactInfo(BaseModel):
"""个人联系方式格式"""
name: str = Field(description="姓名")
email: str = Field(description="个人邮箱地址")
phone: str = Field(description="个人电话号码")
第二步:根据模型能力自动选择策略
整个决策逻辑用一张图就能讲清楚:
Provider Strategy(推荐)
agent = create_agent(
model="gpt-5",
response_format=ContactInfo, # 直接传 Pydantic 类
)
result = agent.invoke({
"messages": [{
"role": "user",
"content": """从以下信息中提取联系人信息:
张强,zhang@example.com,(0411) 123-4567"""
}]
})
print(result["structured_response"])
# name='张强' email='zhang@example.com' phone='(0411) 123-4567'
Tool Strategy(兼容方案)
from langchain.agents.structured_output import ToolStrategy
agent = create_agent(
model=model, # 不支持原生结构化输出
response_format=ToolStrategy(ContactInfo),
)
💡 官方建议优先使用 Provider Strategy,因为它走模型原生的 JSON Schema 通道,比"工具调用模拟"更稳定、延迟更低。
3.3 SystemMessage:直接实例化传入
V1.1 之后,SystemMessage 不再需要手动拼到 messages 列表里,可以直接实例化传给 Agent:
from langchain.messages import SystemMessage
agent = create_agent(
model=model,
system_prompt=SystemMessage(content="你是一个严谨的翻译助手..."),
)
写法更干净,也避免了"字符串 vs 消息对象"混用的尴尬。
3.4 Model Retry 中间件:模型调用层面的重试
之前我们熟悉的 Tool Retry 中间件是给"工具调用失败"准备的;V1.1 新增的 Model Retry 则负责模型调用本身的失败(比如临时网络抖动、限流、5xx 等)。
from langchain.agents.middleware import ModelRetryMiddleware
agent = create_agent(
model=model,
middleware=[
ModelRetryMiddleware(
max_retries=3,
backoff="exponential",
)
],
)
和 Tool Retry 的 API 形态保持一致,降低了学习成本。
3.5 Content Moderation 中间件:内容安全
V1.1 把 OpenAI Moderation API 包装成了中间件,可以在 Agent 出口处自动审核内容:
from langchain.agents.middleware import ContentModerationMiddleware
agent = create_agent(
model=model,
middleware=[
ContentModerationMiddleware(
provider="openai",
categories=["hate", "violence", "self-harm"],
)
],
)
🛡️ 适用于 C 端产品、需要合规审计的场景。
3.6 Profile 的 3 大作用(小结)
把 Profile 对框架的"驱动作用"再总结一次:
- Summarization 可以根据模型的上下文窗口大小触发摘要;
create_agent中的结构化输出策略可以被自动推断;- 模型输入可以根据支持的模态和最大输入标记进行控制匹配。
四、LangChain V1.2 的 2 项更新
V1.2 体量不大,但每一项都打在了"框架适配多厂商能力"的痛点上。
4.1 工具的 extra 参数:兼容各厂商私有工具
过去,LangChain 工具装饰器只能定义"通用工具"。如果想用 Anthropic 的内置工具(比如 tool search、文件读取),得绕一圈。
V1.2 引入了 extras 参数,可以把供应商专用参数直接透传进去:
from anthropic.types.beta import BetaToolSearchToolRegex20251119Param
from langchain_anthropic import ChatAnthropic
from langchain.tools import tool
@tool(extras={"defer_loading": True}) # 透传 Anthropic 专用参数
def get_weather(location: str, unit: str = "fahrenheit") -> str:
"""Get the current weather for a location.
Args:
location: City name
unit: Temperature unit (celsius or fahrenheit)
"""
return f"Weather in {location}: Sunny"
它解决的是这样一个问题:
核心理念:通用能力抽象在 LangChain 层,厂商特有能力通过 extras 透传——既保留了抽象,又不失灵活性。
4.2 结构化输出的 strict 策略
V1.2 给 ProviderStrategy 加了一个 strict 参数,开启后强制模型严格遵循 schema:
agent = create_agent(
model="gpt-5",
response_format=ProviderStrategy[ContactInfo](ContactInfo, strict=True),
)
它和"严格模式"的关系是:
⚠️ 注意:
strict=True通常意味着 token 消耗略高、延迟略大,但换来的是确定性,适合做合同抽取、表单填写等容错极低的场景。
五、设计哲学:为什么是"加法"而不是"改法"?
LangChain 团队这次迭代非常克制,几乎没有破坏性改动。背后的两条核心思想是:
- 优先拓展、减少修改 —— 遵循 OCP(开闭原则),用 Profile 这种新抽象承接能力,新功能以"中间件/策略"的形式外挂;
- 尽可能提升对各厂商独特内容的适配 —— 用
extras、strict这种"小开口"来对接厂商私有特性,避免对核心 API 做硬绑定。
用一张对比图能直观感受到两种思路的差异:
对于应用层开发者来说,这意味着:升级到 V1.1/V1.2 大概率是"无痛"的,只需在合适的位置加上 profile=、extras=、strict=True 等参数即可。
六、迁移决策树
如果你正打算把项目升级到 V1.1/V1.2,这张决策图可以帮你快速判断该改哪些地方:
七、实用建议清单
最后,把这次更新的所有"最佳实践"提炼成 4 条可执行建议:
- 优先用
.profile读取模型能力,避免在代码里硬编码max_input_tokens、模态等参数; - 结构化输出默认让框架根据 profile 自动选择策略;要"绝对稳定"就显式使用
ProviderStrategy并开启strict=True; - 切换模型供应商时使用
init_chat_model("provider:model"),让中间件自动适配; - 本地/私有模型必须显式声明
profile=,否则 Summarization、结构化输出等中间件可能不会按预期工作。
八、写在最后
两个月两次发版,LangChain 团队没有去做"大而全的重构",而是用一个轻巧的 Profile 抽象作为支点,把 Summarization、Structured Output、Content Moderation、Model Retry 等能力像乐高一样串起来,再用 V1.2 的 extras 和 strict 把"厂商差异"和"严格性"这两个长期痛点稳稳接住。
这种"用抽象换扩展性"的思路,比任何单点功能更新都值得学习。下一次当你面对一个不断扩张的系统时,不妨也想想:有没有一个"Profile"式的核心抽象,能把所有可变量收敛到一处?
如果你想跟进 LangChain 的最新动态,建议收藏两个入口:
- 📦 官方文档:https://python.langchain.com
- 📊 模型能力数据:https://models.dev
💬 读完这篇博客,你对 V1.1/V1.2 的设计思路是不是更清晰了?如果你在升级过程中踩到了坑,或者有更好的实践技巧,欢迎在评论区分享,我们一起把这条升级路径走得更顺。
—— 整理自 LangChain V1.1 / V1.2 版本更新要点 · 2026-08-02