LangChain 與 CrewAI:與 OpenRouter 原生路由的協調比較
LangChain vs CrewAI: Orchestration Compared to OpenRouter-Native Routing
本文說明 LangChain 與 CrewAI 在多模型協調方面的差異,並示範如何將 OpenRouter 原生路由與這兩個框架結合。
- 三層架構:工作流協調、模型路由、供應商路由。
文章說明多模型協調的三層架構,並示範如何將 OpenRouter 與 LangChain 或 CrewAI 結合,對構建可擴充的 LLM 工作流十分實用。
你在工作流程中需要多於一個模型。一個成本較低的模型處理例行呼叫,較強的模型處理困難的任務。像 LangChain 與 CrewAI 的代理框架是構建此功能的一種方式。兩者都提供協調層,但組織方式不同。LangChain 的執行環境 LangGraph 為你提供明確的狀態與控制流程。CrewAI 則以角色為基礎的代理與事件驅動流程來組織工作。
兩個框架在你構建具備規劃、保持狀態、呼叫工具或委派工作功能的代理時都很有幫助。若你只需要為每一步選擇模型並在失敗時回退,完整的協調框架會加入你不會使用的部份。
本文比較 LangChain 與 LangGraph、CrewAI,以及 OpenRouter 原生路由,依各自執行的工作。它展示了直接對 OpenRouter 寫出的相同兩步驟流程以及通過 LangChain 寫出的流程,說明我們的 Agent SDK 位於兩者之間的位置,並說明如何在需要同時使用協調與路由時,將 OpenRouter 放在任一框架之下。
TL;DR
- 多模型協調包含三個層次。工作流程協調涵蓋規劃、狀態、記憶與委派。模型路由是為一次呼叫選擇模型並在返回錯誤時回退。供應商路由則是選擇哪個供應商端點提供你選擇的模型。
- LangGraph 與 CrewAI 進行工作流程協調。OpenRouter 處理模型路由與供應商路由。兩者互不取代。
- OpenRouter 的
models引數是一個有序的回退列表。當第一個模型返回錯誤時,我們嘗試下一個。回退是錯誤驅動的,並不評估答案品質。 - 我們的 Agent SDK 處理中間情境,即帶驗證、串流與停止條件的有界多輪工具迴圈,且不使用持久化圖或基於角色的工作團隊。
- LangChain 擁有專用的
ChatOpenRouter整合,CrewAI 透過其LLM類別將 OpenRouter 作為供應商進行檔案說明。你可以保留任一框架的協調功能,並將 OpenRouter 作為底層模型層使用。
三層共稱為一個名稱
「多模型協調」這個詞涵蓋三個不同的決策。將它們分開可以縮短框架比較。
工作流程協調 是規劃、狀態、記憶與委派。你將任務拆分為步驟,跨回合與跨執行保持狀態,暫停以供人類審查,並將子任務交給其他代理。LangGraph 與 CrewAI 為此層設計。
模型路由 是選擇哪個模型處理特定呼叫,以及該模型返回錯誤時的處理方式。OpenRouter 的 models 引數在一個請求欄位中處理此問題。
供應商路由 是選擇哪個供應商端點提供你已選擇的模型。OpenRouter 上的許多模型由多個供應商提供。對每個請求,我們在符合條件的供應商中選擇,且對包含工具的請求,Auto Exacto 會依照工具呼叫效能重新排序這些供應商。供應商路由永遠不會改變你所要求的模型。
一個工作流程可能需要三者。規劃邏輯決定下一步,模型路由決定使用哪個模型,供應商路由決定哪個端點提供該模型。你不需要第一層就能得到後兩層。models 列表和若干 if 陳述式即可在沒有代理框架的情況下在模型之間進行路由。
LangChain 與 LangGraph
LangChain 目前的檔案說明有兩個不同角色的產品。LangChain 是代理框架,提供模型、工具與代理迴圈的抽象與整合。LangGraph 是其底層的低階協調執行環境,著重於耐久執行、串流、人機互動與持久化。你可以不使用 LangChain 直接使用 LangGraph,而 LangChain 的預建代理則執行於 LangGraph 上。
LangGraph 將工作流程建模為節點圖。你可以在同一圖中混合使用決定性、手動編碼的步驟與模型驅動的步驟。持久化由兩個元件提供。checkpointer 會為執行緒儲存圖狀態,提供對話連續性、容錯、時間旅行,以及人機審查的基礎。store 則將應用資料儲存在圖狀態之外,以實現長期、跨執行緒的記憶。interrupt() 函式會在節點的任何位置暫停執行,透過 checkpointer 儲存狀態,並等待你以 Command 重新啟動,讓人員可以在執行繼續前審核、編輯或拒絕該步驟。
這種控制的代價是你必須自行描述控制流程。每個節點、邊、狀態列位、checkpointer 與中斷都是你編寫並維護的程式碼。若你需要一個多步驟管線,且每個節點都可檢查與可續行,LangGraph 能提供結構;若你只是需要模型呼叫並具備回退功能,那麼它已超出需求。
CrewAI
CrewAI 的檔案說明瞭兩個基礎構件。Crew 是代理團隊,每個代理都有角色、目標與背景故事,並負責執行指定任務。Crew 以順序流程執行任務,任務輸出成為下一個任務的上下文;或以階層流程執行,管理模型或管理代理負責指派與協調任務。當 allow_delegation 啟用時,代理可相互委派;每個代理都有一個 max_iter 限制,預設為 20,並可選擇性設定 max_execution_time。
Flows 是環繞 Crew 的結構化、事件驅動層。Flow 定義步驟、在步驟間流動的狀態,以及控制流程,包括條件邏輯、迴圈與分支。每個 Flow 例項攜帶一個唯一 ID 的狀態物件,並在執行期間持久化。CrewAI 的說明將 Flow 視為應用的骨幹,而 Crew 為 Flow 內的工作單元。
CrewAI 的模型更像是任務描述,而非圖結構定義。你投入更多精力於角色、目標與任務字串,較少在節點連結上。這與 LangGraph 的不同取捨,而非其縮小版。Crew 讓代理自行決定完成任務的方式,Flow 則是你重新掌握控制權的地方。
Comparison
| LangChain and LangGraph | CrewAI | OpenRouter direct | |
|---|---|---|---|
| Built for | 以圖為基礎的協調,具備明確的狀態、持久化與人機審查 | 以角色為基礎的代理團隊,嵌入事件驅動的 Flow | 每次呼叫選擇模型、錯誤驅動的回退與供應商路由 |
| 多模型支援 | 是,節點或代理各自擁有一個模型物件 | 是,每個代理、Crew 或管理者各自擁有一個 LLM | 是,每個請求都有一個 models 列表 |
| 規劃、記憶與委派 | 是,明確於圖、checkpointer 與 store | 是,透過代理、流程與 Flow 狀態 | 否,僅提供路由 |
| 串流 | 是 | 是,在 Crew 級別使用 stream=True | 是,每個請求 |
| 人機審查 | interrupt() 伴隨 checkpointer | 由你撰寫的 Flow 邏輯 | 未提供 |
| 你撰寫的內容 | 節點、邊、狀態模式與持久化設定 | 代理、任務、Crew 與 Flow 定義 | 請求主體 |
OpenRouter 原生路由
“Native” 這裡指的是不使用任何框架。你會對 https://openrouter.ai/api/v1/chat/completions 傳送請求,並在 models 引數中以優先順序列出你的模型,剩餘流程由我們處理。若第一個模型回傳錯誤,我們會嘗試列表中的下一個模型。預設情況下,任何錯誤都能觸發回退,包括上下文長度驗證錯誤、過濾模型的審核標記、速率限制以及停機。若回退模型也回傳錯誤,我們將回傳該錯誤。請求的價格以最終提供服務的模型計算,回應中的 model 欄位會告訴你是哪一個模型。
回退機制會對錯誤作出反應。它不會評估第一個模型的答案是否正確。若你想讓更強大的模型審核較弱模型的輸出,那是你程式碼中的第二個步驟,而非 models 列表所能做到的。
以兩步驟流程為例,先用一個模型草擬,然後用另一個模型審核草稿;若第一個模型回傳錯誤,兩步驟皆會回退。直接針對 OpenRouter 寫成,這樣就只需要一個函式和兩個 models 列表。
import os
import requests
def route(models: list[str], prompt: str) -> tuple[str, str]:
response = requests.post(
"https://openrouter.ai/api/v1/chat/completions",
headers={"Authorization": f"Bearer {os.environ['OPENROUTER_API_KEY']}"},
json={"models": models, "messages": [{"role": "user", "content": prompt}]},
timeout=120,
)
response.raise_for_status()
body = response.json()
return body["choices"][0]["message"]["content"], body["model"]
draft, draft_model = route(
["anthropic/claude-sonnet-5", "openai/gpt-5.6-sol"],
"Draft a one-paragraph summary of what a model fallback list does.",
)
review, review_model = route(
["openai/gpt-5.6-sol", "anthropic/claude-sonnet-5"],
f"Review this draft for accuracy and suggest one improvement:\n\n{draft}",
)
print(f"draft by {draft_model}, review by {review_model}")
print(review)若要將某一步驟送至不同模型,你只需更改列表。由於我們的 API 相容 OpenAI,所有聊天模型都可使用相同的聊天完成請求格式,而模型變更只需改變一個字串。服務其他端點的模型,例如嵌入、影片、文字轉語音或語音轉文字,則使用各自的請求格式。
同樣的流程在 LangChain 中使用專用的 ChatOpenRouter 模型類別。你為每一步建立一個模型物件,並用 LangChain 的 with_fallbacks 包裝每個物件,使失敗的呼叫會重試下一個模型物件,最後透過 invoke 呼叫結果。
from langchain_openrouter import ChatOpenRouter
drafter = ChatOpenRouter(model="anthropic/claude-sonnet-5").with_fallbacks(
[ChatOpenRouter(model="openai/gpt-5.6-sol")]
)
reviewer = ChatOpenRouter(model="openai/gpt-5.6-sol").with_fallbacks(
[ChatOpenRouter(model="anthropic/claude-sonnet-5")]
)
draft = drafter.invoke("Draft a one-paragraph summary of what a model fallback list does.")
review = reviewer.invoke(
f"Review this draft for accuracy and suggest one improvement:\n\n{draft.content}"
)
print(review.content)兩種版本都以相同的兩步驟、相同的兩個模型、相同的回退順序進行路由。差異在於回退執行的位置。在直接版本中,我們在單一請求內於伺服器端執行回退;在 LangChain 版本中,框架會在你的流程中捕捉失敗呼叫並傳送第二個請求。對於使用 LangChain 的 create_agent 構建的代理,框架還提供 ModelFallbackMiddleware,在主模型失敗時嘗試其他模型。框架版本為你提供模型物件和共用的 invoke 介面,這正是你在有圖形、檢查點或工具管理集時所需要的結構。若沒有,則為額外負擔。
透過我們的路由(無論哪種版本)會帶來三項功能。每一次回應都會包含一個 usage 物件,內含 token 數量與以信用計算的成本,且不需要額外引數,讓你能在決定是否採用分層設定前先了解每一次呼叫的成本。Prompt caching 在支援的模型上可降低重複上下文的費用。若請求包含工具,Auto Exacto 會預設執行。它會根據吞吐量、工具呼叫成功率與基準資料重新排序你選擇模型的供應商,讓工具呼叫落在有良好工具呼叫紀錄的供應商,而不需要你額外設定。Auto Exacto 改變的是供應商順序,而非模型。
直接路由不會規劃、跨回合保持狀態,也不決定哪些子任務分配給哪個代理。這是工作流程編排層,而 models 列表並不提供此功能。下一個層級不一定是完整框架。
The OpenRouter Agent SDK
在直接路由與完整框架之間,我們的 Agent SDK,即 @openrouter/agent 套件。聊天完成是無狀態的。你傳送訊息並得到一次回應。將其轉換為代理意味著執行一個迴圈,模型請求工具呼叫,你的程式碼驗證引數並執行工具,結果回傳給模型,迴圈重複直到工作完成。Agent SDK 將該迴圈打包為一個 callModel 函式。
你可以使用 tool() 助手和 Zod 模式定義工具,SDK 會處理驗證、執行以及跨回合的對話狀態。停止條件如 stepCountIs 與 maxCost 限制迴圈。每個條件在步驟完成後檢查,因此 maxCost 會在達到閾值的那一步之後停止迴圈,而非阻止該步驟,且預設 SDK 會再進行一次模型回合以產生最終答案。將 maxCost 視為停止規則,而非消費上限。串流已內建,你亦可將遠端 MCP 伺服器作為工具來源。
import { OpenRouter, tool, stepCountIs, maxCost } from "@openrouter/agent";
import { z } from "zod";
const client = new OpenRouter({ apiKey: process.env.OPENROUTER_API_KEY });
const result = client.callModel({
model: "anthropic/claude-sonnet-5",
input: "What time is it in Tokyo?",
tools: [
tool({
name: "get_time",
description: "Get the current time in a timezone",
inputSchema: z.object({ timezone: z.string() }),
execute: async ({ timezone }) => ({
time: new Date().toLocaleString("en-US", { timeZone: timezone }),
}),
}),
],
stopWhen: [stepCountIs(5), maxCost(0.5)],
});
const text = await result.getText();
console.log(text);SDK 使用 TypeScript 編寫,Python 與 Go 版本保持同步。它提供帶驗證、串流與停止條件的受限工具迴圈。它不提供持久化圖、檢查點或基於角色的團隊。
在單一請求內進行委派時,openrouter:subagent 伺服器工具允許模型在生成過程中將自包含任務交給工作者模型。工作者可為 OpenRouter 上任何模型。每個任務獨立,工作者僅看到任務描述,且不保留任務間記憶。伺服器工具仍處於測試階段,API 與行為可能變更。
SDK 亦支援人類審核與在該迴圈內持久化對話狀態。工具可設定 requireApproval 以在執行前暫停,且 StateAccessor 在 callModel 呼叫之間持久化訊息、審核與工具結果。它不提供帶明確轉換與檢查點的持久化圖,亦無跨代理團隊協調功能。若需要這些功能,則應升級至 LangGraph 或 CrewAI。
在 LangChain 或 CrewAI 下使用 OpenRouter
不必在框架與閘道之間做選擇。你保留框架的規劃、狀態與委派,並將 OpenRouter 作為其下方的模型層。
使用 LangChain,我們維護一個專用的 integration。Python 的 langchain-openrouter 套件與 JavaScript 的 @langchain/openrouter 套件為你提供一個 ChatOpenRouter 模型,你可以將代理與圖表指向它。LangChain 的檔案目前將 Python integration 標記為 beta。
from langchain_openrouter import ChatOpenRouter
model = ChatOpenRouter(
model="anthropic/claude-sonnet-5",
temperature=0,
model_kwargs={"models": ["anthropic/claude-sonnet-5", "openai/gpt-5.6-sol"]},
)ChatOpenRouter 物件傳送一個 model 值。若要在 LangChain 下使用我們的伺服器端回退,請將 models 清單透過 model_kwargs 傳遞,該套件會將其展開到請求主體中。若未提供,回退由框架處理,如上方 with_fallbacks 範例所示。
使用 CrewAI,你可以用我們的端點配置其 LLM 類別。CrewAI 的 LLM documentation 列出 OpenRouter 為使用 LiteLLM 的供應商,因此你安裝 crewai[litellm] extra,將模型 slug 字首為 openrouter/,並傳入我們的基礎 URL 與你的金鑰。
import os
from crewai import LLM
llm = LLM(
model="openrouter/anthropic/claude-sonnet-5",
base_url="https://openrouter.ai/api/v1",
api_key=os.environ["OPENROUTER_API_KEY"],
)CrewAI 範例設定單一模型。供應商路由適用於每一次請求,改變哪個模型處理某一步即為更改 slug。伺服器端模型回退僅在請求攜帶 models 清單時適用,而 CrewAI 檔案未說明如何傳遞此欄位。無論如何,你的圖表或團隊皆可按設計運作,切換至不同模型即為設定變更,而非新增供應商整合或每個模型使用獨立 API 金鑰。
選擇層級
如果你的直接實作開始累積狀態機、可恢復的檢查點、審批步驟與委派規則,你就會手動構建工作流程協調層,而框架則取代了本來你需要自行設計與維護的程式碼。這是我們的編輯指導,而非產品保證,且從應用程式必須擁有的行為開始。
- 當工作流程已經明確,且你只需為每次呼叫選擇模型、加入備援列表或控制供應商路由時,請使用 OpenRouter 原生路由。
- 若你需要受限的多輪工具迴圈,並具備驗證、串流與停止條件,而不需要持久化圖形或基於角色的工作團隊,請使用 OpenRouter Agent SDK。
- 若你需要明確的狀態轉移、持久化、恢復、人為審查,或結合決定性與模型驅動步驟,請使用 LangGraph。
- 當工作對應於專業代理、任務委派以及順序或分層協作,且環境應用程式需要結構化狀態與控制時,請使用 CrewAI。
- 若你希望框架負責協調,OpenRouter 負責模型存取與供應商路由,並在框架轉發
models列表時提供伺服器端模型備援,請將 OpenRouter 放在 LangGraph 或 CrewAI 之下。
結論
多模型協調包含三層。工作流程協調涵蓋規劃、狀態、記憶與委派,LangGraph 與 CrewAI 為此而設,且具有不同的權衡。LangGraph 讓你以明確圖形控制為代價自行編寫控制程式;CrewAI 以角色為基礎的代理與流程為代價,將更多執行路徑交給代理。模型路由與供應商路由是 OpenRouter 的功能,無論框架是否位於其上,我們都以相同方式處理。
如果你不確定專案處於哪一邊,先嘗試較小的承諾。使用 models 清單將兩步流程路由到兩個模型,先決定是否需要在其上層加框架。在為任何方式選擇模型時,models directory 讓你可依支援的引數過濾,包括 tools。
常見問題
我需要使用 LangChain 或 CrewAI 才能使用多個模型嗎?
不需要。若你的唯一需求是為一次呼叫選擇模型,並在第一個模型返回錯誤時備援至另一模型,OpenRouter 的 models 引數即可在一次請求中完成。若工作流程還需要規劃、持久化狀態、記憶、人為審查或代理間的委派,請選擇 LangGraph 或 CrewAI。
如何在一個代理工作流程中協調多個 LLM?
分層處理。對於跨步驟的規劃、狀態與委派,使用 LangGraph 或 CrewAI 等協調框架。對於選擇哪個模型處理每次呼叫,將有序的 models 列表傳送給 OpenRouter,讓我們在第一個模型返回錯誤時備援至下一個模型。我們也會為執行呼叫的模型選擇供應商端點。工作流程可同時使用兩者,框架位於上層,OpenRouter 位於下層作為模型層。
我可以將 OpenRouter 與 LangChain 或 CrewAI 一起使用,而不是選擇其中一個嗎?
是的。LangChain 在 Python 的 langchain-openrouter 套件中提供專用的 ChatOpenRouter 整合,JavaScript 的 @langchain/openrouter 套件也同樣。CrewAI 透過其使用 LiteLLM 的 LLM 類別,將 OpenRouter 記錄為提供者。在兩種情況下,框架保持編排功能,而 OpenRouter 提供模型存取與供應商路由。我們的伺服器端模型回退僅在請求攜帶 models 列表時執行,該列表由 ChatOpenRouter 透過其 model_kwargs 引數轉發。
採用 LangChain 或 CrewAI 會否將我鎖定於單一模型供應商?
不會,只要將框架指向 OpenRouter 而非單一供應商的 SDK。兩個框架都接受 OpenRouter 作為模型供應商,因此改變處理某一步驟的模型,只需在框架設定中更改模型字串,而不必重寫供應商整合。你仍可存取 OpenRouter 上的所有模型。
OpenRouter 的模型回退是否會評估答案的品質?
不會。回退是基於錯誤的。當你 models 列表中的第一個模型返回錯誤(例如上下文長度驗證錯誤、審核旗標、速率限制或停機),我們會嘗試列表中的下一個模型。成功的回覆將原樣返回,且回覆的 model 欄位會告訴你是哪個模型產生的。
參考文獻
- 模型回退, OpenRouter
- 供應商路由, OpenRouter
- Auto Exacto, OpenRouter
- Prompt Caching, OpenRouter
- Tool Calling, OpenRouter
- Agent SDK and Stop Conditions, OpenRouter
- Subagent server tool, OpenRouter
- LangChain integration, OpenRouter
- LangGraph overview, Persistence, and Interrupts, LangChain
- ChatOpenRouter and Built‑in middleware, LangChain
- Introduction, Flows, Processes, Agents, and LLMs, CrewAI
來源:openrouter blog · openrouter.ai
