Rust · 无 Docker · 单文件二进制

用 Rust 子进程管好你的
一堆 JS / Python 服务

Maylin 是一个服务集群管理器:以 Rust 子进程 + 插件 直接拉起任意数量的实例, 每个实例独占端口、互不干扰,不需要 Docker。内置多服务器集群、RBAC Token API、 WebSocket 终端、cron 定时启动与反向代理负载均衡。

CI Release License Platform
10,902LB 转发 RPS(p99 47.7ms)
61,000API RPS(p99 5.3ms)
0故障转移失败请求
~2000行 Rust,零运行时依赖

核心能力

每一块都可以单独用,也可以组合成一个小型集群编排层。

⚙ 无 Docker 多子进程

直接托管 JS / Python / Go / 任意二进制,CREATE_NO_WINDOW 防弹窗、kill_on_drop 防孤儿,每个实例独占端口。

🧩 插件化运行时

新增一种运行时只需写一个 toml:command + args,支持 {script} {port} {name} 占位符。

🛡 supervisor 守护

崩溃按策略自动拉起,指数退避(2s×n,上限 30s),超过 max_retries 熔断并告警,绝不无限重启。

🌐 多服务器集群

各节点 peers 互配,状态聚合查询、restart all 动作广播,负载均衡上游可混合跨机实例。

🔑 RBAC Token API

三级角色 admin / operator / viewer,全部 REST 与 WebSocket 强制 Bearer Token,按方法与路径判权。

⌨ 命令终端

ctl terminal 直连实例 stdin/stdout 做交互调试,ctl exec 在节点上跑 shell 命令(带并发上限)。

⏱ cron 定时启动

标准 5 段 cron 驱动 start / stop / restart,target 支持实例名或 all,配置热加载不重启进程。

📊 负载均衡 + 可观测

round-robin + 健康探活摘除 + 请求级失败重试;事件环缓冲、JSONL 落盘、webhook 告警、状态快照。

架构

一个控制面(API / 终端 / 调度)+ 一个数据面(进程与端口),控制面故障不影响已运行实例。

maylin ctl CLI 客户端 HTTP API REST + WS 终端 浏览器 / 其他系统 Bearer Token RBAC admin/op/viewer maylind 节点 进程管理器 supervisor · 优雅停止 插件运行时 node · python · binary cron 调度器 start / stop / restart 负载均衡 轮询 · 摘除 · 重试 事件 / 告警 / 状态快照 events.jsonl · webhook · state.json api-node :3001 api-py :3002 worker :3003 …

快速开始

首次启动会自动生成 config/ 目录、随机访问令牌与 demo 示例,30 秒内可跑通全流程。

bash
# 1. 构建(或直接从 Releases 下载预编译二进制)
cargo build --release

# 2. 启动节点(首次运行自动生成 config/ 与随机 Token)
./target/release/maylin node --config config/maylin.toml

# 3. 配置客户端
export MAYLIN_TOKEN=<config/maylin.toml 里的 tokens[0]>
export MAYLIN_URL=http://127.0.0.1:7000

# 4. 管理实例
maylin ctl start demo-node        # 拉起 Node 实例 :3001
maylin ctl start demo-python      # 拉起 Python 实例 :3002
maylin ctl status                 # 节点状态 + 指标
maylin ctl logs demo-node --lines 50
maylin ctl terminal demo-node     # 交互式终端
maylin ctl events --limit 20      # 事件审计
maylin ctl cluster                # 集群聚合状态

# 5. 负载均衡 :8000 → 轮询 :3001 / :3002,停掉一个也零失败
curl http://127.0.0.1:8000/

HTTP API

全部接口需 Authorization: Bearer <token>,WebSocket 可用 ?token=。写操作按角色校验权限。

方法路径说明
GET/api/status节点状态(实例 + LB + 集群 + metrics)
GET POST/api/instances实例列表 / 创建实例(JSON)
GET/api/instances/{name}实例详情(状态 / pid / 重试次数)
POST/api/instances/{name}/start启动实例
POST/api/instances/{name}/stop优雅停止(宽限后强杀)
POST/api/instances/{name}/restart重启实例
GET/api/instances/{name}/logs?lines=100实例日志
WS/api/instances/{name}/terminalWebSocket 终端(stdin / stdout)
POST/api/exec在节点执行 shell 命令(并发受限)
GET/api/events?limit=100事件流(启动 / 退出 / 重启 / 摘除 / 认证失败)
GET/api/plugins /api/schedules插件与定时任务
POST/api/reload重新扫描配置目录(不影响运行中实例)
GET/api/lb/status负载均衡上游健康状态
GET POST/api/cluster/status /api/cluster/action集群聚合状态 / 动作广播

实测与工程细节

数据来自本机 release 构建(examples/loadtest.rs,可自行复现)。

压测结果

  • LB 反向代理:并发 100 × 5000 请求 → 10,902 RPS,p99 47.7ms
  • 控制面 API:并发 50 × 2000 请求 → 61,000 RPS,p99 5.3ms
  • 故障转移:停掉一个上游后连续请求零失败(请求级重试到存活上游)
  • E2E:cargo 集成测试拉起真实节点,18.5 秒验证 11 步全链路

踩过的坑(已固化)

  • Windows 命名管道不可用:Rust std / tokio 建匿名管道报 os error 231 → 改用经典 CreatePipe + 阻塞泵线程
  • 管道 EOF 永不到达:改读端为 PeekNamedPipe 轮询 + 退出标志排空,不依赖 EOF
  • 系统代理劫持回环流量:内部健康检查 / 转发 / 集群通信全部 no_proxy() 直连
  • 跨平台:Windows 一套管道实现,unix 走 std::io::pipe + BufRead,SIGTERM 分支隔离