Security Go — 攻击检测库
English · API 接口文档
Go 语言编写的攻击检测包,覆盖 36 个检测器、6 大攻击类别、3 种可插拔存储后端。统一接口 + 注册表模式,纯检测库,适配任何 Go HTTP 框架。
设计思路
核心原则
- 零依赖检测 — 所有检测器仅使用 Go 标准库
regexp,无外部依赖
- 统一接口 — 每个检测器实现
Detector 接口(Name() + Detect()),通过 Engine 注册表统一管理
- 预编译正则 — 所有模式在
var 初始化时编译,运行时零开销
- 按需配置 — 注入/协议/数据/文件检测器即插即用;HTTP 校验器与会话安全检测需应用自定义配置
设计架构
┌───────────────────────────────┐
│ security.Engine │
│ ┌─────────────────────────┐ │
│ │ Detector Registry │ │
│ │ map[string]Detector │ │
│ └─────────────────────────┘ │
│ │
│ Detect(name, input) │
│ DetectAll(input) │
│ DetectRequest(*http.Request) │
└──────────────┬────────────────┘
│
┌─────────────────┬───────────┴───────────┬─────────────────┐
│ │ │ │
┌──────▼──────┐ ┌──────▼──────┐ ┌────────────▼────────┐ ┌───▼───────────┐
│ injection │ │ protocol │ │ data │ │ file │
│ (10 个) │ │ (9 个) │ │ (5 个) │ │ (3 个) │
│ │ │ │ │ │ │ │
│ xss, sql, │ │ ssrf, xxe, │ │ deser, csv, │ │ traversal, │
│ command, │ │ header, │ │ mail, jwt, │ │ upload, │
│ nosql, │ │ host, │ │ proto_poll │ │ data_leak │
│ ldap, │ │ smuggling, │ │ │ │ │
│ xpath, │ │ redirect, │ │ │ │ │
│ jndi, ssi, │ │ cors, ws, │ │ │ │ │
│ graphql, │ │ dns_rebind │ │ │ │ │
│ ssti │ │ │ │ │ │ │
└─────────────┘ └─────────────┘ └─────────────────────┘ └───────────────┘
│
┌───────────────────────────────────────────────────────────────┤
│ │
┌──────▼──────────┐ ┌──────────▼──────────┐
│ httpval │ │ storage │
│ (7 个) │ │ ┌──────────────┐ │
│ │ │ │ Backend │ │
│ method, size, │ │ │ interface │ │
│ type, csrf, │ │ └──┬───┬───┬───┘ │
│ cookie,nested │ │ │
│ ip_blacklist │◄────── 使用 storage.Backend ──────────►│ Memory File Redis │
│ (需配置参数) │ │ │
└─────────────────┘ └────────────────────┘
┌─────────────────────────────────────────────────────────────────────┐
│ session (2) outside the Engine registry │
│ │
│ Tracker (session_guard) + Signer (data_tamper) │
│ Issue / Check / Observe / Guard / Revoke Sign / Verify │
└─────────────────────────────────────────────────────────────────────┘
session 包不经过 Engine 注册:会话校验必须读到完整的 *http.Request(token、客户端 IP、User-Agent),
且需要应用提供存储与密钥,因此直接作为中间件调用,见下文「会话安全配置」。
数据流
HTTP Request
│
▼
┌──────────────┐ ┌─────────────────┐ ┌──────────────┐
│ collectInputs│────▶│ DetectAll() │────▶│ []*Result │
│ URL, Query, │ │ 逐个检测器调用 │ │ 聚合结果 │
│ Headers, │ │ Detect(input) │ │ │
│ Cookies │ └─────────────────┘ └──────────────┘
└──────────────┘
严重程度分级
| 级别 |
说明 |
典型场景 |
SeverityLow |
低风险 |
非法 HTTP 方法、Content-Type 不匹配 |
SeverityMedium |
中风险 |
弱特征命中:CORS 配置问题、开放重定向、GraphQL 内省;以及各检测器刻意分离的无上下文模式(../、on…=、javascript:、sleep(、sqlite_master、反引号、{#…#}、__proto__:、PHP 魔术方法名),教程与正常内容里常见 |
SeverityHigh |
高风险 |
强特征命中:XSS、SQL 注入、SSRF、路径遍历、会话异常 |
SeverityCritical |
严重 |
强特征命中:命令注入、JNDI、SSTI、XXE、数据泄露、反序列化(PHP 序列化对象 / pickle / Java / .NET) |
实现功能
注入类攻击 (10)
| 检测器 |
检测模式 |
| XSS |
<script>、on[a-z]+= 事件处理器、javascript: 伪协议、SVG/CSS 注入、eval()、document.cookie |
| SQL 注入 |
UNION SELECT(含 /**/ 绕过)、sleep/benchmark/pg_sleep、布尔盲注、information_schema 枚举、xp_cmdshell |
| 命令注入 |
反引号、$()、管道符、/dev/tcp、PHP system/exec/shell_exec、链式执行 && ; || |
| NoSQL 注入 |
MongoDB $ne $gt $regex $where 操作符、$func、JSON 键注入 |
| LDAP 注入 |
过滤操作符 (|(&(!、objectClass=*、URL 编码绕过 |
| XPATH 注入 |
布尔绕过 ' or '1'='1、string-length()、count() |
| JNDI/Log4Shell |
${jndi:ldap://、${lower:j} 混淆、${env:} 环境变量、ldap/rmi/dns 协议 |
| SSI 注入 |
<!--#exec cmd=、<!--#include file=、<!--#echo var= |
| GraphQL 注入 |
__schema/__type 内省、深度嵌套 DoS(5层+)、mutation 检测 |
| SSTI |
Jinja2 {{}}、FreeMarker ${}、ERB <% %>、Python MRO 遍历、config/self 访问 |
协议与请求攻击 (9)
| 检测器 |
检测模式 |
| SSRF |
内网 IP(127/10/172.16/192.168)、169.254.169.254、IPv6 loopback、gopher/dict/file/ftp 协议 |
| XXE |
<!ENTITY SYSTEM/PUBLIC、参数实体 %entity;、DOCTYPE 声明 |
| HTTP 头注入 |
CRLF %0d%0a / \r\n、Set-Cookie/Location/Content-Length 注入 |
| Host 头攻击 |
CRLF Host 注入、X-Forwarded-Host、X-Original-URL 投毒 |
| 请求走私 |
Transfer-Encoding/Content-Length 不一致、双重 TE 头、\x0b 折叠头混淆 |
| 开放重定向 |
//evil.com 协议相对 URL、javascript:/data: 伪协议 |
| CORS 绕过 |
Origin: null、Access-Control-Allow-* 头注入 |
| WebSocket 劫持 |
Upgrade 头注入、null Origin 绕过、ws:// URL |
| DNS 重绑定 |
Host 头内网 IP、localhost、无 TLD 短主机名 |
HTTP 协议层校验 (7)
| JSON 嵌套深度 | json.Decoder 流式扫描:嵌套层级或元素数超限即判 JSON 炸弹(默认深度 32);非法或截断 JSON 不告警 |
| Cookie 属性校验 | Set-Cookie 缺 Secure/HttpOnly/SameSite、值超长或为空;缺失属性合并为一条结果 |
| 检测器 |
说明 |
| HTTP 方法 |
仅允许 GET/POST/PUT/DELETE/HEAD/OPTIONS/PATCH,其他返回告警 |
| 请求体大小 |
超过上限(默认 10MB)触发告警 |
| Content-Type |
仅允许配置的 MIME 类型白名单 |
| CSRF Origin |
检测跨域请求 Origin 与 Host 是否匹配,支持额外白名单 |
| IP 黑名单 |
窗口时间 N 次攻击后自动封禁(默认 5次/60s→封禁15分钟),支持 File/Redis/Memory 存储 |
数据与序列化攻击 (5)
| 检测器 |
检测模式 |
| 反序列化 |
O:数字: / C:数字: 序列化对象、unserialize()、魔术方法(__wakeup/__destruct);覆盖 PHP / pickle / Java / .NET 四类载荷 |
| CSV 注入 |
=cmd|、@SUM(、+/- 公式前缀、HYPERLINK/DDE |
| 邮件头注入 |
Bcc/Cc/From/To 注入、MIME multipart、boundary 参数 |
| JWT 攻击 |
alg: none 绕过、kid 路径遍历、空签名检测(结构解码分析) |
| 原型污染 |
__proto__/constructor 键、__defineGetter__/__defineSetter__ |
文件与敏感数据 (3)
| 检测器 |
检测模式 |
| 路径遍历 |
../、..\\、php://filter/php://input、null 字节、URL 编码绕过、/etc/passwd |
| 恶意上传 |
扩展名白名单(15种)+ PHP 标签 <?php/<?= 内容扫描 |
| 数据泄露 |
信用卡号、AWS Access Key、私钥 -----BEGIN、数据库连接串、API Token、JWT Secret、GitHub PAT |
会话安全 (2)
| 检测器 |
检测模式 |
会话守护 (session_guard) |
token 与会话建立时的客户端绑定,逐请求比对:User-Agent 或设备指纹变化判定客户端被劫持(Critical);客户端 IP 落到其他网段或国家判定异地登录(High/Critical);Observe() 在登录时比对历史网段,出现新网段即告警。会话滑动续期,Revoke() 可立即失效;RecordFailure() 累计失败次数,窗口内超阈值即锁定 token,Check() 报 token_locked,ClearFailures() 在登录成功时清零;CheckLogin() 另行拦截撞库(同一 IP 失败过的不同身份数达上限报 credential_stuffing),且锁定时长逐次翻倍(上限 24h) |
数据篡改 (data_tamper) |
对请求参数做 HMAC-SHA256 签名(时间戳.nonce.签名),识别参数改动、密钥不符、时间戳超差、签名重放(nonce 计数器) |
存储后端 (3)
| 后端 |
说明 |
| Memory |
sync.Mutex + map,30s 自动清理过期条目 |
| File |
JSON 文件持久化,Close 时 flush |
| Redis |
独立子模块,Pipeline Incr + TTL,需 go-redis/v9 |
使用说明
安装
go get github.com/erikwang2013/security-go
快速开始
package main
import (
"fmt"
"github.com/erikwang2013/security-go"
"github.com/erikwang2013/security-go/all"
)
func main() {
e := security.NewEngine()
all.RegisterAll(e) // 一键注册 27 个零配置检测器
// 单个检测
r := e.Detect("xss", "<script>alert(1)</script>")
fmt.Printf("检测到: %v, 严重程度: %d\n", r.Detected, r.Severity)
// 全量检测
for _, r := range e.DetectAll("' OR '1'='1") {
fmt.Printf("[%s] %s\n", r.Name, r.Message)
}
}
HTTP 请求检测
func handler(w http.ResponseWriter, r *http.Request) {
e := security.NewEngine()
all.RegisterAll(e)
for _, result := range e.DetectRequest(r) {
if result.Detected {
log.Printf("攻击检测: [%s] %s", result.Name, result.Message)
}
}
}
HTTP 校验器配置
// 方法校验
e.Register(&httpval.Method{})
// 请求体大小限制
e.Register(httpval.NewBodySize(5 * 1024 * 1024)) // 5MB
// Content-Type 白名单
e.Register(httpval.NewContentType([]string{
"application/json", "application/x-www-form-urlencoded",
}))
// CSRF Origin 检查
e.Register(&httpval.CSRFOrigin{
Host: "example.com", AllowList: []string{"api.example.com"},
})
// IP 黑名单(自动封禁:5次/60s → 封禁15分钟)
mem := storage.NewMemory()
defer mem.Close()
bl := httpval.NewIPBlacklist(mem)
e.Register(bl)
// 攻击发生时记录
blocked, _ := bl.RecordAttack(clientIP)
会话安全配置
session 包直接作为中间件使用,不经过 Engine。存储需应用自备(默认提供内存实现,可替换为 Redis 等):
import "github.com/erikwang2013/security-go/session"
st := session.NewMemoryStore()
defer st.Close()
tr := session.NewTracker(st)
tr.CountryOf = geo.Lookup // 可选:接入 GeoIP,用于识别跨国家登录
// 登录成功后绑定会话(token 由你的登录流程生成)
// 异地登录检测:比对该用户历史登录网段,出现新网段即告警
if res := tr.Observe("user-1", r); res.Detected {
log.Printf("[%s] %s (%v)", res.Name, res.Message, res.Details["reason"])
}
if err := tr.Issue(token, r); err != nil { // 绑定 token → IP 网段 / UA / 设备指纹
http.Error(w, "session error", http.StatusInternalServerError)
return
}
// 保护路由:命中劫持或异地登录直接返回 401
mux.Handle("/api/", tr.Guard(apiHandler))
// 或只做检测、自行决定处置
if res := tr.Check(r); res.Detected {
log.Printf("[%s] %s (%v)", res.Name, res.Message, res.Details["reason"])
}
// 登出
tr.Revoke(token)
数据篡改检测:客户端与服务端共享密钥,客户端对参数签名,服务端重算校验:
signer := session.NewSigner(secret, storage.NewMemory()) // 第二个参数用于拦截签名重放,可为 nil
sig, _ := signer.Sign(map[string]string{"amount": "100", "to": "bob"}) // 客户端:随参数一起提交
if res := signer.Verify(map[string]string{"amount": "100", "to": "bob"}, sig); res.Detected {
log.Printf("[%s] %s (%v)", res.Name, res.Message, res.Details["reason"])
}
TrustProxyHeaders 默认关闭:X-Forwarded-For / X-Real-IP 由客户端可控,仅在自有反向代理后开启。
FailClosed 默认关闭(存储故障时放行,与 IPBlacklist 一致);对会话敏感的业务建议开启。
自定义检测器
type MyDetector struct{}
func (d *MyDetector) Name() string { return "my_detector" }
func (d *MyDetector) Detect(input string) *security.Result {
return &security.Result{
Name: "my_detector", Detected: strings.Contains(input, "evil"),
Severity: security.SeverityHigh, Message: "检测到恶意内容",
}
}
e.Register(&MyDetector{})
相关文档
- API 接口文档 — 核心类型、Detector/Engine 接口、存储后端接口、HTTP 校验器
- 设计规范 — 包结构、检测器目录
- 实施计划 — 分步任务计划与实施偏差对照
- 代码审查报告 — Bug 修复、测试覆盖、架构评估
多语言文档
捐赠支持
如果这个项目对你有帮助,欢迎打赏支持:
| 方式 |
二维码 |
| 支付宝 |
 |
| 微信支付 |
 |
全球转账打赏(银行汇款)
收款人信息
- 收款人姓名:WANG KEXUN
- 收款账户号码:881015918251
收款银行(ZA Bank)
- SWIFT Code:
AABLHKHHXXX
- 银行名称:ZA Bank Limited
- 银行编号:387
- 银行地址:Core F, Cyberport 3, 100 Cyberport Road, Hong Kong
跨境汇款代理银行(如需)
请留意,此为跨境汇款代理银行(中转银行)信息,非收款银行信息。请向汇款银行查询是否需要提供跨境汇款代理银行信息。
- 汇入港元、人民币及美元的代理银行为 Citibank:
- 银行名称:Citibank N.A. Hong Kong
- SWIFT Code:
CITIHKHXXXX
- 银行编号:006
- 分行名称:Hong Kong Branch
- 分行编号:391
- 银行地址:Citibank Tower, Citibank Plaza, 3 Garden Road, Central, Hong Kong
- 汇入其他币种时的代理银行为 BNY Mellon:
- 银行名称:THE BANK OF NEW YORK MELLON
- SWIFT Code:
IRVTUS3NXXX
- 银行地址:THE BANK OF NEW YORK MELLON, 240 GREENWICH STREET, NEW YORK, United States
English
See README-EN.md for the full English documentation.
Copyright (c) 2026 erik erik@erik.xyz — https://erik.xyz