Skip to main content
Glama

sweep-mcp

一个可以删除目录的 MCP 服务器——以及让语言模型拥有这种能力时,使其不至于鲁莽的护栏。

它通过模型上下文协议暴露 sweep,因此代理可以找到并回收 node_modules、.venv、target、__pycache__ 等目录。有趣的部分不在于删除本身,而在于允许删除之前必须满足的所有条件。

2026 年发表的研究发现,在扫描的 1,808 个 MCP 服务器中,66% 存在安全问题,一个季度内针对 MCP 实现提交了 30 多个 CVE。这个仓库是一个以相反方式编写的服务器:拒绝优先,功能其次。


威胁模型

一个能够删除目录的 MCP 服务器,就像一把上膛的枪,指向进程所能触及的任何地方。有五件事可能出错,每件事都有对应的控制措施和测试来确保其触发。

风险

控制措施

测试

代理扫描 / 或 C:\ 并删除整个机器

根目录白名单,在服务器启动时固定。代理无法设置、扩展或读取超出白名单的范围。未配置根目录 → 拒绝所有请求

test_empty_allowlist_denies_every_path

使用 ../../ 或符号链接逃逸白名单

每个路径在包含性检查之前都经过 resolve() 处理,因此根据其实际指向进行判断

test_dotdot_traversal_is_denied、test_symlink_pointing_outside_root_is_denied

代理要求删除一个从未扫描过的路径

reclaim 接受 id,而不是路径。 API 中没有任何地方提供路径形式的删除入口

test_there_is_no_way_to_delete_by_path

目录在扫描和删除之间发生变化

每次查找在删除时都会重新检查实时文件系统——仍然在包含范围内,仍然是目录,仍然不是链接,标记文件仍然存在

test_revalidate_refuses_a_directory_swapped_for_a_symlink

意外破坏

默认是试运行。 删除需要精确的 confirm="delete";其他任何内容都视为不删除

test_a_wrong_confirmation_string_stays_a_dry_run

还有两个较小的风险,出于同样的原因:

  • 票据 ID 是随机的,不是顺序的。 例如 f-3a91c02b77de,而不是 1。顺序 ID 会诱使代理迭代直到删除某些内容。

  • 工具描述是字符串字面量。 它们永远不会从磁盘上读取的任何内容组装而成,因此名为 ignore-previous-instructions 的目录会作为数据而非句子到达模型(test_tool_descriptions_are_static)。

Related MCP server: MCP Duplicate File Manager Server

它不保护的内容

上述控制措施仅在其覆盖范围内有效,仅此而已。

  • 配置错误的根目录。 使用 --root / 启动,它会愉快地遍历你的文件系统。白名单的有效性取决于你放入的内容,这里没有任何东西会质疑你的选择。

  • 恶意客户端。 守卫限制的是可以删除什么,而不是谁在请求。一个合法扫描并合法确认的客户端会得到它要求的东西。

  • 被说服的代理。 静态工具描述阻止文件系统内容进入模型的指令,但这里没有任何东西能阻止一个出于自身不良原因决定删除它真正找到的 node_modules 的代理。

  • 最后几毫秒。 revalidate() 缩小了检查与删除之间的窗口,但并未关闭它。正确关闭它需要跨操作持有目录文件描述符,而 shutil.rmtree 无法可移植地提供这一点。这是一个真实的竞态条件,它更小,但并非不存在。

  • Python 3.11 上的 Windows 联接点。 os.path.isjunction 在 3.12 中才引入。在此版本以下,联接点检测退化为仅检测符号链接——这与 sweep 本身所做的妥协相同,在此处明确说明而非隐藏。

  • 权限。 这不是沙箱。它以启动它的用户身份运行。

扫描器结果

针对 2026 年 8 月 18 日的 agent-audit 0.19.2 运行。

静态扫描——0 个发现,风险评分 0.0(低),7 个文件。

第一次扫描出现了一个低风险发现:AGENT-110,源代码映射工件未从分发中排除。此包不包含任何 JavaScript,因此没有源代码映射可泄露,但排除规则现在已在 pyproject.toml 中声明——这不需要任何成本,与供应链检查清单争论是浪费下午时间。

工具检查——0 个工具发现。 在三个定义中均未检测到工具投毒、跨源或 rug-pull 模式。

它分配的风险评级值得重现,因为它们以具有启发性的方式是错误的:

工具

评级

推断的权限

list_targets

中

SHELL_EXEC、FILE_READ

scan

高

FILE_DELETE、SHELL_EXEC、FILE_READ

reclaim

高

FILE_DELETE、SHELL_EXEC、FILE_READ

scan 不能删除任何东西。它是只读的,声明了 read_only_hint=True,并且有一个测试断言它保持只读。它被评为高并带有 FILE_DELETE 权限,因为扫描器根据描述匹配关键词,而这个服务器的 scan 描述包含以下句子:

“只读:这永远不会删除任何东西。”

单词 deletes 在 FILE_DELETE 关键词列表中。SHELL_EXEC 来自单词 command,在“重新生成它的命令”中——这个服务器从不执行任何 shell 命令。

描述可以重新措辞以获得更好的评分。但没有这样做,因为描述的目标受众是决定是否调用该工具的语言模型,而“这永远不会删除任何东西”是其中最有用的句子。关键词扫描器是烟雾探测器,不是法官——干净的运行值得拥有并值得发布,而从字符串匹配散文得出的评级并不能证明行为的方向。

尝试了两个扫描器,其中一个无法运行:Invariant Labs 的 mcp-scan 在 Snyk 收购后已更名为 snyk-agent-scan,现在需要 SNYK_TOKEN。Cisco 的 mcp-scanner 未发布到 PyPI。agent-audit 自己的 stdio 传输在 Windows 上对此服务器也会超时,而手动握手到相同的二进制文件只需几毫秒,因此其分析器直接接收了真实的 tools/list 输出——传输被绕过,但分析没有被绕过。

安装

pip install -e .

配置

服务器接受一个或多个 --root 目录。它没有默认值。 在没有根目录的情况下启动是一个错误,而不是扫描所有内容的邀请:

{
  "mcpServers": {
    "sweep": {
      "command": "sweep-mcp",
      "args": ["--root", "/home/you/code", "--root", "/home/you/work"]
    }
  }
}

工具

工具

破坏性

功能

list_targets

否

它知道如何回收的目录类型,以及重新生成每个目录的命令

scan

否

在根目录下的路径中查找可回收的目录。返回 id、大小和重新生成命令

reclaim

是

按 id 删除查找结果。除非 confirm="delete",否则为试运行

所有三个工具都携带 MCP ToolAnnotations,因此将破坏性工具置于确认提示后的客户端拥有所需信息:reclaim 声明 destructive_hint=True,另外两个声明 read_only_hint=True。测试套件中也对此进行了断言——一个静默回归的提示比没有更糟糕。

一次会话

scan(path="/home/you/code")
  → 12 finds, 3.4 GB
    f-3a91c02b77de  /home/you/code/api/node_modules   1.9 GB  npm install
    f-8e0244fd1b6c  /home/you/code/ml/.venv           842 MB  python -m venv .venv

reclaim(ids=["f-3a91c02b77de"])
  → dry_run: true
    would_delete: 1 path, 1.9 GB
    note: Nothing was deleted. Call again with confirm='delete'.

reclaim(ids=["f-3a91c02b77de"], confirm="delete")
  → deleted: 1 path, reclaimed 1.9 GB

测试

38 个测试。34 个在 Windows 上运行;所有 38 个在 Linux 上运行。

本地跳过的四个测试需要创建符号链接,Windows 在没有开发者模式的情况下拒绝创建——其中一个测试涵盖了扫描与删除之间的交换攻击,这是这里最重要的测试。静默跳过它会使测试套件成为装饰品,因此 CI 在 Linux 上运行,如果这些测试在那里报告为跳过,则构建失败。

pytest -q --cov=sweep_mcp

覆盖率在 83%。差距主要是 main() 和 argparse 连接代码,测试套件通过 build_server 驱动这些代码——传输是最不值得模拟的部分,也是最不可能造成损害的部分。

测试套件中没有模拟文件系统。模拟的 Path 会通过这里的所有测试,而服务器仍然会删除错误的目录。

布局

src/sweep_mcp/
  guard.py    212 lines - the allowlist, the tickets, the re-check. Imports no MCP.
  server.py   280 lines - three tools. Translation only.
tests/
  test_guard.py    23 tests - one per rule, each named for the attack it stands in for
  test_server.py   15 tests - driven through call_tool, the way a client would

guard.py 故意对 MCP 一无所知。每个可能导致用户数据丢失的决策都可以在没有客户端、传输或代理参与的情况下进行测试。如果某个规则看起来是在 server.py 中强制执行的,那是一个错误——它应该位于下一层,测试可以触及的地方。

许可证

MIT。

Related MCP Connectors

Related MCP Servers

  • F
    license
    Not graded
    quality
    D
    maintenance
    Enables AI agents to clean disk space by scanning and removing temporary files, caches, and duplicates through natural language commands via MCP protocol.
    1
    -
  • A
    license
    Not graded
    quality
    B
    maintenance
    Provides git-aware safe file operations, allowing AI agents to delete files while protecting git-tracked source code from accidental deletion.
    MIT
  • A
    license
    A
    quality
    A
    maintenance
    Enables AI assistants to audit and clean development workspaces safely by detecting reclaimable artifacts, exposed .env files, and potential secret leaks.
    6
    MIT