The full upstream README, mirrored here for reference. Install config, tool schemas, adoption signals, and an original overview live on the Odoo19 MCP Server listing page.
支援的 MCP Client
Odoo 19 MCP Server,使用 JSON-2 API 連線。
✨ 支援多 user:設定 MCP_MULTIUSER=true 後,每個 client 以自己的 Odoo API key 認證,權限、操作歸屬、審計紀錄都對應真實 user,不再全部掛在同一個服務帳號上,詳見多 user 模式。
本專案基於 Odoo 19 JSON-2 API 完整使用指南 開發。

| 特性 | Resources | Tools |
|---|---|---|
| 用途 | 提供上下文資訊 | 執行操作/動作 |
| 觸發 | 客戶端控制(如 Claude Code) | LLM 自動決定呼叫 |
| 參數 | 無(或 URI 參數) | 有(需 LLM 生成) |
| 類比 | 員工手冊(背景知識) | 工具箱(按需使用) |
| HTTP 類比 | GET(讀取) | POST/PUT/DELETE(操作) |
Resources - 動態上下文,LLM 一開始就知道的背景資訊:
Tools - 需要時才呼叫的操作:
| 方式 | Default Prompt | Resource |
|---|---|---|
| 資料來源 | 寫死在程式碼 | 即時從 Odoo 查詢 |
| 更新時機 | 部署時 | 每次連線時 |
| 換用戶登入 | 資訊錯誤 | 自動正確 |
結論:Resource 是「動態的上下文」,不是靜態文字。
參考:MCP Resources | MCP Tools
| 變數 | 說明 | 預設值 |
|---|---|---|
ODOO_URL | Odoo 伺服器 URL | http://localhost:8069 |
ODOO_DATABASE | 資料庫名稱 | - |
ODOO_API_KEY | API Key 認證 | - |
READONLY_MODE | 唯讀模式(禁止寫入操作) | false |
MCP_ALLOW_SENSITIVE_MODELS | 設 true 停用模型黑名單(預設擋 credential 模型 ir.config_parameter、res.users.apikeys 的讀寫) | false |
MCP_AUTH_TOKEN | HTTP/SSE 模式的 Bearer Token 認證(未設定=無認證;stdio 不適用),見安全機制 | -(停用) |
MCP_MULTIUSER | 多 user 模式:每個 client 拿自己的 Odoo API key 當 Bearer token,見安全機制 | false |
UPLOAD_TOKEN_SECRET | upload token 的 HMAC secret;僅多 worker 部署需要設定(單一程序自動衍生) | - |
建立 .env 檔案:
本專案支援三種 MCP 傳輸模式:
| 模式 | 說明 | 適用情境 |
|---|---|---|
stdio | 標準輸入輸出(預設) | Claude Desktop、Cursor IDE、本機開發 |
http | HTTP 協定 | 遠端服務、n8n、Web 應用整合 |
sse | Server-Sent Events(已棄用) | 向下相容舊版 Client |
兩種模式的關鍵差異在於「誰來啟動 MCP Server」以及「算力在哪裡執行」:
stdio 模式(本機算力)
HTTP/SSE 模式(遠端算力)
⚠️ 安全提醒:HTTP 模式預設沒有認證——任何連得到該 port 的人都直接繼承
ODOO_API_KEY的完整權限。除非 server 只在受信任的內網使用, 否則請務必設定MCP_AUTH_TOKEN(或改用多 user 模式MCP_MULTIUSER)並搭配 TLS,詳見安全機制
專案提供 docker-compose.example.yml 範本,複製後修改即可使用:
範本內容
圖片 / 附件傳遞:
add_attachment的file_path模式會從/shared/uploads/讀檔上傳到 Odoo,避免大量 base64 佔用 LLM output token。client 與 server 跨機器(不共用此 volume)時,改走prepare_upload→/upload把檔案送進UPLOAD_DIR,詳見安全機制。
連不上、回
Invalid host header? 這是底層 MCP SDK 的 DNS rebinding 防護——用非 localhost 的 IP/網域連進來時,Host 標頭不在允許清單內就會被擋。用FASTMCP_HTTP_ALLOWED_HOSTS放行:官方明確警告:使用萬用字元
*會讓 server 對任何來源開放,正式環境請務必列出明確 host。必要時另有FASTMCP_HTTP_ALLOWED_ORIGINS(瀏覽器型 client 的 Origin 白名單)。
⚠️ 純 HTTP 下 Bearer token 是明文傳輸,僅適合受信任內網/臨時測試;對外請改用
https://(TLS)。
server 未啟用 MCP_AUTH_TOKEN、也未開多 user 模式時,headers 整段可省略。
多 user 模式(MCP_MULTIUSER=true)下 headers 必填,Bearer 改填自己的 Odoo API key,見多 user 模式。
| URI | 說明 |
|---|---|
odoo://models | 列出所有模型 |
odoo://model/{model_name} | 取得模型欄位定義 |
odoo://record/{model_name}/{record_id} | 取得單筆記錄 |
odoo://user | 當前登入用戶資訊 |
odoo://company | 當前用戶所屬公司資訊 |
| Tool | 說明 | 唯讀 |
|---|---|---|
list_models | 列出/搜尋可用模型 | Yes |
get_fields | 取得模型欄位定義 | Yes |
search_records | 搜尋記錄 | Yes |
count_records | 計數記錄 | Yes |
read_records | 讀取指定 ID 記錄 | Yes |
create_record | 建立記錄 | No |
update_record | 更新記錄 | No |
delete_record | 刪除記錄(需二次確認) | No |
execute_method | 執行任意模型方法(萬用入口,unlink 與黑名單模型已封鎖,見安全機制) | No |
add_attachment | 上傳附件到 Odoo(file_path / base64_data 兩種模式,見安全機制) | No |
prepare_upload | 取得 /upload 端點用法與短效 upload_token(跨機器傳檔,見安全機制) | No |
部分 client 的 Docker 設定(Claude Code / Gemini 的 Docker 版本)需要先建置本機映像檔:
本專案支援以下 MCP Client,各自的完整設定步驟見對應章節:
| Client | 加入方式 | 設定檔 |
|---|---|---|
| Claude Code | claude mcp add | ~/.claude.json |
| Gemini CLI | gemini mcp add | ~/.gemini/settings.json |
| Antigravity CLI | 手動編輯 | ~/.gemini/config/mcp_config.json |
| OpenClaw | openclaw mcp set | OpenClaw config |
| Codex CLI | codex mcp add + 手動編輯 | ~/.codex/config.toml |
設定檔位於 ~/.claude.json:
適用於 Odoo 執行在本機的情況:
使用主機網路模式:
自 2026/6/18 起個人版 Gemini CLI 停止服務,改用 Antigravity CLI。目前 沒有
mcp add子指令,需手動編輯設定檔。
設定檔路徑為 ~/.gemini/config/mcp_config.json(Antigravity CLI / IDE / SDK 共用,等同 Gemini CLI 的 --scope user)。
JSON 格式與上方 Gemini CLI 設定相同。
設定後進入 Antigravity CLI 以 /mcp 指令重新載入,並確認連線狀態。
OpenClaw 透過 CLI 管理 MCP server,設定會寫入 mcp.servers.<name>。
/mcp指令為 owner-only 且預設關閉,需以commands.mcp: true開啟才能在 chat session 中使用。
OpenClaw 會自動正規化設定,把 type:"http" 轉成 transport:"streamable-http" 後存入:
/mcp 指令若想等進行中的工作排空再重啟,可改用
openclaw gateway restart --safe。
完成後請開一個新的 chat session(或硬重整 dashboard),再輸入 /mcp 確認 odoo-mcp 連線狀態。
Codex 的
codex mcp add只支援 stdio(command/args),並不支援 url(streamable HTTP)形式的遠端 server。因此要連雲端 HTTP 模式的 MCP server,需先用佔位指令建立設定,再手動編輯~/.codex/config.toml。
codex mcp add 產生的佔位設定:
手動改為 url(streamable HTTP):
若 server 端設定了
MCP_AUTH_TOKEN,需加上bearer_token_env_var = "ODOO_MCP_TOKEN", 並在執行 Codex 的環境中export ODOO_MCP_TOKEN=<與 server MCP_AUTH_TOKEN 相同的值>; 或改用自訂http_headers直接填Authorizationheader。 多 user 模式(MCP_MULTIUSER=true)下同理,ODOO_MCP_TOKEN改 export 自己的 Odoo API key。
MCP_AUTH_TOKEN)設定 MCP_AUTH_TOKEN 環境變數即可啟用 Bearer Token 認證(opt-in):
/mcp 端點要求 Authorization: Bearer <token>,未帶或錯誤一律回 401MCP_MULTIUSER)預設情況下,所有操作都透過 ODOO_API_KEY 這一個 Odoo 帳號執行——多人共用時,
Odoo 端的權限、chatter、審計紀錄全部歸到同一個 user。設定 MCP_MULTIUSER=true
後改為 pass-through 認證:
MCP_AUTH_TOKEN 可並存,作為 admin fallback(走 ODOO_API_KEY 的共享連線);
stdio 模式不受影響MCP_AUTH_TOKEN、不跑 stdio)可連 ODOO_API_KEY 都不設
——server 端零長效憑證,設定檔外洩也沒東西可偷。誤走到 fallback 路徑時會收到
明確的設定錯誤訊息(不會拿 placeholder 去打 Odoo)Client 端設定與 MCP_AUTH_TOKEN 完全相同(完整範例見雲端部署(HTTP 模式)),
只是 Bearer 換成各自的 Odoo API key:
UPLOAD_DIR)add_attachment 的 file_path 模式是本 server 唯一會讀取 MCP 主機本地檔案的入口。
若不設限,被 prompt injection 的 LLM 可用 file_path="/app/.env" 把 server 機密
(含 ODOO_API_KEY 本身)讀出、上傳成 Odoo 附件外洩——這是 confused deputy,
MCP_AUTH_TOKEN 擋不住(LLM 本來就是合法持 token 的 client)。
因此 file_path 被限制在 UPLOAD_DIR(預設 /shared/uploads)底下:
Path.resolve() 正規化後,必須落在 UPLOAD_DIR 內,否則回 ToolErrorresolve() 會一併解掉 symlink,所以「白名單目錄裡放一個指向外部的 symlink」也擋得掉/shared/uploads 圖片傳遞通道,Docker 部署無需額外設定UPLOAD_DIR=/(等於解除限制,自負風險)base64_data 模式,不受此限制prepare_upload → /upload)當 client 與 server 不在同一台機器時,shared-uploads volume 用不到,file_path
沒有共用檔案系統可讀;若改走 base64_data,整包 base64 會流經 LLM 的 token stream,又慢又貴。
/upload 提供一條 out-of-band 的檔案通道:client 用普通 HTTP POST 把位元組直接推到 server
(不經 LLM),server 存進 UPLOAD_DIR 後回傳 file_path,client 再用這個路徑呼叫
add_attachment——只有短路徑字串會進 token stream。
整個工作流透過 MCP 協定自我描述,client 端零安裝、零設定:agent(如 Claude Code)呼叫
prepare_upload 工具就拿到端點用法與短效 upload_token,接著自己上傳:
接著呼叫 add_attachment(file_path="/shared/uploads/<uuid>.png", file_name="invoice.png", ...)。
不經 MCP 的手動整合(腳本、CI 等)也可以直接拿 MCP_AUTH_TOKEN 本體打同一個端點。
安全機制:
/upload 是會寫檔的端點,設了 MCP_AUTH_TOKEN 就要求 Bearer token(custom route 不受 MCP 認證保護,故自行驗證)prepare_upload 簽發的是 HMAC 衍生短效 token(MCP_AUTH_TOKEN 為根秘密簽出、預設 10 分鐘、只對 /upload 有效、無狀態驗證)——master token 不進 LLM context,就算對話 transcript 外流,外洩的也只是效期內的上傳權限uuid 產生,client 給的檔名絕不進入路徑,無法逃出 UPLOAD_DIRUPLOAD_MAX_BYTES(預設 25 MiB),超過回 413UPLOAD_DIR,請搭配定期清理或使用 ephemeral volumeMCP_ALLOW_SENSITIVE_MODELS)預設封鎖以下兩個機密模型的所有讀寫,防範 prompt injection——LLM 讀到藏在資料裡的惡意指令,拿著你的 API key 做出「權限上合法、但你沒要求」的操作:
ir.config_parameter:存第三方 API key、webhook token 等機密,一句 search 就全外洩res.users.apikeys:可產生新的長效 API key——事後 rotate 原 key 也擋不住,等於留後門正常的 agent 工作流程用不到這兩個模型,封鎖不影響日常使用;所有工具與 Resources(含 execute_method)都會檢查。
黑名單只是多一層保險,不是權限控管——權限仍由 Odoo ACL 決定,請給 MCP 低權限使用者的 API key (
res.users、ir.rule等安全模型因此不在黑名單內)。 真的需要透過 MCP 管理這兩個模型時,設MCP_ALLOW_SENSITIVE_MODELS=true停用。
設定 READONLY_MODE=true 啟用唯讀模式,適用於生產環境查詢:
create_record、update_record、delete_record、execute_method、add_attachment)在註冊時即被停用——LLM 看不到這些工具,直接呼叫也會被拒絕python odoo_mcp_server.py、fastmcp run、fastmcp dev)都同樣生效execute_method 的安全邊界delete_record 內建 confirm 機制:LLM 必須先以 confirm=False 呼叫取得確認提示,經使用者同意後才能以 confirm=True 執行刪除。
注意:confirm 參數由 LLM 自行填入,屬於「引導 LLM」層級的防護, 並非強制性的安全邊界(LLM 理論上可直接傳
confirm=True)。
execute_method 是萬用入口(escape hatch),用來呼叫沒有專用工具的模型方法,請理解其風險:
unlink 已被攔下,會導向 delete_record 的二次確認流程,無法藉此繞過確認ir.config_parameter、res.users.apikeys)全擋action_confirm、action_post、button_validate 這類會改資料的業務方法不設防——
Odoo 有上千個模型方法,server 無法枚舉哪些會寫入資料庫HTTP/SSE transport 模式下提供 /health 端點:
適用於 Docker healthcheck、Kubernetes probe、load balancer 探活。stdio 模式下不影響。
此端點不受 MCP_AUTH_TOKEN 保護(不需帶 token)。
Apache 2.0