Static security scanner for MoonBit projects
Dependencies
| 项目 | 检出 | 类型 | 修复 PR | 状态 |
|---|---|---|---|---|
| mizchi/luna.mbt | 14 | CRLF 注入 | #103 | ✅ 已合并 |
| oboard/mocket | 8 | XSS、CRLF 注入、Cookie、CORS、目录穿越 | #12 | ✅ 已合并 |
| moonbit-community/crescent | 8 | Cookie、DoS、CORS | #44 | 🔵 Open |
| moonbitlang/async | 3 | CRLF 注入 | #494 | ✅ 已合并 |
| moonbit-community/rabbita | 2 | 目录穿越 | #126 | ✅ 已合并 |
| moonbit-community/cmark.mbt | 1 | XSS(已由上游修复为 safe=true) | #137 | 🔵 Open |
git clone https://github.com/I3eg1nner/moon-audit.git
cd moon-audit
moon install && moon build --target native
# 扫描项目(一键全流程)
./moon-audit pipeline /path/to/project
# 或单独运行静态扫描
./moon-audit /path/to/project二进制位于 _build/native/debug/build/src/main/main.exe,可复制到 PATH。 也可通过 moon add minie135/moon-audit 作为库依赖使用。
moon-audit --format json /path/to/project # JSON
moon-audit --format sarif -o results.sarif /path/to # SARIF(GitHub Code Scanning)
moon-audit --fail-on-error /path/to/project # 有 Error 级别漏洞时 exit 1| 规则 ID | 描述 | 默认 | 上下文过滤 |
|---|---|---|---|
| CWE-676/unsafe-call | 危险类型转换 (unsafe_to_*/unsafe_from_*/unsafe_new) | 关闭 | 性能操作、guard body 跳过 |
| CWE-248/panic-reachable | 库代码中 abort("message") 使调用者无法恢复 | 关闭 | 裸 panic、guard-else、平台桩、契约断言跳过 |
| CWE-704/unsafe-cast | .cast() 绕过类型系统 | 关闭 | FFI 绑定文件跳过 |
| CWE-116/replace-escaping | String::replace() 仅替换首次出现,HTML 转义不完整 | 开启 | — |
| CWE-94/eval-extern | extern JS 中使用 eval()/new Function() | 关闭 | — |
| CWE-22/path-concat | 路径拼接可能导致目录穿越 | 关闭 | — |
| 规则 ID | 描述 | 默认 | 门控框架 |
|---|---|---|---|
| CWE-79/cmark-unsafe | cmark 渲染 safe=false,原始 HTML 注入 | 开启 | cmark |
| CWE-79/inner-html | inner_html() 接收动态内容,DOM XSS | 关闭 | rabbita |
| CWE-79/template-injection | HTML 响应字符串插值,反射型 XSS | 开启 | mocket/crescent |
| CWE-113/crlf-injection | HTTP 响应头注入动态值 | 开启 | 通用 |
| CWE-942/cors-credentials | CORS credentials=true 且未限制 Origin | 开启 | mocket/crescent |
| CWE-614/cookie-attrs | Cookie 缺少 HttpOnly/Secure/SameSite | 开启 | mocket/crescent |
| CWE-770/no-body-limit | 无请求体大小限制,DoS 风险 | 开启 | crescent |
| CWE-346/ws-origin | WebSocket 无 Origin 校验 | 开启 | mocket/crescent |
# .github/workflows/security.yml
name: Security Audit
on: [push, pull_request]
jobs:
audit:
runs-on: ubuntu-latest
permissions:
security-events: write
steps:
- uses: actions/checkout@v4
- uses: I3eg1nner/moon-audit@main- uses: I3eg1nner/moon-audit@main
with:
fail-on-findings: 'true' # 显式启用:发现漏洞时阻断 CI
severity: 'error' # 最低报告级别
upload-sarif: 'true' # 上传到 GitHub Securitycurl -fsSL https://cli.moonbitlang.com/install/unix.sh | bash
export PATH="$HOME/.moon/bin:$PATH"
git clone --depth 1 https://github.com/I3eg1nner/moon-audit.git /tmp/moon-audit
cd /tmp/moon-audit && moon install
moon run src/main -- --format json -o "$PROJECT_DIR/audit.json" "$PROJECT_DIR"{
"rules": {
"CWE-676/unsafe-call": { "enabled": true },
"CWE-94/eval-extern": { "enabled": false }
},
"exclude": ["_build", ".mooncakes", "*_test.mbt"]
}moon-audit --rule CWE-676/unsafe-call --rule CWE-248/panic-reachable /path/to/project
moon-audit list-rules # 查看所有规则# LLM 辅助验证(需配置 .env 中的 API Key)
moon-audit llm-analyze --format script /path/to/project
python3 llm_analyze.py
# PoC 验证脚本生成
moon-audit generate-poc -o poc.md /path/to/project
# 修复建议(含 Before/After 代码示例)
moon-audit remediate -o fixes.md /path/to/project
# 统计报告(按 CWE/OWASP 分类聚合)
moon-audit summary /path/to/projectmoon add minie135/moon-auditfn check_security(project_path : String) -> Unit {
let config = @audit.Config::default()
let result = @audit.scan_project(project_path, config)
let errors = result.findings.filter(fn(f) { f.severity == @audit.Error })
if errors.length() > 0 {
println(@audit.format_text(result, false))
}
} .mbt 源码 → Import 分析(moon.pkg/moon.mod) → AST 解析(moonbitlang/parser) → 14 条规则匹配 → 报告输出(Text/JSON/SARIF)moon check # 编译检查
moon test # 运行测试(65 个用例 × 4 编译目标)
moon fmt # 格式化Static security scanner for MoonBit projects
Dependencies