Skip to content

Repository files navigation

SubMesh

轻量级分布式订阅网关:一个中央管理后台统一配置策略和查看日志,每台物理入口机只运行一个小型 Agent;一台机器上的多个宝塔/Nginx站点可分别接入同一个 Agent。

架构

                            SubMesh Server
                      管理后台 / 策略 / 日志分析
                                  ▲
                         HTTPS 心跳、策略、日志
                                  │
       ┌──────────────────────────┴──────────────────────────┐
       │                                                     │
  物理机 host-01                                       物理机 host-02
  ├─ 直连站点 B ─→ 127.0.0.1:18081 ┐                  IP+端口站点 A
  ├─ CDN 站点 C ─→ 127.0.0.1:18082 ├→ 一个 Agent ─┐       │
  └─ 其他站点   ─→ 127.0.0.1:18083 ┘              │    一个 Agent
                                                   └────┬────┘
                                                        ▼
                                                    机场源站

Nginx/宝塔负责公网入口、域名和 TLS;Agent 在本机完成真实 IP 识别、规则拦截、限速和反向代理。中央服务不承载订阅流量,只负责管理,因此后台暂时离线不会阻断边缘转发。

当前 MVP 能力

  • Vue 3 + TypeScript 管理后台,构建后嵌入 Go 二进制
  • 一个物理节点运行一个 Agent,一个 Agent 承载多个入口站点
  • IP/CIDR 黑白名单、云厂商 CIDR、UA 关键词和 Token 指纹黑名单
  • 每 IP 每分钟限速
  • 集中请求日志,按节点/站点记录
  • 同 Token 多 IP、同 IP 多 Token 可疑行为分析
  • 中央 ip2region IPv4/IPv6 离线归属地查询(国家、省市、运营商)
  • 云厂商网段每日自动更新、厂商标注及可选自动拦截
  • 管理后台 History 路由,刷新保留概览/日志/规则/节点/设置页面
  • Element Plus 组件化管理后台,刷新时静默校验会话,不闪现登录页面
  • 请求日志显示原始订阅 Token,便于在 V2Board 等机场后台定位用户
  • 同时保留 SHA-256 Token 指纹,用于稳定统计和黑名单匹配
  • 节点独立随机密钥,策略自动拉取并本地缓存
  • 中央服务离线时继续使用最后一次有效策略
  • systemd、宝塔/原生 Nginx配置模板
  • 单个静态 Go 二进制,无 Docker、无 PHP、无运行时 Node.js

快速开发

要求 Go 1.23+、Node.js 20+ 和 pnpm 10+:

make all
SUBMESH_ADMIN_PASSWORD='change-me-now' ./bin/submesh server

打开 http://127.0.0.1:9090,默认用户名为 admin

部署中央服务

发布 GitHub Release 后,在中央服务器执行:

curl -fsSL https://raw.githubusercontent.com/PangHu-Code/SubMesh/main/scripts/install-server.sh | sudo bash

服务只监听 127.0.0.1:9090。在宝塔创建一个 HTTPS 站点,将其反代到:

http://127.0.0.1:9090

配置片段见 deploy/nginx/control-panel.conf。管理后台应使用 HTTPS,并建议限制管理员来源 IP。

进入后台后:

  1. 配置机场真实上游,例如 http://10.0.0.8:8080https://origin.example.com
  2. 配置机场真实订阅路径。
  3. 在“节点”页面创建物理节点,复制仅显示一次的节点密钥。

部署 Agent

在每台物理入口机执行一次:

curl -fsSL https://raw.githubusercontent.com/PangHu-Code/SubMesh/main/scripts/install-agent.sh \
  | sudo bash -s -- https://你的中央后台域名 hk-host-01 节点密钥

中国大陆机器无法稳定连接 GitHub 时,可让安装脚本及其内部下载统一经过 GitHub 加速前缀:

curl -fsSL "https://ghfast.top/https://raw.githubusercontent.com/PangHu-Code/SubMesh/main/scripts/install-agent.sh" \
  | sudo env SUBMESH_GITHUB_PROXY="https://ghfast.top/" bash -s -- \
      https://你的中央后台域名 hk-host-01 节点密钥

Agent 默认创建一个站点:

site-1 → 127.0.0.1:18081

升级

中央服务和 Agent 均可使用同一升级脚本;中央服务会同时更新离线 IP 库,并保留管理员密码、节点和策略,Agent 会保留多站点配置:

curl -fsSL "https://ghfast.top/https://raw.githubusercontent.com/PangHu-Code/SubMesh/main/scripts/update.sh" \
  | sudo env SUBMESH_GITHUB_PROXY="https://ghfast.top/" bash

安装支持自更新的版本后,中央服务和 Agent 以后直接执行以下命令即可。更新会校验 Release 的 SHA-256;中央 IP 数据库未变化时会自动跳过下载:

sudo submesh update

国内节点如需 GitHub 加速:

sudo submesh update --github-proxy https://ghfast.top/

编辑 /etc/submesh-agent/config.json 可在同一机器增加更多站点:

{
  "control_url": "https://panel.example.com",
  "node_id": "hk-host-01",
  "node_secret": "节点独立密钥",
  "data_dir": "/var/lib/submesh-agent",
  "policy_interval_seconds": 15,
  "sites": [
    {
      "id": "site-b-direct",
      "listen": "127.0.0.1:18081",
      "public_path": "/api/v1/client/subscribe",
      "upstream": ""
    },
    {
      "id": "site-c-cdn",
      "listen": "127.0.0.1:18082",
      "public_path": "/api/v1/client/subscribe",
      "upstream": ""
    }
  ]
}

upstream 留空时使用中央后台的默认上游;填写时可为该站点覆盖上游地址。修改后执行:

systemctl restart submesh-agent
systemctl status submesh-agent
journalctl -u submesh-agent -f

宝塔/Nginx站点接入

直连域名、IP+端口

反代到对应的本机 Agent 端口,并覆盖外部传入的真实 IP 请求头:

location ^~ /api/v1/client/subscribe {
    access_log off;
    proxy_pass http://127.0.0.1:18081;
    proxy_set_header Host $host;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $remote_addr;
}

完整片段见 deploy/nginx/site-direct.conf。Agent 只允许监听回环地址,公网用户不能绕过 Nginx直接访问它。

CDN + 宝塔站点

套 CDN 的站点必须先让 Nginx只信任 CDN 官方出口网段,从 CDN 头恢复用户 IP,再传给 Agent:

set_real_ip_from CDN官方出口网段;
real_ip_header X-Forwarded-For;
real_ip_recursive on;

location ^~ /api/v1/client/subscribe {
    access_log off;
    proxy_pass http://127.0.0.1:18082;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $remote_addr;
}

参考 deploy/nginx/site-cdn.conf。这些 real_ip 规则只能放在 CDN 站点的 server 中,不能全局应用到同机直连站点,否则直连用户可能伪造 IP。还应通过 CDN 回源认证或防火墙避免绕过 CDN 直连源站。

数据与安全边界

  • 中央状态:/var/lib/submesh/server/state.json
  • 中央事件:/var/lib/submesh/server/events.jsonl
  • IP 归属地库:/var/lib/submesh/server/intel/ip2region_v4.xdbip2region_v6.xdb
  • 云厂商网段:/var/lib/submesh/server/intel/cloud-prefixes.json
  • Agent 缓存策略:/var/lib/submesh-agent/policy.json
  • Agent 只信任来自本机回环 Nginx 的 X-Real-IP
  • Agent 到中央服务必须使用 HTTPS;第一版采用每节点 Bearer 密钥,后续升级 mTLS
  • 管理 Session 使用 HttpOnly、SameSite=Strict Cookie 和 CSRF Token
  • 上游 URL 支持 HTTP/HTTPS 与 IP+端口,不要求域名

当前限制

这是第一版 MVP,发布生产前仍计划补充:

  • Agent 磁盘事件队列;当前网络失败期间只保留最多约 2000 条内存事件
  • 日志轮转、分页和长期聚合存储
  • 规则作用域(全局/节点/站点)与临时封禁
  • 节点 mTLS 注册、密钥轮换和吊销
  • Agent 灰度升级与失败回滚
  • 主服务高可用和备份工具

License

MIT

About

No description, website, or topics provided.

Resources

Stars

1 star

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages