声明在前面:我不是 casbin-gateway 的作者,本文是一个第三方开发者的拆解笔记。功能描述以 apache/casbin-gateway 仓库(Apache 2.0)为准;文中的排障部分是我用开源工具 casbin-config-doctor 实测过的,命令和输出可以逐字复现。
一、先说一个被忽略的事实:你的 Agent 什么都能干
Claude Code、Codex CLI、Cursor、Gemini CLI……装的时候大家都爽,装完很少有人想过一个问题:
这些 Agent 默认能读你整个项目、跑任意 shell 命令、联网、写文件。 一个 prompt injection、一条从网页抄来的「看起来合理」的指令,就足以让它把 .env 里的 key 发出去,或者 rm 掉没提交的代码。
管 Agent 的配置已经有人管了——casbin 社区上周发的 casbin-gateway(apache 组织下,Go + React,单二进制,Apache 2.0)就是干这个的:一个本地 Agent 管理助手,把机器上所有编程 Agent 收进同一个面板,统一管供应商切换、用量统计、模型真伪校验,以及本文要重点说的——权限。
官方在 V2EX 的发布帖写得很全(支持 29 个 Agent 客户端、44 家模型厂商预置),这里不重复官方文案,只拆我最关心的一层:它的权限是怎么工作的、坏了怎么查。
二、权限层拆解:开关底下是一套标准的 Casbin 策略
Gateway 给每个 Agent 提供四十来个权限开关,分六组:终端、读项目、改项目、联网、规划与派子 Agent、以及它装的每一个 MCP Server。两个设计点值得单独说:
- 关掉的工具在请求离开这台机器之前就被摘掉了——模型压根看不到这个工具,不是「看到了不让用」,Agent 无从尝试绕过。
- 不同 Agent 的工具名被归一化了——
Bash、shell、run_shell_command在这里对应同一个开关;每组还有兜底项管住没见过的新工具,「这组全关」是真的全关。
而这些开关底下,编译成的是一套完全标准的 Casbin model.conf + policy.csv——在界面的 Advanced 里能直接看,也能自己加规则。比如官方帖里那条「除了 github 这个 MCP,其他 MCP 全禁」:
p, claude-code, tool:mcp/github, use, allow
p, claude-code, tool:mcp/*, use, deny
p, claude-code, tool:*, use, allow
这套配置用的是 Casbin 的 priority 效果(e = priority(p.eft) || deny):第一条匹配的规则说了算。这是它表达力强的原因,也是新手最容易踩的坑——
三、实战:agent 被拒了,到底是谁拦的?
Gateway 界面会告诉你某个工具被拒,但「为什么」要你自己想。priority 语义 + keyMatch 通配符叠加的时候,肉眼推很容易错。我把这套配置原样喂给 casbin-config-doctor(我维护的一个开源离线排障工具,支持逐规则归因)实测了一遍:
问题一:claude-code 能用 github 这个 MCP 吗? 第 2、3 行的通配规则让人心里打鼓:
python doctor.py explain-deny \
--model gateway_model.conf --policy gateway_policy.csv \
--sub claude-code --obj tool:mcp/github --act use
verdict: ALLOWED
matching rules:
line 1: p,claude-code,tool:mcp/github,use,allow
line 2: p,claude-code,tool:mcp/*,use,deny
line 3: p,claude-code,tool:*,use,allow
advice: Request matches policy (line 1, allow); ...
结论:第 1 行精确 allow 按 priority 先赢,后面两行虽然也匹配但轮不到。
问题二:Slack MCP 为什么被拒?
python doctor.py explain-deny ... --obj tool:mcp/slack ...
verdict: DENIED
matching rules:
line 2: p,claude-code,tool:mcp/*,use,deny
advice: Line 2 matched and DENIED this request (effect: priority).
Reorder rules, narrow the deny pattern, or change this line's eft.
归因精确到行:第 2 行的 deny 通配排在了 allow 前面。修法三条任选——把 allow 行挪到前面 / 把 deny 收窄成更精确的前缀 / 改这一行的 eft。
改完策略重启生效之前,还可以跑一遍 validate-model(模型结构检查)和 lint(孤儿规则、死赋值、重复规则),30 秒排掉低级错误。整套工具纯本地运行,策略不出你的机器。
四、装它 & 老实说的部分
一条命令,不用 Docker 不用配数据库:
# Linux / macOS
curl -fsSL https://raw.githubusercontent.com/apache/casbin-gateway/master/scripts/install.sh | bash
# Windows PowerShell
irm https://raw.githubusercontent.com/apache/casbin-gateway/master/scripts/install.ps1 | iex
官方发布帖自己列了几个已知的坑,这种主动坦白在开源项目里不多见,我原文搬运(详细说明见官方帖):
- 默认密码
admin/123——只监听 127.0.0.1 时免密无所谓,但一旦把httpaddr改成0.0.0.0,第一件事改密码:那个端口后面揣着你所有 API Key; - 容器里跑看不到宿主机上的 Agent(它靠读本机家目录发现 Agent);
- Roo Code、Copilot CLI 目前只能识别,还没接上更多能力;
- macOS 不抢
ccswitch://协议,链接请粘到 Import 页输入框。
我自己补一句边界:本文第三节用的 casbin-config-doctor 是静态分析,keyMatch/regexMatch/globMatch 按真实语义求值,但 ipMatch 和运行时自定义函数只能退化成精确比较,工具自己会在输出里提示你去运行时确认。
五、收尾
- casbin-gateway:github.com/apache/casb… (Apache 2.0,在线 Demo 见 README)
- casbin-config-doctor(本文排障工具):github.com/tlyyxjz/cas… / 在线版 tlyyxjz.github.io/casbin-doct…
如果你机器上也装了三个以上的编程 Agent,权限这层值得认真配一次;配完之后如果哪天它把你的请求拒了,至少你现在知道去哪查。
有交流欢迎评论区,或者直接在两个仓库提 issue。