LangChain 是 2023 年以来 AI 工程界最有争议的框架之一 —— 它把 LLM 应用开发从"裸调 API"提升到"组件化",但也因为过度抽象、文档跟不上、API 频繁改动被开发者抱怨。这篇文章不站队,而是讲清楚 LangChain / LlamaIndex 实际能解决什么问题、什么场景该用、什么场景该绕开,以及 2025 年最稳的使用姿势。
LangChain 到底提供什么
核心是把 LLM 应用拆成可组合的组件:
- Models:统一接口包装各家 LLM(OpenAI、Anthropic、本地模型),换厂商只改一行。
- Prompts:模板化的 prompt 管理。
- Output Parsers:把 LLM 输出解析成结构化对象。
- Retrievers:统一的检索接口(向量库、Elasticsearch、Web 搜索)。
- Chains:把多个调用串成一个流程。
- Agents:基于 ReAct / Plan-and-Execute 的 Agent 框架。
- Memory:对话历史管理。
- Callbacks:运行时回调,做监控、日志、缓存。
这套组件抽象在"快速搭原型"时威力很大,几行代码就能搞一个 RAG 或 Agent。
LCEL:LangChain Expression Language
LangChain 0.1+ 引入的声明式管道语法,用 | 操作符串联组件:
from langchain_core.prompts import ChatPromptTemplate
from langchain_openai import ChatOpenAI
from langchain_core.output_parsers import StrOutputParser
prompt = ChatPromptTemplate.from_template("用 50 字解释什么是 {concept}")
model = ChatOpenAI(model="gpt-4o")
parser = StrOutputParser()
chain = prompt | model | parser
result = chain.invoke({"concept": "websocket"})
# "WebSocket 是一种基于 TCP 的全双工通信协议..."
# 流式输出
for chunk in chain.stream({"concept": "kubernetes"}):
print(chunk, end="", flush=True)
# 批量
results = chain.batch([{"concept": "redis"}, {"concept": "kafka"}])
# 异步
result = await chain.ainvoke({"concept": "rabbitmq"})
LCEL 的好处:同一个 chain 自动支持同步、异步、流式、批量、并发。不用自己包装 4 种调用方式。
构建 RAG:LangChain 风格
from langchain_community.document_loaders import PyPDFLoader
from langchain_text_splitters import RecursiveCharacterTextSplitter
from langchain_community.vectorstores import Chroma
from langchain_openai import OpenAIEmbeddings, ChatOpenAI
from langchain_core.prompts import ChatPromptTemplate
from langchain_core.runnables import RunnablePassthrough
# 索引
docs = PyPDFLoader("manual.pdf").load()
chunks = RecursiveCharacterTextSplitter(chunk_size=500, chunk_overlap=50).split_documents(docs)
vectorstore = Chroma.from_documents(chunks, OpenAIEmbeddings())
retriever = vectorstore.as_retriever(search_kwargs={"k": 4})
# Chain
prompt = ChatPromptTemplate.from_template("""
基于以下资料回答问题。资料中没有的不要编。
资料:
{context}
问题:{question}
""")
def format_docs(docs):
return "\n\n".join(d.page_content for d in docs)
chain = (
{"context": retriever | format_docs, "question": RunnablePassthrough()}
| prompt
| ChatOpenAI(model="gpt-4o")
| StrOutputParser()
)
answer = chain.invoke("如何配置 HTTPS?")
20 行实现一个能跑的 RAG。但生产级 RAG 还需要 reranker、混合检索、query 改写 —— LangChain 都有现成组件,堆起来就行。
LlamaIndex:专注数据接入
LlamaIndex(原 GPT-Index)和 LangChain 定位略有不同 —— 它更专注"如何把企业数据接入 LLM":
- 更多文档加载器(Notion、Slack、Confluence、Jira、Salesforce 等)。
- 更精细的索引结构(Tree Index、List Index、Knowledge Graph Index、Vector Index)。
- 更强的 RAG 优化(Auto Retrieval、Sub-Question Query、Sentence Window)。
from llama_index.core import VectorStoreIndex, SimpleDirectoryReader
from llama_index.llms.openai import OpenAI
from llama_index.embeddings.openai import OpenAIEmbedding
# 简单到一行
documents = SimpleDirectoryReader("./docs").load_data()
index = VectorStoreIndex.from_documents(documents)
query_engine = index.as_query_engine(llm=OpenAI(model="gpt-4o"))
response = query_engine.query("如何配置 HTTPS?")
选型:纯 RAG 场景或要接入很多奇怪数据源 → LlamaIndex;复杂 Agent / 工作流 → LangChain / LangGraph。当然两者也可以一起用 —— LlamaIndex 做检索层,LangChain 做编排层。
LangGraph:状态化的 Agent 编排
LangChain 团队 2024 年推出 LangGraph,专门做 Agent / 工作流编排。它把流程建模成有向图,每个节点是 LLM 调用或工具,节点间有条件边:
from langgraph.graph import StateGraph, END
from typing import TypedDict
class State(TypedDict):
question: str
docs: list
answer: str
needs_more_info: bool
# 节点
def retrieve(state):
docs = retriever.invoke(state["question"])
return {"docs": docs}
def grade_docs(state):
# 用 LLM 判断 docs 是否足够回答
needed = grade_chain.invoke({"question": state["question"], "docs": state["docs"]})
return {"needs_more_info": needed}
def transform_query(state):
new_q = rewrite_chain.invoke({"question": state["question"]})
return {"question": new_q}
def generate(state):
answer = answer_chain.invoke({"question": state["question"], "docs": state["docs"]})
return {"answer": answer}
# 构图
workflow = StateGraph(State)
workflow.add_node("retrieve", retrieve)
workflow.add_node("grade", grade_docs)
workflow.add_node("transform", transform_query)
workflow.add_node("generate", generate)
workflow.set_entry_point("retrieve")
workflow.add_edge("retrieve", "grade")
# 条件边:根据状态决定下一步
workflow.add_conditional_edges(
"grade",
lambda state: "transform" if state["needs_more_info"] else "generate",
{"transform": "transform", "generate": "generate"}
)
workflow.add_edge("transform", "retrieve") # 循环回检索
workflow.add_edge("generate", END)
app = workflow.compile()
result = app.invoke({"question": "如何配置 HTTPS?"})
这是Self-Correcting RAG(自纠错 RAG)的实现 —— 检索后判断是否够答,不够就改写 query 重新检索。LangGraph 把这种带状态、有循环、有分支的 Agent 流程表达得清晰。
LangSmith:观测性
LangChain 自家的可观测性平台。运行时自动记录每个组件的输入、输出、耗时、token、错误。生产级 LLM 应用必备工具:
import os
os.environ["LANGCHAIN_TRACING_V2"] = "true"
os.environ["LANGCHAIN_API_KEY"] = "..."
os.environ["LANGCHAIN_PROJECT"] = "my-app"
# 之后所有 chain 调用自动上传到 LangSmith
result = chain.invoke({"question": "..."})
# 在 LangSmith Web UI 看到完整 trace
LangSmith 还提供数据集管理、自动评估、A/B 测试、提示词版本管理。对生产应用极其有用。竞品:Weave(Weights & Biases)、Helicone、Phoenix。
LangChain 的争议
抱怨 1:过度抽象
很多场景只是想"调一下 OpenAI",LangChain 让你先理解 Runnable、LCEL、Callback、Memory、Tool... 学习曲线陡。
对策:简单调用直接用厂商 SDK(openai、anthropic),复杂场景才上 LangChain。
抱怨 2:API 频繁变动
0.0.x → 0.1 → 0.2 → 0.3 几次大改,网上 tutorials 经常和当前版本不一致。
对策:看官方 docs 当下版本的写法,GitHub issues 里搜最近 30 天的讨论。
抱怨 3:性能开销
LangChain 在每个组件外都包了一层,callback、tracing、metadata 收集让简单调用比裸调慢 10-30%。
对策:高 QPS 场景关闭不必要的 callback,或者绕开 LangChain 直接调。
什么时候用,什么时候不用
用 LangChain
- 需要快速搭原型,组件能拿现成的。
- 要支持多家 LLM 切换。
- 需要复杂编排(Multi-Agent、Self-Correcting、并行分支)。
- 需要 LangSmith 这样的可观测平台。
不用
- 简单的"调 GPT 写邮件"—— 直接用 openai SDK 更简单。
- 极致性能场景(实时对话、低延迟)—— 抽象层是瓶颈。
- 团队成员都不熟 LangChain,引入学习成本超过收益。
替代方案
2024-2025 年出现了不少 LangChain 的"轻量替代":
- Instructor:专注结构化输出,极简。
- Marvin:类似 Instructor,把 LLM 当函数调。
- DSPy(Stanford):把 prompt 当作"可优化代码",自动调优 few-shot 例子。
- Pydantic AI:Pydantic 团队出品,类型安全 + 简单 API。
- Vercel AI SDK:前端工程师友好,边缘部署友好。
不同场景选不同工具。LangChain 适合"大而全",这些替代品适合"专而精"。
工程心得
1. Prompt 和 Chain 分离
# 不好:prompt 写死在代码里
prompt = ChatPromptTemplate.from_template("用 50 字回答 {q}")
# 好:prompt 集中管理,可以版本化
from langchain_core.prompts import load_prompt
prompt = load_prompt("./prompts/answer_v3.yaml")
2. 给 chain 起名字
chain = (prompt | model | parser).with_config({"run_name": "answer_chain"})
# LangSmith 里能看到这个名字,debug 更清晰
3. 错误处理
chain = (prompt | model | parser).with_retry(stop_after_attempt=3)
# 或者 fallback 到备用模型
chain = primary_chain.with_fallbacks([backup_chain])
LangChain 之外:Vercel AI SDK
2025 年前端工程师用得最多的 LLM 工具包之一。专注 streaming、React/Next.js 集成、边缘部署:
// API 路由
import { streamText } from 'ai';
import { openai } from '@ai-sdk/openai';
export async function POST(req) {
const { messages } = await req.json();
const result = await streamText({
model: openai('gpt-4o'),
messages,
tools: {
getWeather: {
description: '查询天气',
parameters: z.object({ city: z.string() }),
execute: async ({ city }) => { /* ... */ }
}
}
});
return result.toDataStreamResponse();
}
// React 组件
import { useChat } from 'ai/react';
export default function Chat() {
const { messages, input, handleSubmit } = useChat();
return (
<form onSubmit={handleSubmit}>
{messages.map(m => <div key={m.id}>{m.content}</div>)}
<input value={input} />
</form>
);
}
Vercel AI SDK 的卖点是"类型安全 + 流式 + 边缘友好",写聊天应用比 LangChain 简单得多。但纯后端复杂业务还是 LangChain / LlamaIndex 更全。
DSPy:把 Prompt 当代码自动优化
Stanford 出品的革命性框架。核心理念:你定义"任务签名"(输入 / 输出 / 步骤),DSPy 自动生成和优化 prompt。
import dspy
# 定义任务签名
class QA(dspy.Signature):
"""根据上下文回答问题"""
context = dspy.InputField()
question = dspy.InputField()
answer = dspy.OutputField(desc="简洁的回答")
# 定义流程
class RAG(dspy.Module):
def __init__(self):
self.retrieve = dspy.Retrieve(k=3)
self.generate = dspy.ChainOfThought(QA)
def forward(self, question):
context = self.retrieve(question).passages
return self.generate(context=context, question=question)
# 自动优化:DSPy 会用 few-shot 示例和评估指标自动调 prompt
optimizer = dspy.BootstrapFewShot(metric=accuracy_metric)
optimized = optimizer.compile(RAG(), trainset=train_data)
DSPy 解决的痛点:prompt 调参太靠玄学。它把这个过程数据化、可优化。学习成本略高,但对长期维护的 LLM 应用非常有价值。
写在最后
LangChain / LlamaIndex / LangGraph 这套生态,代表了"把 LLM 当组件"的工程化思路。它有抽象成本,但当你的应用真的开始处理"多模型、多工具、多步骤、多分支、长会话"时,这些抽象省下来的开发时间会让你回头感谢它。
给一个判断标准:项目的复杂度 = 框架引入的合理性。一两天的 demo 不需要 LangChain,几个月的 SaaS 产品几乎必须用。具体到选型,2025 年的现状:结构化输出用 Instructor,纯 RAG 用 LlamaIndex,复杂 Agent 用 LangGraph,前端集成用 Vercel AI SDK,可观测都用 LangSmith。这套组合在大多数场景下都够用且不踩坑。
—— 别看了 · 2026