Doramagic 项目包 · 项目说明书

decoy-scan 项目

生成时间:2026-05-14 05:23:08 UTC

项目介绍

decoy-scan 是一款面向 MCP (Model Context Protocol) 生态的供应链安全扫描工具,旨在 Agent 执行工具调用之前发现 MCP 服务器中的安全风险。该项目由 Decoy 团队开发,采用零依赖设计,仅需 Node.js 18+ 即可运行,无需安装任何 npm 包。资料来源:[README.md:1]()

章节 相关页面

继续阅读本节完整说明和来源证据。

章节 工具风险等级定义

继续阅读本节完整说明和来源证据。

章节 提示注入检测类型

继续阅读本节完整说明和来源证据。

章节 架构概览

继续阅读本节完整说明和来源证据。

概述

decoy-scan 是一款面向 MCP (Model Context Protocol) 生态的供应链安全扫描工具,旨在 Agent 执行工具调用之前发现 MCP 服务器中的安全风险。该项目由 Decoy 团队开发,采用零依赖设计,仅需 Node.js 18+ 即可运行,无需安装任何 npm 包。资料来源:README.md:1

decoy-scan 的核心价值在于:

  • 主动防御:在攻击者利用漏洞之前识别 MCP 服务器中的危险工具和提示注入
  • 零配置:开箱即用,自动发现本地 MCP 客户端配置
  • 多平台支持:覆盖主流 MCP 客户端(Claude Desktop、Cursor、Windsurf 等)
  • CI/CD 友好:支持 JSON、SARIF 等结构化输出,便于集成到自动化流水线

资料来源:README.md:1-3

核心功能

decoy-scan 提供全面的 MCP 安全扫描能力,涵盖以下检查维度:

检查类别功能描述
工具风险分类基于名称和描述将工具分为 critical/high/medium/low 四个风险等级
提示注入检测37 种正则模式,覆盖 20 个攻击类别,检测工具描述中的提示注入
毒性流分析识别跨服务器数据泄露(TF001)和破坏性攻击链(TF002)
工具清单哈希追踪工具的增删改,检测扫描间的清单变化
Skill 扫描检测 Claude Code 中的提示注入、硬编码密钥、可疑 URL
服务器命令分析检测管道到 shell、内联代码、域名仿冒、临时目录生成
环境变量暴露识别传递给服务器的 API 密钥、令牌、敏感凭证
供应链告警对接 Decoy 告警数据库,覆盖 40+ 已知漏洞 MCP 包
传输安全检查 HTTP 无 TLS、缺失认证、通配符 CORS、公共 SSE
输入验证验证参数约束、maxLength、开放模式
权限范围评估过度授权服务器和危险能力组合
OWASP 映射将所有发现映射到 ASI01–ASI05(OWASP Agentic Top 10)

资料来源:README.md:1

工具风险等级定义

等级含义示例工具
Critical可执行代码、修改数据或造成不可逆变更execute_command, write_file
High可读取文件或发起网络请求read_file, fetch_url
Medium轻度风险,需注意配置list_directory
Low安全工具,可放心使用get_time

资料来源:AGENTS.md:1

提示注入检测类型

decoy-scan 内置 37 种提示注入检测模式,涵盖以下攻击类别:

  • 指令覆盖(Instruction Override)
  • 隐匿(Concealment)
  • 数据外泄(Data Exfiltration)
  • 凭证收割(Credential Harvesting)
  • 强制执行(Coercive Execution)
  • 工具影身(Tool Shadowing)
  • 规避技术(Evasion Techniques)

资料来源:AGENTS.md:1

支持的平台

decoy-scan 支持检测以下 MCP 客户端的配置文件:

平台操作系统配置文件路径
Claude DesktopmacOS / Windows / Linux平台相关配置目录
CursormacOS / Windows / Linux平台相关配置目录
WindsurfmacOS / Windows / Linux平台相关配置目录
VS CodemacOS / Windows / Linux平台相关配置目录
Claude CodemacOS / Windows / Linux平台相关配置目录
ZedmacOS / Windows / Linux平台相关配置目录
ClinemacOS / Windows / Linux平台相关配置目录

配置文件路径根据操作系统自动适配(macOS、Windows、Linux)。

资料来源:AGENTS.md:1

技术架构

架构概览

graph TD
    A[用户执行 decoy-scan] --> B[发现 MCP 配置]
    B --> C{配置类型}
    C -->|项目级| D[扫描 .mcp.json]
    C -->|用户级| E[扫描各客户端配置]
    D --> F[探针 MCP 服务器]
    E --> F
    F --> G[获取工具列表]
    G --> H[分类工具风险]
    G --> I[检测提示注入]
    G --> J[分析服务器命令]
    G --> K[检查环境变量]
    H --> L[生成扫描报告]
    I --> L
    J --> L
    K --> L
    L --> M[JSON / SARIF / CLI 输出]

核心模块结构

根据 CONTRIBUTING.md 的代码结构说明,主逻辑位于 index.mjs

模块功能
RISK_PATTERNS + classifyTool()基于名称/描述的工具风险分类
POISONING_PATTERNS + detectPoisoning()工具描述中的提示注入检测
analyzeServerCommand()服务器启动命令分析
SENSITIVE_ENV_PATTERNS + analyzeEnvExposure()环境变量暴露检测
analyzeReadiness()生产就绪状态启发式检查
OWASP_MAP + mapToOwasp()OWASP Agentic Top 10 映射
HOST_CONFIGS + discoverConfigs()MCP 客户端配置发现
probeServer()MCP stdio 探针
scan()完整扫描编排器
toSarif()SARIF 输出生成器

资料来源:CONTRIBUTING.md:1

库模式使用

decoy-scan 不仅可作为 CLI 工具使用,还提供编程接口:

import {
  scan,
  toSarif,
  classifyTool,
  detectPoisoning,
  analyzeToxicFlows,
  hashToolManifest,
  detectManifestChanges,
  discoverSkills,
  analyzeSkill,
} from 'decoy-scan';

const results = await scan({ skills: true });
console.log(results.toxicFlows);    // [{ id: "TF001", severity: "critical", roles: {...} }]
console.log(results.skills);        // [{ name: "...", findings: [...] }]
console.log(results.servers[0].manifestHash);  // "45c4c571f03c78a2"

资料来源:README.md:1

安装与使用

快速开始

无需安装,直接使用 npx 运行:

npx decoy-scan                        # 完整扫描
npx decoy-scan --json                 # 机器可读输出
npx decoy-scan --sarif                # SARIF 2.1.0 格式(适用于 CI/CD)
npx decoy-scan explain <target>       # 解释风险等级/类别/工具
npx decoy-scan explain <target> --json  # 结构化解释输出

资料来源:AGENTS.md:1

CLI 选项

选项简写描述
--json-j输出 JSON 格式
--sarif-输出 SARIF 2.1.0 格式
--brief-输出最小摘要(隐含 --json
--verbose-v显示所有工具,包括低风险
--quiet-q抑制状态输出
--version-V打印版本
--help-h打印帮助信息

资料来源:AGENTS.md:1

GitHub Actions 集成

decoy-scan 提供官方 GitHub Action,可直接集成到 CI/CD 流水线:

# .github/workflows/mcp-security.yml
name: MCP Security
on: [push, pull_request]

jobs:
  scan:
    runs-on: ubuntu-latest
    permissions:
      security-events: write
    steps:
      - uses: actions/checkout@v4
      - uses: decoy-run/decoy-scan@v1
        with:
          policy: no-critical,no-poisoning,no-toxic-flows
          sarif: true
          report: true
          token: ${{ secrets.DECOY_TOKEN }}

Action 输入参数:

输入默认值描述
policyno-critical,no-poisoning逗号分隔的策略规则
sariftrue上传 SARIF 到 GitHub Security
reportfalse上传到 Decoy Guard 仪表板
tokenDecoy API 令牌
verbosefalse显示所有工具包括低风险

策略规则示例:

no-critical          关键工具失败(代码执行、文件写入)
no-high              高风险工具失败(文件读取、网络)
no-poisoning         提示注入失败
no-toxic-flows       跨服务器数据泄露/破坏链失败
no-secrets           MCP 配置中的密钥暴露失败
require-tripwires    未安装 decoy-tripwire 时失败
max-critical=N       关键工具数量限制

资料来源:README.md:1

输出格式

JSON 输出结构

{
  "timestamp": "ISO-8601",
  "hosts": ["Claude Desktop", "Cursor"],
  "servers": [{
    "name": "server-name",
    "hosts": ["Claude Desktop"],
    "command": "npx",
    "args": ["@modelcontextprotocol/server-filesystem"],
    "tools": [{
      "name": "read_file",
      "description": "...",
      "risk": "high",
      "poisoning": [{ "type": "...", "severity": "...", "description": "..." }]
    }],
    "risk": "high",
    "error": null,
    "findings": [{
      "type": "env-exposure",
      "severity": "high",
      "description": "...",
      "source": "env-config"
    }]
  }],
  "summary": {
    "total": 2, "critical": 1, "high": 1, "medium": 0, "low": 0, "poisoned": 0
  },
  "exitCode": 1
}

资料来源:AGENTS.md:1

SARIF 输出

SARIF 2.1.0 格式输出,适用于 GitHub Security 标签页集成:

npx decoy-scan --sarif

资料来源:README.md:1

退出码

退出码含义
0未发现 critical 或 high 风险问题
1发现 high 风险问题
2发现 critical 问题、工具污染或毒性流

退出码同时作为 exitCode 字段出现在 JSON 和 --brief 输出中,便于程序化判断。

资料来源:AGENTS.md:1

设计原则

decoy-scan 遵循以下核心设计原则:

  1. 零依赖:仅使用 Node.js 内置模块,不添加任何 npm 包
  2. 无构建步骤:纯 ES 模块,无需 TypeScript 或打包器
  3. 高性能:扫描应在数秒内完成,对服务器探针采用激进超时策略
  4. 安全扫描:仅读取配置,不修改任何文件,及时终止启动的服务器
  5. Agent 优先:JSON 和 SARIF 输出必须可被机器解析,AGENTS.md 必须完整

资料来源:CONTRIBUTING.md:1

版本历史

decoy-scan 采用语义化版本号,主要版本特性如下:

版本日期主要更新
0.7.02026-05-10v2遥测信封、重试+持久队列、首次运行仪表板链接
0.6.02026-05-08毒性流分析 v2、Skill 扫描、仪表板上传
0.5.02026-04-21explain 子命令、CLI 输出重构
0.2.02026-03-20SSE 传输安全、输入验证、动态诱饵检测
0.1.02026-03-15初始版本发布

资料来源:CHANGELOG.md:1

开发指南

本地开发

git clone https://github.com/decoy-run/decoy-scan
cd decoy-scan
node bin/cli.mjs --help

无需安装依赖,无需构建步骤,仅需 Node.js >= 18。

资料来源:CONTRIBUTING.md:1

测试

运行完整测试套件:

npm test

测试覆盖 CLI 输出、JSON/SARIF 结构、策略门控、毒性流检测、Skill 分析和清单哈希。所有测试通过后方可提交 PR。

手动测试不同输出模式:

node bin/cli.mjs --no-probe              # 仅配置扫描
node bin/cli.mjs --no-advisories         # 跳过网络请求
node bin/cli.mjs --json                  # 验证 JSON 结构
node bin/cli.mjs --sarif                 # 验证 SARIF 结构
node bin/cli.mjs --verbose               # 显示所有输出

资料来源:CONTRIBUTING.md:1

添加新的检测模式

污染检测模式定义在 index.mjsPOISONING_PATTERNS 中:

{
  pattern: /regex/i,           // 匹配规则
  type: "category-name",       // 发现类型(用于 OWASP 映射)
  severity: "critical",        // critical, high, medium, low
  description: "人类可读描述"    // 输出中显示
}

添加模式后,若适用,需将 type 添加到 OWASP_MAP

资料来源:CONTRIBUTING.md:1

添加新平台支持

HOST_CONFIGS 中添加新条目:

"New Client": () => {
  const p = platform();
  if (p === "darwin") return join(homedir(), "path", "to", "config.json");
  if (p === "win32") return join(process.env.APPDATA || "", "path", "config.json");
  return join(homedir(), ".config", "path", "config.json");
},

资料来源:CONTRIBUTING.md:1

安全问题报告

发现安全漏洞请通过电子邮件联系 [email protected],请勿为此项目创建公开 Issue。

资料来源:CONTRIBUTING.md:1

资料来源:[README.md:1-3]()

快速开始

decoy-scan 是一个 MCP(Model Context Protocol)供应链安全扫描工具,用于检测 MCP 服务器配置中的安全风险、提示注入和有毒数据流。

章节 相关页面

继续阅读本节完整说明和来源证据。

章节 方式一:直接运行(推荐)

继续阅读本节完整说明和来源证据。

章节 方式二:本地开发

继续阅读本节完整说明和来源证据。

章节 全局参数

继续阅读本节完整说明和来源证据。

功能概述

功能模块说明
工具风险分类按名称和描述将工具分类为 critical/high/medium/low
提示注入检测37 种正则模式覆盖 20 个攻击类别
有毒流分析跨服务器数据泄漏(TF001)和破坏性(TF002)攻击链检测
工具清单哈希检测扫描间工具的增删改
技能扫描Claude Code 技能中的提示注入、硬编码密钥、可疑 URL 检测
服务器命令分析管道到 shell、内联代码、 typosquatting、临时目录检测
环境变量暴露API 密钥、令牌、密码、云凭证检测
供应链情报40+ 已知漏洞 MCP 包
传输安全HTTP 无 TLS、缺失认证、泛域 CORS
OWASP 映射所有发现映射到 ASI01-ASI05

资料来源:README.md:37-51

系统要求

要求详情
Node.js 版本>= 18
依赖零依赖(仅使用 Node.js 内置模块)
构建步骤无需构建,直接运行 ES 模块
支持平台macOS, Windows, Linux

资料来源:CONTRIBUTING.md:8-10

基本用法

方式一:直接运行(推荐)

npx decoy-scan

无需安装,直接运行。工具会自动扫描本地所有支持的 MCP 客户端配置。

资料来源:README.md:23-24

方式二:本地开发

git clone https://github.com/decoy-run/decoy-scan
cd decoy-scan
node bin/cli.mjs --help

资料来源:CONTRIBUTING.md:4-8

支持的主机

decoy-scan 支持以下 7 个 MCP 客户端的配置文件自动发现:

主机平台支持
Claude DesktopmacOS, Windows, Linux
CursormacOS, Windows, Linux
WindsurfmacOS, Windows, Linux
VS CodemacOS, Windows, Linux
Claude CodemacOS, Windows, Linux
ZedmacOS, Windows, Linux
ClinemacOS, Windows, Linux

配置文件路径根据操作系统自动适配(macOS 使用 ~/Library/...,Windows 使用 %APPDATA%,Linux 使用 ~/.config)。

资料来源:AGENTS.md:59-61

扫描工作流

graph TD
    A[启动 decoy-scan] --> B[发现 MCP 服务器配置]
    B --> C{配置检测}
    C -->|有配置| D[启动服务器进程]
    C -->|无配置| E[生成诊断信息]
    D --> F[通过 stdio 查询工具列表]
    F --> G[工具风险分类]
    F --> H[提示注入检测]
    F --> I[环境变量暴露分析]
    G --> J[生成扫描报告]
    H --> J
    I --> J
    E --> K[输出 --json / --sarif 格式]
    J --> K

CLI 参数参考

全局参数

参数简写说明
--json-jJSON 结构化输出(机器可读)
--sarif-sSARIF 2.1.0 格式输出(CI/CD 集成)
--brief-b最小摘要信息
--verbose-v显示所有工具包括低风险项
--quiet-q静默模式,不输出状态信息
--version-V显示版本号
--help-h显示帮助信息

资料来源:AGENTS.md:13-18

扫描控制参数

参数说明
--no-probe仅扫描配置,不探测服务器
--no-advisories跳过网络请求(不查询供应链情报)
--no-telemetry禁用遥测数据收集
--verifyAI 验证扫描结果

资料来源:AGENTS.md:19-26

策略控制参数

参数说明
--policy <rules>逗号分隔的策略规则
--report上报结果到 Decoy Guard 仪表板

策略规则包括:no-criticalno-highno-poisoningno-toxic-flowsno-secretsrequire-tripwiresmax-critical=N

资料来源:README.md:78-82

输出格式

标准输出

默认情况下,decoy-scan 输出人类可读的彩色终端界面:

▸ Discovering MCP servers…
▸ Running N checks…

✗ filesystem 2 critical
  Critical: read_file, write_file
  High: list_directory

✓ claude-desktop passed

N issues found · N critical, N high · N checks passed · Ns

服务器状态徽章:

  • ✗ name N critical - 发现严重问题
  • ! name poisoned tool - 检测到提示注入(洋红色)
  • ? name probe failed - 服务器探测失败
  • ✓ name passed - 通过扫描

资料来源:CHANGELOG.md:12-22

JSON 输出

decoy-scan --json

输出结构:

{
  "timestamp": "ISO-8601",
  "hosts": ["Claude Desktop", "Cursor"],
  "servers": [{
    "name": "server-name",
    "hosts": ["Claude Desktop"],
    "command": "npx",
    "args": ["@modelcontextprotocol/server-filesystem"],
    "tools": [{
      "name": "read_file",
      "description": "...",
      "risk": "high",
      "poisoning": [{ "type": "...", "severity": "...", "description": "..." }]
    }],
    "risk": "high",
    "error": null,
    "findings": [{
      "type": "env-exposure",
      "severity": "high",
      "description": "...",
      "source": "env-config"
    }]
  }],
  "summary": {
    "total": 2, "critical": 1, "high": 1, "medium": 0, "low": 0,
    "poisoned": 0, "toxicFlows": [], "status": "warn", "exitCode": 1
  }
}

资料来源:AGENTS.md:64-93

SARIF 输出

decoy-scan --sarif

生成符合 SARIF 2.1.0 标准的输出,可直接上传到 GitHub Security 选项卡。

资料来源:README.md:57-58

Brief 输出

decoy-scan --brief

最小摘要格式:

{
  "servers": 3,
  "critical": 1,
  "high": 2,
  "medium": 4,
  "low": 5,
  "poisoned": 0,
  "status": "fail",
  "exitCode": 2
}

资料来源:AGENTS.md:100-116

退出码

退出码含义
0无 critical 或 high 风险问题
1发现 high 风险问题
2发现 critical 问题、工具中毒或有毒流

退出码在 --json--brief 输出中通过 exitCode 字段暴露,便于自动化脚本处理。

资料来源:AGENTS.md:45-54

GitHub Action 集成

基本配置

.github/workflows/mcp-security.yml 中添加:

name: MCP Security
on: [push, pull_request]

jobs:
  scan:
    runs-on: ubuntu-latest
    permissions:
      security-events: write
    steps:
      - uses: actions/checkout@v4
      - uses: decoy-run/decoy-scan@v1

资料来源:README.md:60-71

完整配置示例

- uses: decoy-run/decoy-scan@v1
  with:
    policy: no-critical,no-poisoning,no-toxic-flows
    sarif: true
    report: true
    token: ${{ secrets.DECOY_TOKEN }}
    verbose: false
输入参数默认值说明
policyno-critical,no-poisoning逗号分隔的策略规则
sariftrue上传 SARIF 到 GitHub Security
reportfalse上传到 Decoy Guard 仪表板
tokenDecoy API 令牌
verbosefalse显示所有工具包括低风险

资料来源:README.md:73-80

GitHub Action 输出

Action 提供以下输出供后续步骤使用:

输出说明
exit-code扫描退出码
sarif-fileSARIF 文件路径
summary摘要信息

资料来源:action.yml:45-54

explain 子命令

用于解释扫描发现的含义,无需解析完整输出:

decoy-scan explain critical              # 严重等级
decoy-scan explain tool-description       # 发现类别
decoy-scan explain prompt-override        # 中毒类型
decoy-scan explain read_file             # 工具名称
decoy-scan explain list                  # 列出所有可解释目标
decoy-scan explain <target> --json       # 结构化输出

JSON 输出示例:

{
  "tool": "decoy-scan",
  "version": "0.5.1",
  "target": "critical",
  "result": {
    "kind": "tier",
    "key": "critical",
    "title": "Critical",
    "summary": "Can execute code, modify data, or cause irreversible changes.",
    "body": "...",
    "examples": ["execute_command", "write_file"],
    "advice": "..."
  }
}

result.kind 可能是:tier(等级)、category(类别)、poisoning(中毒类型)、tool(工具)。

资料来源:AGENTS.md:24-49

库模式使用

decoy-scan 也可作为 Node.js 模块导入使用:

import {
  scan,
  toSarif,
  classifyTool,
  detectPoisoning,
  analyzeToxicFlows,
  hashToolManifest,
  detectManifestChanges,
  discoverSkills,
  analyzeSkill,
} from 'decoy-scan';

const results = await scan({ skills: true });
console.log(results.toxicFlows);    // 有毒流分析结果
console.log(results.skills);        // 技能扫描结果
console.log(results.servers[0].manifestHash);  // "45c4c571f03c78a2"

资料来源:README.md:86-97

扫描检查项速查

检查项检测内容
工具风险分类按名称和描述评估风险等级
提示注入检测指令覆盖、隐藏、凭证窃取、强制执行、工具影子、规避技术
有毒流分析跨服务器数据泄漏(TF001)和破坏性攻击链(TF002)
清单变更追踪工具增删、描述变更的哈希对比
服务器命令管道到 shell、内联代码、typosquatting
环境暴露API 密钥、令牌、数据库 URL、云凭证
供应链情报40+ 已知漏洞 MCP 包
传输安全HTTP 明文、缺失认证、公开 SSE
输入验证无约束参数、缺失长度限制、开放 schema
权限范围过度特权、危险能力组合

资料来源:README.md:37-51

下一步

资料来源:[README.md:37-51]()

命令行工具

decoy-scan 提供了一个零依赖的 Node.js CLI 工具,用于扫描 MCP(Model Context Protocol)客户端配置中的安全风险。该命令行工具无需安装配置,下载后即可直接运行,支持对 Claude Desktop、Cursor、Windsurf、VS Code、Claude Code、Zed 和 Cline 等多种 MCP 主机进行安全扫描。

章节 相关页面

继续阅读本节完整说明和来源证据。

章节 扫描控制选项

继续阅读本节完整说明和来源证据。

章节 输出控制选项

继续阅读本节完整说明和来源证据。

章节 explain 子命令

继续阅读本节完整说明和来源证据。

概述

decoy-scan 提供了一个零依赖的 Node.js CLI 工具,用于扫描 MCP(Model Context Protocol)客户端配置中的安全风险。该命令行工具无需安装配置,下载后即可直接运行,支持对 Claude Desktop、Cursor、Windsurf、VS Code、Claude Code、Zed 和 Cline 等多种 MCP 主机进行安全扫描。

CLI 的核心功能包括:工具风险分类、提示注入检测、有毒数据流分析、工具清单哈希追踪、技能扫描、服务器命令分析、环境变量暴露检测、供应链告警以及 OWASP Agentic Top 10 映射。资料来源:README.md:1-45

快速开始

npx decoy-scan                        # 完整扫描
npx decoy-scan --json                 # 机器可读输出
npx decoy-scan --sarif                # SARIF 2.1.0 格式(用于 CI/CD)
npx decoy-scan explain <target>       # 解释风险等级/类别/工具名称

该工具要求 Node.js 18 或更高版本,无需预先安装任何依赖包。资料来源:CONTRIBUTING.md:1-8

全局选项

选项说明
--verbose, -v显示所有工具,包括低风险项
--quiet, -q抑制状态输出
--version, -V打印版本号
--help, -h打印帮助信息

扫描控制选项

选项说明
--no-probe仅扫描配置文件,不探测服务器
--no-advisories跳过供应链告警检查(避免网络请求)
--json输出 JSON 格式结果
--sarif输出 SARIF 2.1.0 格式结果
--brief仅输出摘要信息(隐含 --json

输出控制选项

选项说明
--output <file>将结果写入指定文件
--no-telemetry禁用遥测数据收集
--report上传结果至 Decoy Guard 仪表板

资料来源:AGENTS.md:1-10

子命令

`explain` 子命令

explain 子命令用于解析扫描结果的含义,无需解析完整的扫描输出。当 AI agent 看到某个发现并需要结构化上下文来采取行动时,此命令非常有用。

decoy-scan explain critical              # 严重性等级
decoy-scan explain tool-description      # 发现类别
decoy-scan explain prompt-override       # 投毒类型
decoy-scan explain read_file             # 工具名称(运行真实分类规则)
decoy-scan explain list                  # 枚举所有可解释的目标
decoy-scan explain <target> --json       # 结构化输出(推荐用于 agent)

资料来源:AGENTS.md:20-35

#### explain 输出格式

--json 输出的 JSON 结构如下:

{
  "tool": "decoy-scan",
  "version": "0.5.1",
  "target": "critical",
  "result": {
    "kind": "tier",
    "key": "critical",
    "title": "Critical",
    "summary": "Can execute code, modify data, or cause irreversible changes.",
    "body": "...",
    "examples": ["execute_command", "write_file", "..."],
    "advice": "..."
  }
}

result.kind 的值包括:

kind 值说明
tier严重性等级(critical、high、medium、low)
category发现类别(如 env-exposure、missing-description)
poisoning投毒类型(如 prompt-override、credential-harvesting)
tool工具名称(包含 risk、reason、matched 等字段)

资料来源:AGENTS.md:36-50

退出码

CLI 通过退出码向调用者传递扫描结果的状态:

退出码含义
0未发现严重或高风险问题
1发现高风险问题
2发现严重问题、工具投毒或有毒数据流

退出码也会在 --json--brief 输出的 exitCode 字段中暴露,便于 agent 在不重新解析严重性计数的情况下进行分支判断。资料来源:AGENTS.md:58-68

输出格式

JSON 输出架构

{
  "timestamp": "ISO-8601",
  "hosts": ["Claude Desktop", "Cursor"],
  "servers": [{
    "name": "server-name",
    "hosts": ["Claude Desktop"],
    "command": "npx",
    "args": ["@modelcontextprotocol/server-filesystem"],
    "tools": [{
      "name": "read_file",
      "description": "...",
      "risk": "high",
      "poisoning": [{ "type": "...", "severity": "...", "description": "..." }]
    }],
    "risk": "high",
    "error": null,
    "findings": [{
      "type": "env-exposure",
      "severity": "high",
      "description": "...",
      "source": "env-config"
    }]
  }],
  "summary": {
    "total": 2,
    "critical": 1,
    "high": 2,
    "medium": 4,
    "low": 5,
    "poisoned": 0
  }
}

资料来源:AGENTS.md:75-100

`--brief` 输出架构

--brief 隐含 --json,输出精简的摘要对象:

{
  "servers": 3,
  "critical": 1,
  "high": 2,
  "medium": 4,
  "low": 5,
  "poisoned": 0,
  "status": "fail",
  "exitCode": 2
}
字段说明
servers扫描的非诱饵、非错误服务器数量
criticalhighmediumlow各风险等级的工具数量
poisoned工具投毒发现数量
statuspass(清洁)、warn(高风险)或 fail(严重/投毒/有毒流)
exitCode进程退出码

资料来源:AGENTS.md:102-125

SARIF 输出

使用 --sarif 选项可生成 SARIF 2.1.0 格式的输出,适用于 GitHub Security 标签页集成:

decoy-scan --sarif
npx decoy-scan --sarif | jq

资料来源:README.md:15-18

工作流程架构

graph TD
    A[用户执行 decoy-scan] --> B[发现 MCP 服务器配置]
    B --> C{选项解析}
    C -->|explain| D[解析 explain 子命令]
    C -->|scan| E[执行安全扫描]
    D --> F[查询 RISK_PATTERNS]
    D --> G[查询 POISONING_PATTERNS]
    F --> H[返回结构化解释]
    G --> H
    E --> I[探测 MCP 服务器]
    I --> J[获取工具列表]
    J --> K[执行安全分析]
    K --> L{发现风险?}
    L -->|是| M[分类风险等级]
    L -->|否| N[标记为通过]
    M --> O[生成扫描报告]
    N --> O
    O --> P[根据结果设置退出码]

支持的主机

decoy-scan 支持以下 7 个 MCP 主机:

主机平台支持
Claude DesktopmacOS, Windows, Linux
CursormacOS, Windows, Linux
WindsurfmacOS, Windows, Linux
VS CodemacOS, Windows, Linux
Claude CodemacOS, Windows, Linux
ZedmacOS, Windows, Linux
ClinemacOS, Windows, Linux

配置文件路径根据操作系统自动适配(macOS、Windows、Linux)。资料来源:AGENTS.md:70-73

CI/CD 集成

GitHub Action

decoy-scan 提供官方 GitHub Action,可用于 CI/CD 流水线:

# .github/workflows/mcp-security.yml
name: MCP Security
on: [push, pull_request]

jobs:
  scan:
    runs-on: ubuntu-latest
    permissions:
      security-events: write
    steps:
      - uses: actions/checkout@v4
      - uses: decoy-run/decoy-scan@v1

#### Action 输入参数

输入默认值说明
policyno-critical,no-poisoning逗号分隔的策略规则
sariftrue上传 SARIF 至 GitHub Security 标签页
reportfalse上传至 Decoy Guard 仪表板
tokenDecoy API token(用于 report
verbosefalse显示所有工具包括低风险项

#### 策略规则

no-critical          严重工具(代码执行、文件写入)导致失败
no-high              高风险工具(文件读取、网络)导致失败
no-poisoning         工具描述中的提示注入导致失败
no-toxic-flows       跨服务器数据泄露/破坏链导致失败
no-secrets           MCP 配置中暴露的密钥导致失败
require-tripwires    未安装 decoy-tripwire 导致失败
max-critical=N       允许的严重问题数量

资料来源:README.md:75-100

CLI 参数与 GitHub Action 输入的映射

graph LR
    A[CLI 参数] --> B[Action 输入]
    A1[--json] --> B1[sarif=false, brief=true]
    A2[--verbose] --> B2[verbose=true]
    A3[--report] --> B3[report=true]
    A4[--policy] --> B4[policy]
    A5[--token] --> B5[token]

代码结构

CLI 的核心实现在 index.mjs 中,各模块职责如下:

模块功能
RISK_PATTERNS + classifyTool()基于名称/描述的工具风险分类
POISONING_PATTERNS + detectPoisoning()工具描述中的提示注入检测
analyzeServerCommand()服务器启动命令分析
SENSITIVE_ENV_PATTERNS + analyzeEnvExposure()环境变量暴露检测
analyzeReadiness()生产就绪性启发式检查
OWASP_MAP + mapToOwasp()OWASP Agentic Top 10 映射
HOST_CONFIGS + discoverConfigs()MCP 客户端配置发现
probeServer()MCP stdio 探测
scan()完整扫描编排器
toSarif()SARIF 输出生成器

资料来源:CONTRIBUTING.md:12-30

扫描类别详解

1. 工具风险分类

根据名称模式和描述分析,将每个工具分类为严重/高/中/低风险。关键风险模式包括代码执行、文件写入、网络调用等。资料来源:CONTRIBUTING.md:20-22

2. 工具投毒检测

37 种正则表达式模式横跨 20 个攻击类别,检测隐藏在工具描述中的提示注入,包括指令覆盖、隐藏、数据外泄、凭证窃取、强制执行、工具影子和规避技术。资料来源:CONTRIBUTING.md:22-24

3. 服务器命令分析

检查启动命令中的管道到 shell、临时目录、内联代码、域名仿冒和网络工具。资料来源:CONTRIBUTING.md:24-26

4. 环境变量暴露

标记 12 类敏感凭证,包括 API 密钥、令牌、密码、数据库 URL 和云凭证。资料来源:CONTRIBUTING.md:26-28

5. 生产就绪性

检查缺失描述、缺失模式、无必需字段、过度作用域以及无安全提示的危险工具。资料来源:CONTRIBUTING.md:28-30

6. 供应链告警

通过 Decoy 告警数据库交叉引用 40+ 个已知易受攻击的 MCP 包。资料来源:CONTRIBUTING.md:30-32

设计原则

  • 零依赖:仅使用 Node.js 内置模块,不添加 npm 包。
  • 无需构建:纯 ES 模块,无 TypeScript,无打包器。
  • 快速:扫描应在数秒内完成,积极设置服务器超时。
  • 安全:从不修改配置,仅读取扫描,遇到问题时立即终止。
  • 面向 Agent:JSON 和 SARIF 输出必须是机器可解析的。资料来源:CONTRIBUTING.md:50-57

手动测试模式

node bin/cli.mjs --no-probe              # 仅配置扫描
node bin/cli.mjs --no-advisories         # 跳过网络调用
node bin/cli.mjs --json                  # 验证 JSON 结构
node bin/cli.mjs --sarif                 # 验证 SARIF 结构
node bin/cli.mjs --verbose               # 显示所有输出

资料来源:CONTRIBUTING.md:45-49

库导出

CLI 的核心功能也可作为库导入使用:

import {
  scan,
  toSarif,
  classifyTool,
  detectPoisoning,
  analyzeToxicFlows,
  hashToolManifest,
  detectManifestChanges,
  discoverSkills,
  analyzeSkill,
} from 'decoy-scan';

const results = await scan({ skills: true });
console.log(results.toxicFlows);    // [{ id: "TF001", severity: "critical", roles: {...} }]
console.log(results.skills);        // [{ name: "...", findings: [...] }]
console.log(results.servers[0].manifestHash);  // "45c4c571f03c78a2"

资料来源:README.md:25-40

遥测数据

CLI 默认收集匿名使用统计信息,可通过以下方式禁用:

  • 设置环境变量 DECOY_TELETELRY=0
  • 使用 --no-telemetry 标志

首次运行会显示遥测通知,并缓存于 ~/.decoy/telemetry-notice-shown。资料来源:CHANGELOG.md:2026-05-10

常见使用场景

场景命令
快速扫描npx decoy-scan
CI 集成npx decoy-scan --sarif --no-advisories
Agent 集成npx decoy-scan --brief --json
了解风险npx decoy-scan explain critical
详细输出npx decoy-scan --verbose
仅配置检查npx decoy-scan --no-probe

资料来源:README.md:10-25

资料来源:[AGENTS.md:1-10]()

安全检查项目

decoy-scan 是一款针对 MCP (Model Context Protocol) 供应链安全的扫描工具,零依赖,基于 Node.js 18+ 运行。本文档详细说明该工具执行的所有安全检查项目及其检测机制。

章节 相关页面

继续阅读本节完整说明和来源证据。

章节 风险级别定义

继续阅读本节完整说明和来源证据。

章节 Critical 级别工具模式

继续阅读本节完整说明和来源证据。

章节 分类算法改进

继续阅读本节完整说明和来源证据。

核心安全检查概览

decoy-scan 实现了 12 大安全检查类别,涵盖从工具风险分类到供应链威胁检测的完整攻击面分析。

检查类别检测内容严重级别
工具风险分类按名称和描述将工具分为 critical/high/medium/low
提示词注入检测37 种正则模式覆盖 20 个攻击类别
有毒数据流分析跨服务器数据泄露和破坏性攻击链
工具清单哈希检测工具新增、移除和描述变更
技能扫描Claude Code 技能中的注入和敏感信息
服务器命令分析管道到 shell、内联代码、域名仿冒等
环境变量暴露API 密钥、令牌、云凭证等
供应链预警40+ 已知漏洞 MCP 包
传输安全HTTP 无 TLS、缺失认证、公开 SSE
输入验证无约束参数、缺失 maxLength、开放 schema
权限范围过度授权服务器、危险能力组合
OWASP 映射每项发现映射到 ASI01-ASI05

资料来源:README.md

工具风险分类体系

风险级别定义

工具风险分类是 decoy-scan 的核心检测引擎,通过 RISK_PATTERNSclassifyTool() 函数实现。

graph TD
    A[工具输入] --> B{名称模式匹配}
    B -->|^execute.*| C[Critical 级别]
    B -->|^read.*|^write.*| D[High 级别]
    B -->|^list.*|^search.*| E[Medium 级别]
    B -->|其他| F[Low 级别]
    C --> G[可执行代码、修改数据、不可逆变更]
    D --> H[文件读写、网络访问]
    E --> I[信息列举]
    F --> J[安全工具]

资料来源:CONTRIBUTING.md:1-9

Critical 级别工具模式

以下工具名称模式被直接判定为 critical 风险:

正则模式匹配示例风险说明
`^execute[_-]?(script\code\js\javascript\python\sql)$`execute_code, execute_python可执行任意代码
`^evaluate[_-]?(script\code)$`evaluate_script脚本评估执行
`^run[_-]?(script\code\js\python\sql)$`run_javascript代码运行
`^eval[_-]?(script\code)$`eval_code直接代码执行
^write[_-]?file$write_file文件写入
^spawn[_-]?process$spawn_process进程生成

资料来源:CHANGELOG.md:1-20

分类算法改进

在 v0.5.6 版本中修复了此前版本存在的边界问题:之前版本对每个名称模式都使用了锚点 ^,导致带有后缀的代码执行名称(如 evaluate_scriptexecute_python)被错误分类为 "low"。

改进措施包括:

  1. 添加了完整的带后缀代码执行模式到 critical 层级
  2. 子串回退机制现在同时对小写化的名称运行,使 evaluatespawnfetch 等危险动词即使没有提供描述也能正确分类

资料来源:CHANGELOG.md:1-20

提示词注入检测

攻击类别体系

提示词注入检测通过 POISONING_PATTERNSdetectPoisoning() 函数实现,包含 37 种正则模式覆盖 20 个攻击类别

graph TD
    A[工具描述文本] --> B{Poisoning Pattern 匹配}
    B -->|指令覆盖| C[instruction-override]
    B -->|隐匿| D[concealment]
    B -->|数据泄露| E[data-exfiltration]
    B -->|凭证窃取| F[credential-harvesting]
    B -->|强制执行| G[coercive-execution]
    B -->|工具影子| H[tool-shadowing]
    B -->|规避技术| I[evasion-techniques]
    C --> J[Critical/High 级别发现]
    D --> J
    E --> J
    F --> J
    G --> J
    H --> J
    I --> J

检测模式结构

每个 poisoning 检测模式包含以下字段:

{
  pattern: /regex/i,           // 匹配规则
  type: "category-name",       // 发现类型(用于 OWASP 映射)
  severity: "critical",        // critical/high/medium/low
  description: "Human-readable" // 人类可读说明
}

资料来源:CONTRIBUTING.md:1-20

OWASP Agentic Top 10 映射

所有提示词注入检测结果都会映射到 OWASP Agentic Top 10 for 2026 标准,通过 OWASP_MAPmapToOwasp() 函数实现。

发现类型OWASP 映射严重级别
instruction-overrideASI01Critical
credential-harvestingASI02Critical
data-exfiltrationASI03High
tool-shadowingASI04High
coercive-executionASI05Medium

有毒数据流分析

攻击链检测

有毒数据流分析检测跨服务器的数据泄露和破坏性攻击链。

graph LR
    A[服务器 A] -->|敏感数据流| B[服务器 B]
    B -->|外部通信| C[攻击者控制端点]
    D[服务器 X] -->|破坏操作| E[系统资源]
    
    subgraph TF001[数据泄露攻击链]
        A
        B
        C
    end
    
    subgraph TF002[破坏性攻击链]
        D
        E
    end

攻击链类型

ID类型说明
TF001数据泄露跨服务器敏感数据流向外部
TF002破坏性攻击跨服务器破坏操作链

资料来源:README.md

服务器命令分析

检测能力

analyzeServerCommand() 函数分析 MCP 服务器的启动命令,检测以下可疑特征:

检测类型特征风险
管道到 shell`bash, sh`命令注入
临时目录执行/tmp/, /var/tmp/持久化攻击
内联代码node -e "...", python -c "..."混淆执行
域名仿冒相似拼写的包名typosquatting
网络工具curl, wget, nc外部通信

资料来源:CONTRIBUTING.md:1-9

环境变量暴露检测

敏感信息模式

SENSITIVE_ENV_PATTERNSanalyzeEnvExposure() 函数检测 12 类敏感环境变量暴露:

graph TD
    A[MCP 配置] --> B{环境变量分析}
    B -->|API 密钥| C[API_KEY, OPENAI_API_KEY]
    B -->|令牌| D[AWS_SECRET, GITHUB_TOKEN]
    B -->|密码| E[DB_PASSWORD, MYSQL_PWD]
    B -->|数据库 URL| F[DATABASE_URL]
    B -->|云凭证| G[AWS_ACCESS_KEY, AZURE_KEY]
    B -->|其他| H[12 类总计]
    C --> I[High 级别发现]
    D --> I
    E --> I
    F --> I
    G --> I

暴露类别

类别模式示例严重级别
API 密钥*_API_KEY, *_SECRET_KEYHigh
访问令牌*_TOKEN, *_ACCESS_TOKENHigh
数据库凭证*_PASSWORD, *_CREDENTIALSCritical
云服务密钥AWS_*, AZURE_*, GCP_*Critical

生产就绪性检查

检查项目

analyzeReadiness() 函数实现以下生产就绪性检查:

检查项条件严重级别
缺失描述工具缺少 description 字段Medium
缺失 schema工具缺少 inputSchemaMedium
无必需字段关键参数缺少 required 声明Medium
过度授权权限范围过大High
破坏性工具无安全提示危险操作无 confirm 参数Medium

资料来源:CONTRIBUTING.md:1-20

工具清单变更追踪

哈希机制

decoy-scan 通过 hashToolManifest()detectManifestChanges() 函数追踪工具清单变更:

graph LR
    A[首次扫描] -->|生成哈希| B[工具清单哈希]
    C[后续扫描] -->|生成哈希| D[工具清单哈希]
    B --> E{哈希比对}
    D --> E
    E -->|哈希变化| F[变更检测]
    E -->|哈希相同| G[无变更]
    F --> H[报告变更详情]

检测变更类型

变更类型说明
工具新增新增的工具可能引入风险
工具移除移除的工具有安全盲区
描述变更描述修改可能隐藏恶意行为

供应链预警集成

预警数据库

decoy-scan 通过供应链预警功能交叉引用 Decoy 预警数据库,覆盖 40+ 已知存在漏洞的 MCP 包:

graph TD
    A[扫描的 MCP 包] --> B{Decoy 预警数据库}
    B -->|已知漏洞| C[高风险警告]
    B -->|未知| D[通过扫描]
    C --> E[提供修复建议]

检查方式

预警检查默认启用,可通过以下方式跳过:

npx decoy-scan --no-advisories  # 跳过网络调用

退出码与状态

退出码定义

退出码含义触发条件
0通过无 critical 或 high 风险问题
1警告发现 high 风险问题
2失败发现 critical 问题、工具投毒或有毒数据流

`--brief` 输出状态

{
  "servers": 3,
  "critical": 1,
  "high": 2,
  "medium": 4,
  "low": 5,
  "poisoned": 0,
  "status": "fail",
  "exitCode": 2
}
状态值含义
pass清洁无问题
warn存在 high 风险
fail存在 critical/poisoned/toxic-flows

资料来源:AGENTS.md

输出格式

支持的输出格式

格式用途使用场景
人类可读默认输出终端查看
--json机器可读输出CI/CD 集成、代理消费
--sarifSARIF 2.1.0GitHub Security 标签
--brief摘要输出快速状态检查

JSON 输出结构

{
  "timestamp": "ISO-8601",
  "hosts": ["Claude Desktop", "Cursor"],
  "servers": [{
    "name": "server-name",
    "hosts": ["Claude Desktop"],
    "command": "npx",
    "args": ["@modelcontextprotocol/server-filesystem"],
    "tools": [{
      "name": "read_file",
      "description": "...",
      "risk": "high",
      "poisoning": [{ "type": "...", "severity": "...", "description": "..." }]
    }],
    "risk": "high",
    "error": null,
    "findings": [{
      "type": "env-exposure",
      "severity": "high",
      "description": "...",
      "source": "env-config"
    }]
  }],
  "summary": {
    "total": 2,
    "critical": 1,
    "high": 1,
    "medium": 0,
    "low": 0
  }
}

架构组件

核心模块结构

模块职责文件位置
RISK_PATTERNS工具风险分类正则index.mjs
POISONING_PATTERNS提示词注入检测正则index.mjs
SENSITIVE_ENV_PATTERNS环境变量暴露模式index.mjs
OWASP_MAPOWASP 映射表index.mjs
HOST_CONFIGSMCP 客户端配置发现index.mjs
classifyTool()工具风险分类函数index.mjs
detectPoisoning()投毒检测函数index.mjs
analyzeServerCommand()服务器命令分析index.mjs
analyzeEnvExposure()环境变量暴露分析index.mjs
analyzeReadiness()生产就绪性检查index.mjs
probeServer()MCP stdio 探测index.mjs
scan()完整扫描编排index.mjs
toSarif()SARIF 输出生成index.mjs

资料来源:CONTRIBUTING.md:1-15

扫描流程

graph TD
    A[启动扫描] --> B[发现 MCP 服务器]
    B --> C[探测服务器工具列表]
    C --> D[工具风险分类]
    C --> E[提示词注入检测]
    C --> F[服务器命令分析]
    C --> G[环境变量暴露检测]
    C --> H[生产就绪性检查]
    D --> I[汇总发现]
    E --> I
    F --> I
    G --> I
    H --> I
    I --> J[输出报告]
    J --> K{退出码判定}
    K -->|0| L[无问题]
    K -->|1| M[High 风险]
    K -->|2| N[Critical/投毒]

设计原则

decoy-scan 的安全检查遵循以下核心设计原则:

  1. 零依赖 — 仅使用 Node.js 内置模块,不引入外部包
  2. 零构建 — 原始 ES 模块,无需 TypeScript 或打包工具
  3. 快速 — 扫描应在秒级完成,激进地设置超时
  4. 安全 — 只读扫描,不修改配置,及时终止派生的服务器进程
  5. 代理优先 — JSON 和 SARIF 输出必须机器可解析

资料来源:CONTRIBUTING.md:1-5

扩展检测能力

添加新的投毒检测模式

POISONING_PATTERNS 中添加新模式:

{
  pattern: /new-suspicious-pattern/i,
  type: "new-category-name",
  severity: "high",
  description: "Human-readable description"
}

添加后需在 OWASP_MAP 中注册(如果适用)。

添加新的就绪性检查

analyzeReadiness() 函数中添加:

if (/* condition */) {
  findings.push({
    type: "readiness-check-name",
    severity: "medium",
    description: "What's wrong and why it matters"
  });
}

添加新的主机支持

HOST_CONFIGS 中添加新客户端配置:

"New Client": () => {
  const p = platform();
  if (p === "darwin") return join(homedir(), "path", "to", "config.json");
  if (p === "win32") return join(process.env.APPDATA || "", "path", "config.json");
  return join(homedir(), ".config", "path", "config.json");
}

相关文档

资料来源:[README.md](https://github.com/decoy-run/decoy-scan/blob/main/README.md)

风险分级系统

decoy-scan 的风险分级系统是 MCP 安全扫描的核心组件,负责对 MCP 服务器中的工具进行分类、评级和映射。该系统通过多层检测机制,识别工具的风险等级,并将所有发现映射到行业标准 OWASP Agentic Top 10。

章节 相关页面

继续阅读本节完整说明和来源证据。

章节 风险等级定义

继续阅读本节完整说明和来源证据。

章节 分类算法流程

继续阅读本节完整说明和来源证据。

章节 Critical 等级模式

继续阅读本节完整说明和来源证据。

系统概述

风险分级系统位于 index.mjs 主模块中,核心由以下组件构成:

组件位置功能描述
RISK_PATTERNSindex.mjs工具风险模式正则表达式集合
classifyTool()index.mjs工具风险分类核心函数
POISONING_PATTERNSindex.mjs提示注入检测模式
detectPoisoning()index.mjs提示注入检测函数
OWASP_MAPindex.mjsOWASP 映射配置
mapToOwasp()index.mjsOWASP 映射转换函数

资料来源:CONTRIBUTING.md:代码结构表

风险等级架构

系统采用四级风险分类体系,每个等级对应不同的安全影响和处置策略。

风险等级定义

等级严重性影响范围示例工具
Critical关键可执行代码、修改数据、不可逆变更execute_command, write_file, eval_code
High文件读取、网络访问、数据外泄风险read_file, fetch, spawn
Medium中等权限操作、需关注配置write_config, create_resource
Low有限权限、安全风险较低read_info, list_items

Critical 等级工具包括代码执行、文件写入等可能造成不可逆影响的操作。High 等级涵盖文件读取和网络访问等存在数据泄露风险的工具。

资料来源:AGENTS.md:Exit Codes、index.mjs:RISK_PATTERNS

分类算法流程

graph TD
    A[工具输入] --> B[提取工具名称]
    B --> C{名称匹配 Critical 模式}
    C -->|匹配| D[返回 Critical]
    C -->|未匹配| E{名称匹配 High 模式}
    E -->|匹配| F[返回 High]
    E -->|未匹配| G{名称匹配 Medium 模式}
    G -->|匹配| H[返回 Medium]
    G -->|未匹配| I{名称包含高风险关键词}
    I -->|匹配| J[返回 High]
    I -->|未匹配| K{描述分析}
    K --> L{关键词匹配}
    L -->|匹配| M[返回对应等级]
    L -->|未匹配| N[返回 Low]
    
    style D fill:#ff6b6b
    style F fill:#ffa500
    style H fill:#ffd93d
    style N fill:#6bcb77

classifyTool() 函数首先检查工具名称是否匹配预定义的正则表达式模式,若未匹配则回退到描述分析。

资料来源:CONTRIBUTING.md:RISK_PATTERNS + classifyTool()

工具名称模式匹配

系统通过 RISK_PATTERNS 定义的正则表达式对工具名称进行精确匹配。

Critical 等级模式

模式匹配示例说明
^execute_command$execute_command命令执行
^run_.*run_script, run_sql带前缀的运行命令
^exec_.*exec_shell, exec_pythonexec 前缀执行
`^eval[_-]?(script\code)$`eval_script, eval-code脚本/代码评估
`^evaluate[_-]?(script\code)$`evaluate_script脚本评估
`^execute[_-]?(script\code\js\python\sql)$`execute_python, execute_js多语言执行
`^run[_-]?(script\code\js\python\sql)$`run_javascript, run_sql多语言运行

v0.5.4 版本修复了后缀代码执行名称漏检问题,将正则模式从锚定匹配改为灵活匹配。

资料来源:CHANGELOG.md:v0.5.4 Fixed

描述回退机制

当工具名称未匹配任何模式时,classifyTool() 会将工具名称小写后进行子字符串匹配,作为回退策略。

graph LR
    A[名称未匹配] --> B[转小写]
    B --> C{子字符串匹配}
    C -->|eval| D[可能 High]
    C -->|spawn| E[可能 High]
    C -->|fetch| F[可能 High]
    C -->|无匹配| G[低风险关键词分析]

这一机制确保即使工具名称不符合标准命名约定,只要包含高风险动词也能被正确分类。

OWASP Agentic Top 10 映射

系统通过 OWASP_MAP 将所有发现映射到 OWASP Agentic Top 10 标准。

映射配置结构

OWASP_MAP = {
  "type-name-1": "ASI01",
  "type-name-2": "ASI02",
  // ...
}

每个 POISONING_PATTERNS 条目的 type 字段值会关联到对应的 OWASP 分类标准。

资料来源:CONTRIBUTING.md:OWASP_MAP + mapToOwasp()

ASI01–ASI05 映射范围

OWASP 标准映射类型检测内容
ASI01提示注入相关指令覆盖、隐藏注入
ASI02凭证窃取相关API 密钥、令牌暴露
ASI03数据外泄相关敏感数据访问
ASI04权限提升相关过度权限配置
ASI05工具影子供给恶意工具替换

所有发现都会通过 mapToOwasp() 函数转换为其对应的 OWASP 分类。

提示注入检测模式

POISONING_PATTERNS 包含 37 个正则表达式模式,分布在 20 个攻击类别中。

攻击类别分类

类别严重性描述
instruction-overridecritical指令覆盖攻击
concealmentcritical隐藏指令
credential-harvestingcritical凭证收割
data-exfiltrationcritical数据外泄
coercive-executionhigh强制执行
tool-shadowinghigh工具影子
evasion-techniquesmedium规避技术

每个模式定义包含 pattern(正则表达式)、type(分类类型)、severity(严重等级)和 description(描述文本)。

资料来源:CONTRIBUTING.md:POISONING_PATTERNS

检测函数工作流程

graph TD
    A[工具描述文本] --> B[遍历 POISONING_PATTERNS]
    B --> C{正则匹配}
    C -->|匹配| D[生成 poisoning 发现]
    C -->|未匹配| E{继续下一模式}
    E --> B
    D --> F[聚合同一工具的所有发现]
    F --> G[返回发现列表]
    
    style A fill:#e3f2fd
    style D fill:#ffcdd2
    style G fill:#c8e6c9

退出码与状态映射

风险分级直接影响程序退出码和扫描状态。

退出码定义

退出码触发条件status 值
0无 critical 或 high 风险问题pass
1发现 high 风险问题warn
2发现 critical 问题、工具中毒或毒性数据流fail

--json--brief 输出中都包含 exitCode 字段,便于程序化处理。

资料来源:AGENTS.md:Exit Codes

状态计算逻辑

graph TD
    A[扫描结果] --> B{critical 计数 > 0?}
    B -->|是| C[status = fail, exitCode = 2]
    B -->|否| D{poisoned 计数 > 0?}
    D -->|是| C
    D -->|否| E{toxicFlows 计数 > 0?}
    E -->|是| C
    E -->|否| F{high 计数 > 0?}
    F -->|是| G[status = warn, exitCode = 1]
    F -->|否| H[status = pass, exitCode = 0]
    
    style C fill:#ff6b6b
    style G fill:#ffa500
    style H fill:#6bcb77

策略门控

通过命令行 --policy 参数可以配置策略规则。

策略规则失败条件
no-critical存在 critical 工具
no-high存在 high 工具
no-poisoning检测到提示注入
no-toxic-flows存在毒性数据流
no-secrets配置中存在暴露的密钥
require-tripwires未安装 decoy-tripwire

策略规则在 CI/CD 环境中用于自动化安全门控。

explain 子命令

decoy-scan explain 提供风险分级的交互式解释功能。

支持的查询类型

kind说明示例
tier严重等级explain critical
category发现类别explain tool-description
poisoning中毒类型explain prompt-override
tool工具名称explain read_file

explain 解析器使用与扫描器相同的 RISK_PATTERNSPOISONING_PATTERNS 数据源,确保解释与实际检测结果一致。

资料来源:AGENTS.md:explain subcommand

JSON 输出结构

{
  "tool": "decoy-scan",
  "version": "0.5.1",
  "target": "critical",
  "result": {
    "kind": "tier",
    "key": "critical",
    "title": "Critical",
    "summary": "Can execute code, modify data, or cause irreversible changes.",
    "body": "...",
    "examples": ["execute_command", "write_file", "..."],
    "advice": "..."
  }
}

库导出接口

decoy-scan 作为库使用时可直接导入分类功能:

import {
  classifyTool,
  detectPoisoning,
  mapToOwasp,
} from 'decoy-scan';

const risk = classifyTool({ name: "read_file", description: "..." });
const poisoningFindings = detectPoisoning(toolDescription);
const owaspCategory = mapToOwasp(findingType);

这使得其他安全工具可以复用 decoy-scan 的风险分级能力。

资料来源:README.md:Library

版本演进

版本重要变更
v0.1.0初始发布,基础风险分类
v0.5.4修复后缀代码执行名称漏检,子字符串回退增强
v0.5.6增强对 evaluate_script、eval_code 等工具的检测

CHANGELOG.md 记录了风险分级系统的所有重要变更。

资料来源:[CONTRIBUTING.md:代码结构表]()

提示注入检测

提示注入检测(Prompt Injection Detection)是 decoy-scan 工具的核心安全功能之一,旨在识别 MCP(Model Context Protocol)服务器工具描述中隐藏的恶意提示注入攻击。该功能通过正则表达式模式匹配技术,分析工具的名称和描述文本,检测 37 种不同的攻击模式,覆盖 20 个攻击类别。

章节 相关页面

继续阅读本节完整说明和来源证据。

章节 整体架构

继续阅读本节完整说明和来源证据。

章节 核心模块关系

继续阅读本节完整说明和来源证据。

章节 攻击类别总览

继续阅读本节完整说明和来源证据。

概述

提示注入检测(Prompt Injection Detection)是 decoy-scan 工具的核心安全功能之一,旨在识别 MCP(Model Context Protocol)服务器工具描述中隐藏的恶意提示注入攻击。该功能通过正则表达式模式匹配技术,分析工具的名称和描述文本,检测 37 种不同的攻击模式,覆盖 20 个攻击类别。

主要职责包括:

  • 在工具描述中识别隐藏的指令覆盖攻击
  • 检测伪装和隐蔽性攻击
  • 发现数据泄露和凭证收集企图
  • 识别强制执行和工具影子供给
  • 映射攻击类型至 OWASP Agentic Top 10 标准

资料来源:README.md:47

架构设计

整体架构

提示注入检测系统位于扫描流程的核心位置,与工具风险分类、毒性流分析和 OWASP 映射等功能紧密协作。

graph TD
    A[MCP Server 工具列表] --> B[detectPoisoning 检测器]
    B --> C{匹配结果}
    C -->|有匹配| D[生成 Poisoning Finding]
    C -->|无匹配| E[标记为安全]
    D --> F[OWASP 映射]
    F --> G[风险报告输出]
    E --> G
    B --> H[explain 子命令]
    H --> I[结构化解释 JSON]

核心模块关系

模块文件位置职责
POISONING_PATTERNSindex.mjs / lib/patterns.mjs定义所有检测正则表达式模式
detectPoisoning()index.mjs / lib/analyzers.mjs执行模式匹配和分析逻辑
OWASP_MAPindex.mjs将攻击类型映射至 OWASP 标准
explain 子命令bin/cli.mjs提供人可读和机器可解析的解释

资料来源:CONTRIBUTING.md:23

检测模式体系

攻击类别总览

decoy-scan 采用分层分类体系组织检测模式,每个模式包含正则表达式、攻击类型、严重等级和人类可读的描述。

{
  pattern: /regex/i,           // 正则匹配表达式
  type: "category-name",       // 攻击类型标识
  severity: "critical",        // 严重等级
  description: "人类可读描述"   // 输出展示
}

资料来源:CONTRIBUTING.md:42-47

支持的攻击类别

系统支持检测以下 20 个攻击类别的提示注入模式:

类别描述严重等级示例
instruction-override指令覆盖攻击critical
concealment伪装攻击critical/high
data-exfiltration数据泄露critical
credential-harvesting凭证收集critical
coercive-execution强制执行high
tool-shadowing工具影子high
evasion-techniques规避技术medium/high
其他 13 个类别各类隐蔽攻击varying

资料来源:README.md:47

严重等级定义

等级含义退出码影响
critical可执行代码、修改数据或造成不可逆变更退出码 2
high高风险操作如文件读取、网络访问退出码 1
medium中等风险,需关注无退出码影响
low低风险操作无退出码影响

资料来源:AGENTS.md:43-47

工作流程

扫描执行流程

sequenceDiagram
    participant Scanner as 扫描器
    participant Pattern as POISONING_PATTERNS
    participant Analyzer as 检测引擎
    participant OWASP as OWASP_MAP
    participant Output as 输出系统

    Scanner->>Scanner: 发现 MCP 服务器
    Scanner->>Scanner: 获取工具列表
    Loop 每个工具
        Scanner->>Analyzer: 传入工具名称和描述
        Analyzer->>Pattern: 遍历正则模式
        Pattern-->>Analyzer: 匹配结果
        Analyzer->>Analyzer: 分类严重等级
        Analyzer->>OWASP: 映射攻击类型
        OWASP-->>Analyzer: ASI 代码
    end
    Analyzer-->>Scanner: 检测结果
    Scanner->>Output: 生成报告

输出格式

#### 工具级别输出

每个被检测为存在提示注入的工具包含以下字段:

{
  "name": "tool-name",
  "risk": "critical",
  "poisoning": [{
    "type": "instruction-override",
    "severity": "critical",
    "description": "发现指令覆盖攻击模式"
  }]
}

#### JSON 完整输出

{
  "timestamp": "ISO-8601",
  "servers": [{
    "name": "server-name",
    "tools": [{
      "name": "tool-name",
      "description": "...",
      "risk": "critical",
      "poisoning": [...]
    }]
  }],
  "summary": {
    "poisoned": 0
  }
}

资料来源:AGENTS.md:59-74

API 与接口

库函数导出

decoy-scan 提供独立的 JavaScript 模块接口,可供其他项目导入使用:

import {
  scan,
  detectPoisoning,
  classifyTool,
  analyzeToxicFlows,
} from 'decoy-scan';

const results = await scan({ skills: true });
console.log(results.servers[0].tools[0].poisoning);

detectPoisoning 函数签名

参数类型描述
toolNamestring工具名称
toolDescriptionstring工具描述文本
返回值array匹配到的 poisoning 对象数组

explain 子命令

用于解析特定发现含义的辅助命令:

decoy-scan explain prompt-override       # 攻击类型说明
decoy-scan explain list                  # 列举所有可解释目标
decoy-scan explain <target> --json       # 机器可读输出

#### --json 输出结构

{
  "tool": "decoy-scan",
  "version": "0.5.1",
  "target": "instruction-override",
  "result": {
    "kind": "poisoning",
    "key": "instruction-override",
    "title": "指令覆盖",
    "summary": "攻击者尝试覆盖原始指令",
    "examples": ["...具体示例..."],
    "advice": "建议修复措施"
  }
}

资料来源:AGENTS.md:29-41

配置与扩展

添加新的检测模式

POISONING_PATTERNS 中添加新模式:

{
  pattern: /new-malicious-pattern/i,
  type: "new-attack-category",
  severity: "high",
  description: "新攻击类型的描述"
}

添加后需将 type 值注册到 OWASP_MAP 中:

const OWASP_MAP = {
  // ... 现有映射
  "new-attack-category": "ASI01",
};

资料来源:CONTRIBUTING.md:35-41

OWASP Agentic Top 10 映射

所有攻击类型均映射至 OWASP Agentic Top 10 标准,便于安全合规报告:

OWASP 代码攻击类型
ASI01Agentic 系统提示注入
ASI02敏感信息泄露
ASI03工具操作验证不足
ASI04供应链攻击
ASI05权限过度授予

资料来源:README.md:56

输出与报告

退出码机制

提示注入检测结果直接影响命令退出码:

退出码触发条件
0无 critical 或 high 风险问题
1发现 high 风险问题
2发现 critical 问题、工具污染或毒性流

--brief 摘要输出

最小化摘要对象:

{
  "servers": 3,
  "critical": 1,
  "high": 2,
  "poisoned": 0,
  "status": "fail",
  "exitCode": 2
}

SARIF 格式支持

支持 SARIF 2.1.0 标准输出,可上传至 GitHub Security:

decoy-scan --sarif

毒性流分析

除了单工具检测外,系统还支持跨服务器数据泄露(TF001)和破坏性(TF002)攻击链分析:

import { analyzeToxicFlows } from 'decoy-scan';

const results = await scan();
console.log(results.toxicFlows);

资料来源:README.md:66-68

版本变更历史

关键版本更新

版本日期变更内容
0.1.02026-03-15初始发布,支持基础提示注入检测
0.2.02026-03-20添加 SSE 传输安全检查和输入验证
0.5.02026-04-21新增 explain 子命令,改进分类逻辑
0.5.62026-04-28修复 classifyTool 对代码执行名称的遗漏
0.7.02026-05-10增强遥测功能,完善 v2 事件信封

资料来源:CHANGELOG.md:1-100

设计原则

零依赖原则

检测引擎完全基于 Node.js 原生能力实现,无外部 npm 依赖:

  • 仅使用内置 RegExp 模块进行模式匹配
  • 不依赖第三方安全扫描库
  • 确保扫描速度和可靠性

无修改原则

所有检测操作均为只读扫描:

  • 不修改任何 MCP 配置文件
  • 不修改工具描述或服务器状态
  • 及时终止检测过程中启动的服务器进程

快速完成原则

扫描应在数秒内完成:

  • 主动超时机制终止响应慢的服务器
  • 高效的正则表达式模式匹配
  • 并行处理多服务器扫描

Agent 优先原则

所有输出格式优先考虑机器可解析性:

  • JSON 输出格式稳定、结构化
  • SARIF 格式符合行业标准
  • --json--brief 输出包含 exitCode 字段便于自动化决策

资料来源:CONTRIBUTING.md:64-72

命令行使用

基础扫描

npx decoy-scan                        # 完整扫描
npx decoy-scan --json                 # 机器可读输出
npx decoy-scan --sarif                # SARIF 格式输出

详细模式

npx decoy-scan --verbose              # 显示所有工具包括 low 风险
npx decoy-scan --no-probe             # 仅配置文件检测
npx decoy-scan --no-advisories        # 跳过网络调用

CI/CD 集成

# .github/workflows/mcp-security.yml
name: MCP Security
on: [push, pull_request]
jobs:
  scan:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: decoy-run/decoy-scan@v1
        with:
          policy: no-critical,no-poisoning
          sarif: true

策略规则

规则描述
no-critical禁止 critical 级别工具
no-high禁止 high 级别工具
no-poisoning禁止工具描述中的提示注入
no-toxic-flows禁止跨服务器数据泄露
no-secrets禁止 MCP 配置中的敏感信息
require-tripwires要求安装 decoy-tripwire

资料来源:README.md:89-96

局限性说明

检测范围限制

  • 检测基于正则表达式模式匹配,可能无法识别未知变体攻击
  • 仅分析工具名称和描述文本,不深入分析工具实现逻辑
  • 依赖服务器正确响应工具列表请求

误报与漏报

  • 高敏感度配置可能导致部分合法工具被标记
  • 混淆或编码的恶意内容可能被遗漏
  • 建议结合人工审查进行最终判断

跨语言支持

  • 默认检测模式针对英文文本设计
  • 非英文工具描述的检测准确度可能降低

资料来源:[README.md:47]()

扫描架构

decoy-scan 的扫描架构是一套零依赖的 MCP(Model Context Protocol)安全扫描解决方案,采用纯 Node.js 原生模块实现。该架构通过配置文件发现、服务器探测、工具风险分析、投毒检测、有毒流程分析和供应链审查等多个环节,对本地 MCP 服务器配置进行全面的安全评估。

章节 相关页面

继续阅读本节完整说明和来源证据。

章节 项目级配置支持

继续阅读本节完整说明和来源证据。

章节 stdio 协议探测

继续阅读本节完整说明和来源证据。

章节 探测超时机制

继续阅读本节完整说明和来源证据。

概述

decoy-scan 的扫描架构是一套零依赖的 MCP(Model Context Protocol)安全扫描解决方案,采用纯 Node.js 原生模块实现。该架构通过配置文件发现、服务器探测、工具风险分析、投毒检测、有毒流程分析和供应链审查等多个环节,对本地 MCP 服务器配置进行全面的安全评估。

扫描架构的核心设计原则包括:

  • 零依赖:仅使用 Node.js 内置模块,无需安装任何 npm 包
  • 无构建步骤:直接运行 ES 模块
  • 快速执行:对服务器进行激进超时,扫描应在数秒内完成
  • 安全操作:仅读取配置,从不修改,使用后立即终止生成的服务器进程

资料来源:CONTRIBUTING.md

核心模块划分

decoy-scan 的扫描架构由多个核心模块组成,每个模块负责特定的安全检查功能:

模块文件位置核心功能
扫描编排器lib/scan.mjs协调整个扫描流程
服务器探测lib/probe.mjs通过 stdio 协议探测 MCP 服务器
策略验证lib/verify.mjs验证扫描结果是否满足策略要求
工具分类器index.mjs工具风险等级分类
投毒检测器index.mjs检测提示词注入攻击
环境分析器index.mjs分析敏感环境变量暴露
就绪检查器index.mjs生产环境就绪状态评估
配置发现器index.mjs发现本地 MCP 客户端配置

资料来源:CONTRIBUTING.md

扫描流程架构图

扫描流程采用流水线式的处理架构,从配置发现到最终报告生成依次执行:

graph TD
    A[开始扫描] --> B[发现 MCP 配置]
    B --> C{发现配置?}
    C -->|无| D[生成空结果]
    C -->|有| E[遍历每个服务器配置]
    E --> F[解析服务器启动命令]
    F --> G{是否探测服务器}
    G -->|否| H[跳过探测]
    G -->|是| I[通过 stdio 探测服务器]
    I --> J{探测成功?}
    J -->|失败| K[记录探测失败]
    J -->|成功| L[获取工具列表]
    L --> M[执行安全分析]
    M --> N{分析完成?}
    N -->|是| O[汇总结果]
    K --> O
    H --> O
    O --> P[生成输出报告]
    P --> Q[退出]
    D --> Q

配置发现模块

配置发现模块负责定位本地系统中各 MCP 客户端的配置文件。该模块维护了一个 HOST_CONFIGS 配置映射,支持以下 MCP 客户端:

  • Claude Desktop
  • Cursor
  • Windsurf
  • VS Code
  • Claude Code
  • Zed
  • Cline

配置发现器针对不同操作系统(macOS、Windows、Linux)使用不同的配置文件路径:

"Claude Desktop": () => {
  const p = platform();
  if (p === "darwin") return join(homedir(), "path", "to", "config.json");
  if (p === "win32") return join(process.env.APPDATA || "", "path", "config.json");
  return join(homedir(), ".config", "path", "config.json");
}

资料来源:CONTRIBUTING.md

项目级配置支持

除系统级 MCP 客户端配置外,扫描器还支持项目级别的 .mcp.json 配置文件。从项目根目录运行时,会自动包含项目级配置扫描。

资料来源:AGENTS.md

服务器探测模块

探测模块是扫描架构的核心组件之一,负责与 MCP 服务器建立通信并获取其工具列表。

stdio 协议探测

探测模块通过 stdio 协议与 MCP 服务器交互:

  1. 解析服务器启动命令和参数
  2. 生成子进程并启动 MCP 服务器
  3. 发送 JSON-RPC 格式的 tools/list 请求
  4. 接收并解析服务器返回的工具列表
  5. 正常终止服务器进程

探测超时机制

为保证扫描速度,探测模块采用激进超时策略:

  • 探测超时后会立即终止服务器进程
  • 探测失败的服务器会记录错误信息但不影响整体扫描继续
// 超时后立即终止并清理
killSpawnedServers();

资料来源:CONTRIBUTING.md

探测结果处理

探测结果包含以下信息:

字段说明
name服务器名称
command启动命令
args命令参数
tools工具列表(包含名称、描述、输入模式)
error探测错误信息(如有)

资料来源:AGENTS.md

安全分析模块

安全分析模块是扫描架构的核心部分,包含多个子分析器:

工具风险分类器

工具风险分类器(classifyTool)根据工具名称和描述将工具分为四个风险等级:

风险等级说明示例
critical可执行代码、修改数据或造成不可逆更改execute_command, write_file
high读取文件或发起网络请求read_file, fetch_url
medium访问系统信息或执行其他操作get_system_info
low低风险工具其他工具

分类器使用 RISK_PATTERNS 正则表达式模式匹配工具名称,并结合工具描述进行综合判断。

关键风险模式包括:

{
  pattern: /^execute[_-]?(script|code|js|javascript|python|sql)$/,
  type: "critical",
  severity: "critical"
}

资料来源:CONTRIBUTING.md

投毒检测器

投毒检测器(detectPoisoning)使用 37 种正则模式检测工具描述中的提示词注入攻击,涵盖 20 个攻击类别:

  • 指令覆盖(instruction override)
  • 隐蔽技术(concealment)
  • 数据泄露(data exfiltration)
  • 凭证收割(credential harvesting)
  • 强制执行(coercive execution)
  • 工具影子(tool shadowing)
  • 规避技术(evasion techniques)

每个投毒模式包含:

{
  pattern: /regex/i,
  type: "category-name",
  severity: "critical",
  description: "Human-readable description"
}

资料来源:CONTRIBUTING.md

服务器命令分析器

命令分析器(analyzeServerCommand)检查服务器启动命令中的可疑特征:

  • 管道到 shell(pipe-to-shell)
  • 临时目录执行
  • 内联代码注入
  • 误植域名攻击(typosquatting)
  • 网络工具调用

环境变量暴露分析器

环境分析器(analyzeEnvExposure)使用 SENSITIVE_ENV_PATTERNS 模式检测 12 类敏感凭证暴露:

  • API 密钥
  • 访问令牌
  • 密码
  • 数据库连接 URL
  • 云服务凭证
  • 其他敏感环境变量

就绪状态检查器

就绪状态检查器(analyzeReadiness)评估生产环境部署就绪程度,检查项包括:

  • 缺失工具描述
  • 缺失输入模式
  • 缺少必需字段
  • 过度授权的工具范围
  • 破坏性工具缺少安全提示

OWASP 映射器

OWASP 映射器(mapToOwasp)将所有发现映射到 OWASP Agentic Top 10:

  • ASI01 - Agentic AI Inventory and Tracking
  • ASI02 - Sensitive Data Exposure
  • ASI03 - Tool Poisoning
  • ASI04 - Agentic AI Hallucinations and Mismanagement
  • ASI05 - Overprivileged Agents and Tools

资料来源:README.md

有毒流程分析

除单个工具的安全分析外,扫描架构还支持跨服务器的有毒流程分析(analyzeToxicFlows):

流程类型ID严重性说明
数据泄露TF001critical跨服务器数据泄露攻击链
破坏性操作TF002critical跨服务器破坏性操作链

有毒流程分析在库模式下可用:

import { scan, analyzeToxicFlows } from 'decoy-scan';

const results = await scan({ skills: true });
console.log(results.toxicFlows);

资料来源:AGENTS.md

供应链审查

扫描架构包含供应链安全审查功能:

已知漏洞包检测

通过 Decoy advisory 数据库(40+ MCP 包)对配置中的服务器进行已知漏洞匹配。

工具清单哈希追踪

工具清单哈希(hashToolManifest)功能可以检测工具变更:

  • 工具新增
  • 工具移除
  • 工具描述变更

通过 detectManifestChanges 函数比较两次扫描之间的工具清单差异。

资料来源:AGENTS.md

技能扫描

扫描架构支持对 Claude Code 技能进行专项安全扫描(discoverSkillsanalyzeSkill):

  • 提示词注入检测
  • 硬编码密钥检测
  • 可疑 URL 检测
import { scan, discoverSkills, analyzeSkill } from 'decoy-scan';

const results = await scan({ skills: true });
console.log(results.skills);

资料来源:AGENTS.md

策略验证模块

策略验证模块(lib/verify.mjs)根据用户定义的策略规则验证扫描结果:

策略规则语法

规则说明
no-critical不允许关键风险工具
no-high不允许高风险工具
no-poisoning不允许提示词注入
no-toxic-flows不允许有毒流程
no-secrets不允许暴露密钥
require-tripwires要求安装 decoy-tripwire
max-critical=N限制关键问题数量

策略检查失败会设置相应的退出码。

资料来源:README.md

输出报告生成

SARIF 报告

SARIF(Static Analysis Results Interchange Format)是一种结构化的安全报告格式,用于 CI/CD 集成:

import { scan, toSarif } from 'decoy-scan';

const results = await scan();
const sarif = toSarif(results);

SARIF 输出会包含:

  • 规则 ID 和级别
  • 问题位置和描述
  • 建议的修复方案
  • OWASP 映射信息

退出码规范

退出码含义
0无关键或高风险问题
1发现高风险问题
2发现关键问题、工具投毒或策略违规

退出码在 --json--brief 输出的 exitCode 字段中也会体现,便于程序化处理。

资料来源:AGENTS.md

CLI 入口

命令行入口位于 bin/cli.mjs,负责:

  1. 解析命令行参数
  2. 初始化扫描配置
  3. 调用扫描模块
  4. 格式化输出结果
  5. 处理退出逻辑

支持的输出模式

模式说明
默认人类可读的彩色输出
--json机器可解析的 JSON 格式
--sarifSARIF 2.1.0 标准格式
--brief最小化摘要信息
--verbose显示所有工具包括低风险

可用参数

参数说明
--no-probe仅扫描配置,不探测服务器
--no-advisories跳过网络请求(供应链审查)
--quiet静默模式,抑制状态输出
--version显示版本信息

资料来源:AGENTS.md

数据流架构图

graph LR
    A[MCP 配置文件] --> B[配置发现器]
    B --> C[服务器列表]
    C --> D{探测模式}
    D -->|探测| E[stdio 探测]
    D -->|跳过| F[跳过探测]
    E --> G[工具列表]
    F --> H[空工具列表]
    G --> I[安全分析引擎]
    H --> I
    I --> J[风险分类结果]
    I --> K[投毒检测结果]
    I --> L[环境分析结果]
    I --> M[就绪检查结果]
    J --> N[结果汇总]
    K --> N
    L --> N
    M --> N
    N --> O[策略验证]
    O --> P{SARIF 格式?}
    P -->|是| Q[SARIF 报告]
    P -->|否| R[JSON/文本报告]
    Q --> S[GitHub Security]
    R --> T[终端输出]

扩展机制

添加新的投毒模式

POISONING_PATTERNS 中添加新模式:

{
  pattern: /regex/i,
  type: "category-name",
  severity: "critical",
  description: "Human-readable description"
}

添加后需在 OWASP_MAP 中添加对应的映射。

添加新的 MCP 客户端支持

HOST_CONFIGS 中添加新的客户端条目:

"New Client": () => {
  const p = platform();
  if (p === "darwin") return join(homedir(), "path", "to", "config.json");
  if (p === "win32") return join(process.env.APPDATA || "", "path", "config.json");
  return join(homedir(), ".config", "path", "config.json");
}

添加新的就绪检查

analyzeReadiness() 函数中添加检查逻辑:

if (/* condition */) {
  findings.push({
    type: "readiness-check-name",
    severity: "medium",
    description: "What's wrong and why it matters"
  });
}

资料来源:CONTRIBUTING.md

性能特性

扫描架构的性能设计目标:

  • 快速启动:无依赖安装,npx 直接运行
  • 快速扫描:激进超时策略,单个服务器探测有明确时间限制
  • 并行发现:配置文件发现与初步分析可并行执行
  • 资源高效:无额外进程开销,服务器进程及时清理

安全特性

扫描架构的安全设计原则:

特性实现方式
读取隔离仅读取配置,从不修改
进程控制服务器进程用后即删
无持久化不在系统留下痕迹
隐私保护支持 --no-telemetry 禁用遥测
安全报告敏感信息脱敏处理

版本演进

版本重大变更
0.8.0v2 遥测信封格式
0.7.0供应链 advisories、工具清单哈希追踪
0.5.0新增 explain 子命令
0.2.0SSE 传输安全检查、输入验证
0.1.0初始版本发布

资料来源:CHANGELOG.md

资料来源:[CONTRIBUTING.md](https://github.com/decoy-run/decoy-scan/blob/main/CONTRIBUTING.md)

MCP 主机发现

MCP 主机发现是 decoy-scan 工具的核心功能之一,负责自动检测本地机器上所有已配置的 MCP(Model Context Protocol)客户端主机,并收集其 MCP 服务器配置信息。该功能使工具能够对用户环境中的 MCP 生态系统进行全面的安全扫描,无需用户手动指定配置文件路径。

章节 相关页面

继续阅读本节完整说明和来源证据。

章节 配置路径规范

继续阅读本节完整说明和来源证据。

章节 路径发现机制

继续阅读本节完整说明和来源证据。

章节 完整发现流程

继续阅读本节完整说明和来源证据。

概述

MCP 主机发现是 decoy-scan 工具的核心功能之一,负责自动检测本地机器上所有已配置的 MCP(Model Context Protocol)客户端主机,并收集其 MCP 服务器配置信息。该功能使工具能够对用户环境中的 MCP 生态系统进行全面的安全扫描,无需用户手动指定配置文件路径。

decoy-scan 采用零依赖设计,完全使用 Node.js 内置模块实现主机发现功能,确保扫描过程快速、轻量且可靠。发现阶段会遍历操作系统特定的配置文件路径,解析 MCP 服务器定义,并准备后续的安全分析工作。

支持的 MCP 主机

decoy-scan 目前支持 7 种主流 MCP 客户端主机,覆盖桌面 IDE、代码编辑器、AI 编程工具等多种开发环境。

主机名称类型支持平台典型用途
Claude DesktopAI 助手macOS/Windows/LinuxAnthropic Claude 桌面集成
CursorAI 代码编辑器macOS/Windows/LinuxAI 驱动的代码补全与生成
WindsurfAI 代码编辑器macOS/Windows/LinuxCascade AI 工作流
VS Code代码编辑器macOS/Windows/LinuxMicrosoft Copilot 集成
Claude CodeCLI 工具macOS/Windows/Linux命令行 Claude 交互
Zed代码编辑器macOS/Windows/Linux高性能 GPU 加速编辑器
ClineVS Code 扩展macOS/Windows/LinuxAI 自主编程代理

资料来源:AGENTS.md:Supported Hosts (7)

平台感知配置路径

MCP 主机发现模块的核心设计原则是平台感知——根据不同操作系统采用相应的配置文件路径规范。这种设计确保工具在 macOS、Windows 和 Linux 三大主流平台上均能正确发现 MCP 配置。

配置路径规范

graph TD
    A[启动扫描] --> B{检测操作系统}
    B -->|macOS| C[使用 homedir() 路径]
    B -->|Windows| D[使用 APPDATA 环境变量]
    B -->|Linux| E[使用 ~/.config 目录]
    
    C --> F[调用平台特定路径解析函数]
    D --> F
    E --> F
    
    F --> G[发现 MCP 服务器配置]
    G --> H[解析配置文件 JSON]
    H --> I[提取服务器定义列表]

路径发现机制

各平台的标准配置存储位置如下:

平台配置目录说明
macOS~/Library/Application Support/使用 homedir() 获取用户主目录
Windows%APPDATA%使用 process.env.APPDATA 环境变量
Linux~/.config/标准 XDG 配置目录规范
// 主机配置结构示例 (CONTRIBUTING.md)
"New Client": () => {
  const p = platform();
  if (p === "darwin") return join(homedir(), "path", "to", "config.json");
  if (p === "win32") return join(process.env.APPDATA || "", "path", "config.json");
  return join(homedir(), ".config", "path", "to", "config.json");
},

资料来源:CONTRIBUTING.md:Adding Host Configs

发现流程架构

MCP 主机发现模块位于 lib/discovery.mjs,是扫描管道的第一个关键环节。整个发现流程分为配置探测、服务器提取、重复数据删除三个主要阶段。

完整发现流程

graph TD
    A[MCP 主机发现开始] --> B[遍历 HOST_CONFIGS]
    B --> C{当前平台匹配?}
    C -->|是| D[读取配置文件]
    C -->|否| E[跳过该主机]
    D --> F{配置文件存在?}
    F -->|是| G[解析 JSON 配置]
    F -->|否| E
    G --> H[提取 servers 数组]
    H --> I{发现 decoy-tripwire?}
    I -->|是| J[去重标记]
    I -->|否| K[添加至待扫描列表]
    J --> L[跨主机去重]
    K --> L
    L --> M[返回已发现服务器列表]
    
    E --> B

配置文件解析

发现的 MCP 配置文件通常为 JSON 格式,包含服务器的启动命令、参数列表等核心定义:

{
  "servers": [{
    "name": "server-name",
    "command": "npx",
    "args": ["@modelcontextprotocol/server-filesystem"],
    "env": {}
  }]
}

解析后的数据将传递给后续的 probeServer() 模块进行 MCP stdio 探测。

资料来源:AGENTS.md:JSON Output Schema

服务器探测阶段

在主机发现完成后,decoy-scan 对每个已发现的 MCP 服务器执行 stdio 探测,查询其工具列表并进行分析。

探测流程

sequenceDiagram
    participant 扫描器 as decoy-scan
    participant 服务器 as MCP Server
    participant 分析器 as 安全分析引擎
    
    扫描器->>服务器: 启动服务器进程 (stdio)
    扫描器->>服务器: 发送 initialize 请求
    服务器-->>扫描器: 返回 server info
    扫描器->>服务器: 发送 tools/list 请求
    服务器-->>扫描器: 返回工具列表
    扫描器->>分析器: 传递工具列表
    分析器->>分析器: 风险分类
    分析器->>分析器: 投毒检测
    分析器->>分析器: 准备就绪检查
    扫描器->>服务器: 终止进程

探测超时控制

为确保扫描性能,服务器探测采用激进超时策略。如果服务器在规定时间内未响应,探测将被强制终止并记录错误信息。

// 探测失败处理
if (probeError) {
  findings.push({
    type: "probe-failed",
    severity: "medium",
    description: "服务器探测超时或连接失败"
  });
}

资料来源:AGENTS.md:JSON Output Schema:error

输出格式

发现阶段的输出可采用多种格式,便于不同使用场景的消费:

JSON 格式

{
  "timestamp": "ISO-8601",
  "hosts": ["Claude Desktop", "Cursor"],
  "servers": [{
    "name": "server-name",
    "hosts": ["Claude Desktop"],
    "command": "npx",
    "args": ["@modelcontextprotocol/server-filesystem"],
    "tools": [{
      "name": "read_file",
      "description": "...",
      "risk": "high",
      "poisoning": [{ "type": "...", "severity": "...", "description": "..." }]
    }],
    "risk": "high",
    "error": null
  }]
}

SARIF 格式

通过 --sarif 参数可输出符合 SARIF 2.1.0 标准的格式,便于集成到 CI/CD 安全扫描流程中:

runs:
  - results:
      - ruleId: "critical-tool"
        level: "error"
        message: "发现高风险工具"

资料来源:lib/sarif.mjs

与其他模块的集成

MCP 主机发现是扫描管道的第一步,后续安全分析依赖于发现阶段提供的数据:

graph LR
    A[MCP 主机发现] --> B[工具风险分类]
    A --> C[投毒检测]
    A --> D[服务器命令分析]
    A --> E[环境变量暴露检测]
    A --> F[准备就绪检查]
    A --> G[供应链告警]
    
    B --> H[结果聚合]
    C --> H
    D --> H
    E --> H
    F --> H
    G --> H
    
    H --> I[JSON/SARIF 输出]
    H --> J[策略检查]
    J --> K{通过?}
    K -->|是| L[退出码 0]
    K -->|否| M[退出码 1/2]

各模块依赖关系

模块依赖发现数据功能说明
工具风险分类基于工具名称和描述进行风险评级
投毒检测检测工具描述中的提示注入模式
服务器命令分析检查启动命令的安全性
环境变量暴露检测扫描配置中的敏感凭证
准备就绪检查评估生产环境就绪程度
供应链告警对已知漏洞包进行交叉比对

资料来源:CONTRIBUTING.md:Code Structure

扩展主机支持

decoy-scan 支持通过修改 HOST_CONFIGS 配置对象来添加新的 MCP 主机支持。

添加新主机步骤

  1. index.mjs 中的 HOST_CONFIGS 对象添加新条目
  2. 实现平台感知的路径解析逻辑
  3. 确保配置文件格式符合 MCP 规范
  4. 运行 npm test 验证测试通过

配置模板

HOST_CONFIGS: {
  // ... 现有配置
  "New MCP Client": () => {
    const p = platform();
    if (p === "darwin") {
      return join(homedir(), "Library", "Application Support", "NewClient", "config.json");
    }
    if (p === "win32") {
      return join(process.env.APPDATA || "", "NewClient", "config.json");
    }
    // Linux
    return join(homedir(), ".config", "newclient", "config.json");
  }
}

资料来源:CONTRIBUTING.md:Adding Host Configs

错误处理与鲁棒性

主机发现模块具备完善的错误处理机制,确保在各种异常情况下仍能提供有用的诊断信息。

常见错误场景

错误类型处理方式用户提示
配置文件不存在静默跳过
JSON 解析失败记录错误显示解析错误详情
权限不足捕获异常提示权限问题
探测超时强制终止显示 ? probe failed

探针失败展示

当服务器探测失败时,CLI 输出会显示明确的错误标识:

? filesystem-server probe failed
  Error: Connection timeout after 5000ms

资料来源:CHANGELOG.md:0.5.3:Fixed

设计原则

MCP 主机发现模块遵循 decoy-scan 的核心设计理念:

原则实现方式优势
零依赖纯 Node.js 内置模块无需安装额外包
零配置自动探测本机配置开箱即用
快速异步 I/O + 超时控制秒级完成扫描
安全只读扫描不修改配置不影响用户环境
Agent 优先JSON/SARIF 结构化输出便于自动化集成

资料来源:CONTRIBUTING.md:Design Principles

命令行使用

主机发现功能通过以下命令行参数进行控制:

参数功能说明
无参数全量扫描发现所有主机和服务器
--no-probe仅配置发现跳过服务器探测,仅读取配置
--no-advisories跳过网络请求跳过供应链告警检查
--verbose显示所有工具包括低风险工具
--jsonJSON 输出结构化机器可读输出
--sarifSARIF 输出符合 SARIF 2.1.0 标准
# 仅发现配置,不探测服务器
npx decoy-scan --no-probe

# 跳过供应链告警检查
npx decoy-scan --no-advisories

# 详细输出模式
npx decoy-scan --verbose

资料来源:AGENTS.md:CLI Flags

技术规格

规格项
支持平台macOS, Windows, Linux
Node.js 最低版本18+
依赖数量0 (零依赖)
配置格式JSON
默认超时5000ms
并发探测串行执行

总结

MCP 主机发现是 decoy-scan 实现自动化安全扫描的基础能力,通过平台感知的配置路径解析和结构化的服务器发现机制,为后续的安全分析提供了完整的目标清单。该模块的零依赖设计和只读扫描原则确保了工具的便携性和安全性,使其能够在各种开发环境中无缝集成到 CI/CD 流程中。

资料来源:[AGENTS.md:Supported Hosts (7)]()

有毒数据流分析

有毒数据流分析(Tainted Flow Analysis 或 Toxic Flow Analysis)是 decoy-scan 安全扫描器的核心检测模块之一。该模块通过追踪 MCP 服务器之间的数据传递路径,识别潜在的安全威胁链,包括跨服务器数据泄露和破坏性操作链。

章节 相关页面

继续阅读本节完整说明和来源证据。

章节 攻击链检测机制

继续阅读本节完整说明和来源证据。

章节 扫描结果数据结构

继续阅读本节完整说明和来源证据。

章节 策略规则

继续阅读本节完整说明和来源证据。

概述

在 MCP(Model Context Protocol)生态系统中,多个服务器通常协同工作,每个服务器拥有不同的工具和权限。有毒数据流分析模块专门检测以下两类攻击链:

攻击类型标识符严重级别描述
跨服务器数据泄露TF001Critical敏感数据通过多个服务器传递后被不当暴露
破坏性攻击链TF002Critical多个工具组合执行导致不可逆的破坏性操作

资料来源:README.md:1

核心功能

攻击链检测机制

有毒数据流分析通过分析工具调用序列和数据传递路径来识别潜在威胁。当扫描器探测 MCP 服务器时,会收集所有可用工具的元数据,包括工具名称、描述和参数模式。然后通过图分析算法构建工具调用依赖图,检测是否存在恶意的数据传递链。

该模块的核心逻辑位于 lib/analyzers.mjs 中的 analyzeToxicFlows 函数。该函数接收扫描到的服务器列表和工具信息,返回检测到的有毒数据流列表。

扫描结果数据结构

扫描完成后,有毒数据流结果通过 results.toxicFlows 属性暴露:

import { scan } from 'decoy-scan';

const results = await scan();
console.log(results.toxicFlows);
// 输出格式:
// [{ id: "TF001", severity: "critical", roles: {...} }]

每个有毒数据流包含以下字段:

字段类型说明
idstring攻击链标识符(如 TF001、TF002)
severitystring严重级别(critical/high/medium/low)
rolesobject涉及的角色和权限信息

资料来源:AGENTS.md:1

工作流程

graph TD
    A[扫描 MCP 配置] --> B[探测服务器工具列表]
    B --> C[收集工具元数据]
    C --> D[构建工具依赖图]
    D --> E{分析数据传递路径}
    E -->|检测到 TF001| F[跨服务器数据泄露]
    E -->|检测到 TF002| G[破坏性攻击链]
    E -->|未检测到威胁| H[扫描通过]
    F --> I[生成安全报告]
    G --> I
    H --> I

策略控制

decoy-scan 提供了细粒度的策略控制机制,允许用户在 CI/CD 环境中根据安全需求配置扫描行为。

策略规则

通过 --policy 参数可以配置以下与有毒数据流相关的策略:

no-toxic-flows       Fail on cross-server data leak / destructive chains

资料来源:README.md:1

退出码机制

有毒数据流检测结果直接影响扫描器的退出码:

退出码含义
0无 critical 或 high 级别问题
1发现 high 级别风险问题
2发现 critical 级别问题、工具投毒或有毒数据流

资料来源:AGENTS.md:1

集成使用

作为库函数导入

decoy-scan 提供了模块化接口,可以直接导入 analyzeToxicFlows 函数用于自定义分析场景:

import {
  scan,
  analyzeToxicFlows,
} from 'decoy-scan';

// 执行完整扫描
const results = await scan();

// 仅执行有毒数据流分析
const toxicFlows = analyzeToxicFlows(results.servers);
console.log(toxicFlows);

完整扫描配置

使用 scan() 函数时,可以通过选项对象配置扫描行为:

const results = await scan({
  skills: true,           // 包含技能扫描
  advisories: true,       // 包含供应链告警
  verbose: false,         // 显示所有工具
  noProbe: false          // 跳过服务器探测
});

扫描结果对象包含完整的分析数据:

{
  servers: [...],        // 服务器列表及工具信息
  toxicFlows: [...],     // 有毒数据流分析结果
  skills: [...],         // 技能分析结果
  summary: {
    total: 2,
    critical: 1,
    high: 2,
    medium: 4,
    low: 5,
    poisoned: 0,
    status: "fail",
    exitCode: 2
  }
}

资料来源:AGENTS.md:1

GitHub Action 集成

在 CI/CD 流程中使用 decoy-scan 时,可以通过 GitHub Action 启用有毒数据流检测:

name: MCP Security
on: [push, pull_request]

jobs:
  scan:
    runs-on: ubuntu-latest
    permissions:
      security-events: write
    steps:
      - uses: actions/checkout@v4
      - uses: decoy-run/decoy-scan@v1
        with:
          policy: no-critical,no-poisoning,no-toxic-flows
          sarif: true

Action 输入参数

参数默认值说明
policyno-critical,no-poisoning策略规则列表
sariftrue上传 SARIF 到 GitHub Security
reportfalse上传到 Decoy Guard 仪表板
tokenDecoy API 令牌(用于 report)
verbosefalse显示所有工具包括低风险

资料来源:README.md:1

威胁场景示例

TF001:跨服务器数据泄露

当一个服务器拥有读取敏感文件的能力,而该数据随后被传递给另一个具有网络访问权限的服务器时,就会形成数据泄露攻击链。decoy-scan 会检测这种跨服务器的敏感数据传递模式。

TF002:破坏性攻击链

当多个工具按特定顺序组合使用时,可能导致文件系统破坏或数据不可逆损失。例如,读取配置 → 修改权限 → 删除文件的连续操作可能被识别为破坏性攻击链。

输出格式

JSON 结构

{
  "timestamp": "ISO-8601",
  "hosts": ["Claude Desktop", "Cursor"],
  "servers": [...],
  "summary": {
    "total": 2,
    "critical": 1,
    "high": 2,
    "medium": 4,
    "low": 5,
    "poisoned": 0,
    "toxicFlows": 1,
    "status": "fail",
    "exitCode": 2
  }
}

Brief 输出

对于简化的概要输出:

{
  "servers": 3,
  "critical": 1,
  "high": 2,
  "medium": 4,
  "low": 5,
  "poisoned": 0,
  "toxicFlows": 1,
  "status": "fail",
  "exitCode": 2
}

资料来源:AGENTS.md:1

版本历史

有毒数据流分析功能在以下版本中逐步完善:

版本更新内容
0.2.0引入有毒数据流分析模块
0.5.0增强分析精度,修复边界情况
0.5.8优化性能,减少误报

资料来源:CHANGELOG.md:1

相关模块

有毒数据流分析与其他安全检测模块协同工作:

模块功能
工具风险分类评估单个工具的风险级别
工具投毒检测检测工具描述中的提示注入
服务器命令分析检查服务器启动命令的安全性
环境变量暴露检测识别敏感凭证的泄露风险

所有模块的检测结果统一汇总到 scan() 函数的返回结果中,形成完整的安全态势报告。

资料来源:[README.md:1]()

GitHub Action 集成

decoy-scan 提供官方的 GitHub Action,用于在 CI/CD 流水线中自动化扫描 MCP 配置。该 Action 无需安装依赖,一行配置即可将 MCP 安全扫描集成到现有的 GitHub 工作流中,支持策略强制执行和 SARIF 结果上传功能。资料来源:[README.md:52-60]()

章节 相关页面

继续阅读本节完整说明和来源证据。

章节 基础配置

继续阅读本节完整说明和来源证据。

章节 完整配置示例

继续阅读本节完整说明和来源证据。

章节 SARIF 未上传

继续阅读本节完整说明和来源证据。

概述

decoy-scan 提供官方的 GitHub Action,用于在 CI/CD 流水线中自动化扫描 MCP 配置。该 Action 无需安装依赖,一行配置即可将 MCP 安全扫描集成到现有的 GitHub 工作流中,支持策略强制执行和 SARIF 结果上传功能。资料来源:README.md:52-60

核心功能

功能说明
自动发现扫描仓库中的 MCP 配置文件
策略强制根据规则失败构建
SARIF 上传将结果上传至 GitHub Security Tab
多主机支持支持 Claude Desktop、Cursor、Windsurf、VS Code、Claude Code、Zed、Cline

工作原理

graph TD
    A[触发工作流] --> B[检出代码]
    B --> C[运行 decoy-scan]
    C --> D{扫描结果}
    D -->|通过| E[✅ 成功]
    D -->|有风险| F[🚨 失败 + 上传 SARIF]
    D -->|仅 SARIF| G[上传 SARIF]
    F --> H[GitHub Security Tab]
    G --> H

使用方式

基础配置

.github/workflows/mcp-security.yml 中添加以下内容:

name: MCP Security
on: [push, pull_request]

jobs:
  scan:
    runs-on: ubuntu-latest
    permissions:
      security-events: write
    steps:
      - uses: actions/checkout@v4
      - uses: decoy-run/decoy-scan@v1

资料来源:README.md:52-66

完整配置示例

name: MCP Security
on: [push, pull_request]

jobs:
  scan:
    runs-on: ubuntu-latest
    permissions:
      security-events: write
    steps:
      - uses: actions/checkout@v4
      - uses: decoy-run/decoy-scan@v1
        with:
          policy: no-critical,no-poisoning,no-toxic-flows
          sarif: true
          report: true
          token: ${{ secrets.DECOY_TOKEN }}
          verbose: false

输入参数

参数默认值必填说明
policyno-critical,no-poisoning逗号分隔的策略规则
sariftrue上传 SARIF 到 GitHub Security Tab
reportfalse上传到 Decoy Guard 仪表板
token条件Decoy API 令牌(仅 report: true 时需要)
verbosefalse显示所有工具包括低风险项

资料来源:README.md:68-76

策略规则

规则说明
no-critical遇到关键工具(代码执行、文件写入)时失败
no-high遇到高风险工具(文件读取、网络请求)时失败
no-poisoning检测到提示词注入时失败
no-toxic-flows检测到跨服务器数据泄露或破坏性链时失败
no-secrets检测到 MCP 配置中暴露的密钥时失败
require-tripwiresdecoy-tripwire 未安装时失败
max-critical=N关键工具数量超过阈值时失败

输出变量

Action 执行后生成以下输出供后续步骤使用:

输出说明
exit-code扫描退出码(0=通过, 1=高风险, 2=严重/投毒)
sarif-file生成的 SARIF 文件路径
summary扫描摘要信息
steps:
  - id: scan
    uses: decoy-run/decoy-scan@v1
  - name: 使用结果
    run: |
      echo "Exit code: ${{ steps.scan.outputs.exit-code }}"
      echo "Summary: ${{ steps.scan.outputs.summary }}"

资料来源:action.yml:55-60

SARIF 集成

启用 sarif: true 后,Action 会自动:

  1. 生成 SARIF 2.1.0 格式的扫描报告
  2. 上传到 GitHub Security Tab
  3. 在 Pull Request 中显示安全警告
- name: Upload SARIF to GitHub Security
  if: always() && inputs.sarif == 'true' && steps.scan.outputs.sarif-file != ''
  uses: github/codeql-action/upload-sarif@v3
  with:
    sarif_file: ${{ steps.scan.outputs.sarif-file }}
    category: decoy-scan
  continue-on-error: true

资料来源:action.yml:68-76

工作流状态处理

graph TD
    A[decoy-scan 执行] --> B{退出码}
    B -->|0| C[✅ Clean - 无问题]
    B -->|1| D[⚠️ Warnings - 高风险问题]
    B -->|2| E[🚨 Failed - 严重/投毒]
    C --> F[写入 GITHUB_STEP_SUMMARY]
    D --> F
    E --> F
    F --> G[Exit 1 失败构建]

Action 使用 set +e 捕获退出码,不会立即失败 step,确保 SARIF 上传和摘要写入在所有情况下都能执行。资料来源:action.yml:38-50

GitHub Step Summary

Action 会在 GitHub Actions 运行日志中生成摘要:

## Decoy Scan

✅ **Clean** — no issues found

## Decoy Scan

🚨 **Issues found** — N servers scanned, N critical, N high

Run `npx decoy-scan -v` locally for full details.

版本管理

版本说明
@v1主版本,稳定接口
@latest始终指向最新发布
@0.x.x指定具体版本

建议使用 @v1 以接收 bug 修复和安全更新,同时保持接口稳定性。

与 decoy-scan CLI 的对比

特性GitHub ActionCLI
部署方式GitHub 市场npx
SARIF 上传内置需手动配置
策略强制通过 policy 参数通过 --policy 参数
CI 集成原生需编写 YAML
密钥管理GitHub Secrets环境变量

故障排除

SARIF 未上传

确保 permissions: security-events: write 已配置:

permissions:
  security-events: write

构建未失败但有安全问题

检查 policy 参数是否包含所需的规则:

with:
  policy: no-critical,no-poisoning

令牌相关错误

验证 Decoy API 令牌格式正确且未过期:

with:
  token: ${{ secrets.DECOY_TOKEN }}

相关文档

资料来源:[README.md:52-66]()

失败模式与踩坑日记

保留 Doramagic 在发现、验证和编译中沉淀的项目专属风险,不把社区讨论只当作装饰信息。

medium 能力判断依赖假设

假设不成立时,用户拿不到承诺的能力。

medium 维护活跃度未知

新项目、停更项目和活跃项目会被混在一起,推荐信任度下降。

medium 下游验证发现风险项

下游已经要求复核,不能在页面中弱化。

medium 存在安全注意事项

用户安装前需要知道权限边界和敏感操作。

Pitfall Log / 踩坑日志

项目:decoy-run/decoy-scan

摘要:发现 7 个潜在踩坑项,其中 0 个为 high/blocking;最高优先级:能力坑 - 能力判断依赖假设。

1. 能力坑 · 能力判断依赖假设

  • 严重度:medium
  • 证据强度:source_linked
  • 发现:README/documentation is current enough for a first validation pass.
  • 对用户的影响:假设不成立时,用户拿不到承诺的能力。
  • 建议检查:将假设转成下游验证清单。
  • 防护动作:假设必须转成验证项;没有验证结果前不能写成事实。
  • 证据:capability.assumptions | github_repo:1185640470 | https://github.com/decoy-run/decoy-scan | README/documentation is current enough for a first validation pass.

2. 维护坑 · 维护活跃度未知

  • 严重度:medium
  • 证据强度:source_linked
  • 发现:未记录 last_activity_observed。
  • 对用户的影响:新项目、停更项目和活跃项目会被混在一起,推荐信任度下降。
  • 建议检查:补 GitHub 最近 commit、release、issue/PR 响应信号。
  • 防护动作:维护活跃度未知时,推荐强度不能标为高信任。
  • 证据:evidence.maintainer_signals | github_repo:1185640470 | https://github.com/decoy-run/decoy-scan | last_activity_observed missing

3. 安全/权限坑 · 下游验证发现风险项

  • 严重度:medium
  • 证据强度:source_linked
  • 发现:no_demo
  • 对用户的影响:下游已经要求复核,不能在页面中弱化。
  • 建议检查:进入安全/权限治理复核队列。
  • 防护动作:下游风险存在时必须保持 review/recommendation 降级。
  • 证据:downstream_validation.risk_items | github_repo:1185640470 | https://github.com/decoy-run/decoy-scan | no_demo; severity=medium

4. 安全/权限坑 · 存在安全注意事项

  • 严重度:medium
  • 证据强度:source_linked
  • 发现:No sandbox install has been executed yet; downstream must verify before user use.
  • 对用户的影响:用户安装前需要知道权限边界和敏感操作。
  • 建议检查:转成明确权限清单和安全审查提示。
  • 防护动作:安全注意事项必须面向用户前置展示。
  • 证据:risks.safety_notes | github_repo:1185640470 | https://github.com/decoy-run/decoy-scan | No sandbox install has been executed yet; downstream must verify before user use.

5. 安全/权限坑 · 存在评分风险

  • 严重度:medium
  • 证据强度:source_linked
  • 发现:no_demo
  • 对用户的影响:风险会影响是否适合普通用户安装。
  • 建议检查:把风险写入边界卡,并确认是否需要人工复核。
  • 防护动作:评分风险必须进入边界卡,不能只作为内部分数。
  • 证据:risks.scoring_risks | github_repo:1185640470 | https://github.com/decoy-run/decoy-scan | no_demo; severity=medium

6. 维护坑 · issue/PR 响应质量未知

  • 严重度:low
  • 证据强度:source_linked
  • 发现:issue_or_pr_quality=unknown。
  • 对用户的影响:用户无法判断遇到问题后是否有人维护。
  • 建议检查:抽样最近 issue/PR,判断是否长期无人处理。
  • 防护动作:issue/PR 响应未知时,必须提示维护风险。
  • 证据:evidence.maintainer_signals | github_repo:1185640470 | https://github.com/decoy-run/decoy-scan | issue_or_pr_quality=unknown

7. 维护坑 · 发布节奏不明确

  • 严重度:low
  • 证据强度:source_linked
  • 发现:release_recency=unknown。
  • 对用户的影响:安装命令和文档可能落后于代码,用户踩坑概率升高。
  • 建议检查:确认最近 release/tag 和 README 安装命令是否一致。
  • 防护动作:发布节奏未知或过期时,安装说明必须标注可能漂移。
  • 证据:evidence.maintainer_signals | github_repo:1185640470 | https://github.com/decoy-run/decoy-scan | release_recency=unknown

来源:Doramagic 发现、验证与编译记录