Docs/ 基础设施/ 多服务器

多服务器

将您拥有的其他服务器接入同一个 sh0 安装,并在其上运行部分应用。主服务器保留控制面板、构建和路由。

Note
本页描述的是 sh0 v1.10.2 代码中实现的行为。多服务器部署需要 Business 许可证。

前提条件

  • Business 许可证,以及 admin 或 owner 角色:否则所有节点接口都会被拒绝。
  • 远程服务器上:已安装并运行 Docker。sh0 不会在其上安装任何东西。
  • 主服务器能通过 SSH 访问远程服务器,且所用用户能访问 Docker 套接字(/var/run/docker.sock):root 或 docker 组成员。
  • 事先在控制面板中(SSH 密钥管理)登记的 SSH 密钥,或该用户的密码。

工作原理

  • 主服务器保留数据库、控制面板和 Caddy。节点只运行容器;sh0 通过 SSH 隧道操作其 Docker。
  • 镜像总是在主服务器上构建,然后传输到节点(部署过程会显示 transferring 步骤)。
  • 域名仍然指向主服务器。其 Caddy 通过同一 SSH 隧道中的中继,将每个请求转发到节点上的容器。
  • 内部名称(my-api.internal)只在同一台服务器内解析:节点上的应用无法通过该名称访问位于另一台服务器上的同项目服务。当项目跨越多个节点时,构建日志会给出警告。

添加节点

  1. 在控制面板中打开 Nodes,然后点击 Add Node。
  2. 填写 Name(小写字母、数字和连字符,最多 64 个字符)和 Hostname(IP 地址或 DNS 名称;localhost 和回环地址会被拒绝)。
  3. 设置 SSH Port(默认 22)、Username(默认 root)和 Authentication:SSH Key 或 Password。
  4. 保存后使用 Test Connection:sh0 会检查 SSH 连接和节点上的 Docker。

通过命令行(nodes create 可用 --port 指定非标准 SSH 端口,可用 --password 代替 --ssh-key):

Terminal
sh0 nodes create --name worker-1 --host 203.0.113.20 --ssh-user root --ssh-key <ssh-key-id>
sh0 nodes list
sh0 nodes info <node-id>
sh0 nodes test <node-id>

通过 API:

Terminal
curl -X POST https://panel.example.com/api/v1/nodes \
  -H "Authorization: Bearer $SH0_TOKEN" -H "Content-Type: application/json" \
  -d '{"name":"worker-1","hostname":"203.0.113.20","port":22,"username":"root","auth_method":"ssh_key","ssh_key_id":"<ssh-key-id>"}'
  • port、username 和 auth_method 为可选项(22、root、ssh_key)。使用 "auth_method":"password" 时,请发送 password 而非 ssh_key_id;密码会加密保存。
  • 自 1.10.3 起:节点创建后 sh0 会立即尝试连接:成功时状态变为 online,失败时变为 error 并附带消息。尝试最多 15 秒:地址无响应时,节点以 error 状态记录,CLI 以退出码 1 结束,并提示用 nodes test 重试、用 nodes delete 删除。
  • 节点的 SSH 主机密钥在首次连接时记录,之后每次校验。如果服务器重装,密钥改变,连接会被拒绝:请重置指纹(POST /api/v1/nodes/<id>/reset-fingerprint),让下一次连接记录新密钥。

部署到节点

从 Git 仓库、Dockerfile、Docker 镜像、框架或压缩包创建应用时,Target Node 字段用于选择服务器;通过 API 时发送 node_id(节点 ID 或名称)。空值表示主服务器;不匹配任何节点的值会被拒绝,而不会悄悄部署到主服务器。

Warning
模板和 Docker Compose 栈只能部署在主服务器上。为它们选择节点会被拒绝:“Templates and Compose stacks can only be deployed on the primary server for now.”

迁移应用

通过 PATCH /api/v1/apps/<id> 修改应用的 node_id 即可迁移。应用必须先停止;否则修改会被拒绝,因为其容器会继续在旧服务器上运行。空字符串表示迁回主服务器。

Terminal
curl -X PATCH https://panel.example.com/api/v1/apps/<app-id> \
  -H "Authorization: Bearer $SH0_TOKEN" -H "Content-Type: application/json" \
  -d '{"node_id":"worker-1"}'

然后重新部署应用:镜像在主服务器上构建并传输到新节点。旧节点上的容器不会被迁移,卷中的数据也不会跟随:请自行复制。

节点状态

Nodes 列出每台服务器的状态(Online、Pending、Error、Offline)、Docker 版本、CPU、内存以及最后联系时间。监控程序每 30 秒复查一次节点,并在重新连接后为运行中的应用重新建立中继。

移除节点

只有当节点上不再分配任何应用时才能移除:“Cannot delete node: N app(s) still assigned. Migrate them first.” 请先迁移或删除这些应用,然后在 Nodes 中删除节点,或使用 sh0 nodes delete <节点 ID>、DELETE /api/v1/nodes/<id>。

限制

  • 主服务器是单点故障。它一旦停止,控制面板、构建以及通往所有节点的路由都会随之停止。
  • 所有流量都经过主服务器。请求经由 SSH 中继到达节点;请据此规划主服务器的带宽。
  • 没有自动调度。sh0 不会替您选择节点,也不会把副本分布到多个节点:每个应用只在一台服务器上运行。
  • 没有排空或自动迁移。清空节点意味着逐个停止、迁移并重新部署其上的应用。
  • 没有跨服务器网络。见上文关于内部名称的说明。
  • 在命令行中请使用节点 ID。sh0 nodes test、info 和 delete 声称接受 “Node ID or name”,但在 v1.10.2 中只能按 ID 找到。