一个用户态欺骗层,将 DDoS 和机器人滥用转化为徒劳无功。
Net Ward 作为反向代理位于你的 HTTP 服务前端。真实流量原样通过。已知的探测和洪水攻击会收到无害的镜像响应,消耗机器人的精力,且永远不会到达你的应用——无需内核钩子、无需载荷、无需反击,设计上故障开放。
由 Dragon Lady 构建和维护 — github.com/Dragon-Lady · X: @answerislove2 独立安全研究员,追踪野外的实时供应链和机器人滥用活动。
网站: dragon-lady.github.io/netward-standalone
python -m pip install --upgrade "netward>=0.4.12"
python -m netward --config example_config.json
建议将 0.4.12 或更高版本作为新安装和升级的基线版本。旧版本仍可获取以用于复现;新部署应使用当前版本。
或从源码安装:
git clone https://github.com/Dragon-Lady/netward-standalone
cd netward-standalone
pip install -e .
Net Ward 监听 listen_address,并将干净流量转发至 upstream_target。
复制示例配置并编辑上游目标:
cp example_config.json config.json
在启动 Net Ward 之前,请将 upstream_target 指向一个真实的 HTTP 服务。如果上游不可达,未匹配的请求将返回默认镜像响应,而不是暴露原始代理错误。
必填字段:
| 字段 | 含义 |
|---|---|
node_id | 此 Net Ward 实例的稳定名称 |
upstream_target | 受保护的 HTTP 服务 |
listen_address | Net Ward 绑定的主机和端口 |
可选字段控制镜像强度、本地存储、网格占位符、告警通道、上游超时和探测日志保留。模式匹配或请求洪水的开始会在 SQLite 中记录一条告警。告警按类型、来源和模式去重,持续五分钟。空的 alert_channels 列表会发送到 stdout;可选择 stdout、email、slack 和 ntfy 的任意组合进行显式投递。出站投递在后台运行,并重试失败的通道。最近未投递的告警会在启动时重试。
电子邮件需要 alert_email、alert_smtp_host 和 alert_smtp_from。设置 alert_smtp_port 和 alert_smtp_security(starttls、ssl 或 none);none 仅允许用于回环 SMTP 服务器。如果需要身份验证,请将 alert_smtp_username 和 alert_smtp_password_env 设置为包含密码的环境变量的名称。Slack 需要 alert_slack_webhook。ntfy 需要 alert_ntfy_topic(ntfy.sh 上的主题或完整的自托管主题 URL);对于受保护的主题,请将 alert_ntfy_token_env 设置为包含其 bearer token 的环境变量的名称。HTTP 目标必须使用 HTTPS,回环除外。alert_timeout_secs 默认为五秒。Net Ward 在启动时检查请求的目标,并将成功的投递回执存储在 alerts 表中。告警消息包含源 IP、模式 ID 和分类;它们不包含原始请求体或标头。
| 可选字段 | 默认值 | 含义 |
|---|---|---|
upstream_timeout_total | 10 | 上游调用的整个请求预算,以秒为单位 |
upstream_timeout_connect | 3 | 连接(DNS + TCP + TLS)超时,以秒为单位 |
upstream_timeout_sock_read | 5 | 上游套接字读取之间的空闲时间,以秒为单位 |
upstream_max_concurrency | 64 | 进行中的上游请求数 |
upstream_max_body_bytes | 8388608 | 最大缓冲上游响应体(8 MiB)。更大的响应体会故障开放到默认镜像 |
probe_retention_secs | 604800 | 探测日志 TTL(7 天) |
probe_max_rows | 10000 | 写入时清除后的最大探测日志行数 |
alert_timeout_secs | 5 | 出站告警投递的每通道超时,以秒为单位 |
python -m netward --config config.json
示例拓扑:
| 组件 | 地址 |
|---|---|
| Net Ward | 127.0.0.1:8080 |
| 上游应用 | http://127.0.0.1:9000 |
| 存储 | netward.db |
将你的负载均衡器或 Web 服务器指向 Net Ward。在可能的情况下,保持上游应用仅可从主机或受信任网络访问。
仅当你确实希望 Net Ward 可在 localhost 之外访问时,才将 listen_address 设置为 0.0.0.0:<port>。
在 Linux/macOS 上,保持 storage_path 不可被所有用户写入。例如:chmod 600 netward.db,或仅当你确实需要为监控提供读取权限时才使用 chmod 644 netward.db。
Net Ward 可持续维持其文档所述的每台机器容量,但 Python 运行时内存池在持续高负载后可能会保留工作集状态。在持续高流量下运行 Net Ward 的运维人员应监控进程资源使用情况,并定期重启守护进程,例如每周一次,或在 RSS 超过基线 2 倍时重启。v0.5 将根据运维人员反馈和本地测试观察(而非自动遥测)完善此指导。
干净的请求应能到达上游:
curl -i http://127.0.0.1:8080/
已知探针应被镜像:
curl -i http://127.0.0.1:8080/wp-admin/
WordPress 探测请求会返回一个伪造的登录页面。上游服务不会收到该请求。
使用上面的示例拓扑,一次健康的首轮运行应如下所示:
127.0.0.1:9000 上启动一个小型上游服务。127.0.0.1:8080 上启动 Net Ward。/,并确认上游响应返回。/wp-admin/,并确认返回的是镜像响应。预期结果:正常流量到达上游应用,而已知的探测请求由 Net Ward 的镜像层处理。这是代理路径、模式匹配和镜像响应均正常工作的最简单信号。
安装或刷新捆绑的供应商模式集:
python -m netward.cli --db netward.db install-patterns
python -m netward.cli --db netward.db install-patterns --force
列出活动模式:
python -m netward.cli --db netward.db list-patterns
在不写入数据库的情况下读取探测报告。该报告为聚合计数:触发了哪些探测族、这些探测族命中了哪些请求路径总计,以及涉及了多少个来源。它不会打印原始 IP 地址或地理位置。--send 会投递同一份摘要——包含路径计数,绝不包含原始 IP。输出文件仅所有者可访问(0600)。
python -m netward.cli --db netward.db report
python -m netward.cli --db netward.db report --since 7d --format md --output report.md
python -m netward.cli --db netward.db report --format html --output report.html
python -m netward.cli --db netward.db report --family wordpress --top 10
python -m netward.cli --db netward.db report --send --config config.json
存储的探测日志上限为 7 天或 10,000 行。报告会描述该时间窗口并明确说明这一点。建议的更严格模式会被打印出来供审查,但不会被安装。
禁用或重新启用某个模式:
python -m netward.cli --db netward.db disable-pattern wordpress_admin_probe
python -m netward.cli --db netward.db enable-pattern wordpress_admin_probe
如果你的上游在 /admin 暴露了真实的管理面板,请在将 Net Ward 部署到该服务之前,禁用 generic_admin_login_probe 或将其替换为更严格的 operator 模式:
python -m netward.cli --db netward.db disable-pattern generic_admin_login_probe
部分厂商模式已随附提供,但默认处于禁用状态,因为如果你的上游使用了该模式所针对的同一协议特性,它们可能会破坏合法流量。
basic_auth_probe捕获通过 Authorization: Basic <base64> 进行的暴力破解凭据填充攻击。
仅在以下情况下可安全启用: 你的上游完全不使用 HTTP Basic Auth。如果你的上游接受真实用户的 Basic Auth 凭据,启用此模式会将这些用户困在无限 401 循环中——Net Ward 返回一个伪造的质询,浏览器重新提示,循环往复。
启用:
netward-cli --db netward.db enable-pattern basic_auth_probe
再次禁用:
netward-cli --db netward.db disable-pattern basic_auth_probe
启用后,要验证其是否正常工作:
curl -i -H "Authorization: Basic dXNlcjpwYXNz" http://127.0.0.1:8080/api/admin
应返回 401 并带有 WWW-Authenticate: Basic realm="Restricted"。上游不应收到该请求。
Net Ward 采用故障开放(fail-open)策略,且仅运行在用户空间:
镜像层旨在转移自动化滥用,而非对其发起反击。
登录值并非收集的产品。敏感头部(Authorization、Cookie、Set-Cookie、Proxy-Authorization 及类似项)以及类似密码的请求体或查询键,在探针写入本地数据库前会被脱敏。残余风险仍然存在:其他头部、非结构化请求体以及未使用上述键名的值,仍可能在操作员控制下被本地存储。请勿将探针日志视为凭据保险库,也请勿在公开报告中发送真实密钥。
Net Ward 不向项目维护者发送遥测数据,也不将操作员流量用于任何外部目的。
由于 Net Ward 是实时反向代理,它会保留操作员拥有的本地记录,用于检测和转移 DDoS、探测及机器人活动。这些记录可能包括源 IP、时间戳、请求路径、选定的(已脱敏)头部、已脱敏的查询字符串、请求大小、简短的已脱敏请求体片段、分类结果、模式匹配以及告警元数据,均存储于配置的本地 SQLite 数据库中。
探针行数有界:超过 probe_retention_secs 或超出 probe_max_rows 的旧数据会在写入时清除。这就是“有界日志”保证——若无这些上限,探针表将无限增长。
这些数据始终处于操作员控制之下。它不会被上传、出售、共享,也不会被 Net Ward 项目使用。其用途仅限于本地攻击点检测、滥用模式审查、告警以及改进操作员自身的转移规则。脱敏可减少意外的凭据留存;但这并不保证本地行中永远不会出现类似登录值的条目。
请勿在公开 issue 或支持请求中发送真实凭据、私有客户数据或完整流量捕获。仅分享经过净化的示例。
有关发布说明和计划改进,请参阅 CHANGELOG.md。
Net Ward 是免费且开源的,并将一直如此。 没有任何功能被付费墙限制,也没有任何功能因赞助而被保留。
如果 Net Ward 为你的服务减轻了一些困扰,并且你愿意帮助它持续测试并推进至 v0.5,支持是可选的,且始终感激不尽:
| 文件 | 用途 |
|---|---|
capture.py | 反向代理与请求捕获 |
classify.py | 模式匹配与洪泛分类 |
mirror.py | 安全镜像响应渲染 |
storage.py | SQLite 持久化 |
bootstrap.py | 供应商模式种子数据 |
cli.py | 操作员管理命令 |
report.py | 只读探针报告 |
data/vendor_patterns.json | 内置默认探针模式 |
operator_layer.py | 配置验证与告警面 |