news 2026/9/14 7:10:29

如何在同一台 VPS 上部署多个 Agent Zero 实例并隔离端口、目录与域名?

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
如何在同一台 VPS 上部署多个 Agent Zero 实例并隔离端口、目录与域名?

如何在同一台 VPS 上部署多个 Agent Zero 实例并隔离端口、目录与域名?

【免费下载链接】agent-zeroAgent Zero AI framework项目地址: https://gitcode.com/GitHub_Trending/ag/agent-zero

Agent Zero 的官方 VPS 部署指南 vps-deployment.md 在附录Multi-Instance Setup中给出了同一台服务器运行多个独立实例的方案:每个实例使用独立的容器名、主机端口、数据目录、域名/子域名和 Apache vhost 配置。本文按该指南给出从第一个实例到第二、第三个实例的完整部署路径,并附验证与常见故障处理。

适用前提(均来自该指南):

  • 服务器:支持 Docker 的 Linux(AlmaLinux、CentOS、Rocky、Ubuntu、Debian),64 位,静态 IP
  • 资源:RAM 最低 2 GB(推荐 4 GB 以上)、存储最低 20 GB(推荐 50 GB 以上)、CPU 最低 1 vCPU(推荐 2 以上)
  • 软件:Docker Engine 24.0+;Apache 2.4+,需mod_proxymod_proxy_httpmod_proxy_wstunnelmod_sslmod_rewrite
  • 权限:root 或 sudo、SSH 访问、可控 DNS 的域名/子域名、SSL 证书(Let's Encrypt 或商业证书)

规划隔离维度:端口、目录、域名、vhost

指南列出多实例环境下每个实例必须满足的条件:

  • 唯一的容器名
  • 唯一的主机端口
  • 独立的数据目录
  • 独立的域名/子域名
  • 独立的 Apache vhost 配置

指南给出的端口规划是:

主机端口用途
50080第一个 A0 实例(反向代理场景的标准/推荐端口)
50081第二个实例
50082第三个实例
80HTTP(仅用于重定向到 HTTPS)
443HTTPS(主要访问入口)

按此规划三个实例(实例名可按需替换):

实例容器名主机端口数据目录
主实例a0-primary50080/opt/a0-primary
开发实例a0-dev50081/opt/a0-dev
备份实例a0-backup50082/opt/a0-backup

域名方面,每个实例准备一个不同的子域名,指南示例使用a0.example.com这类格式,替换为你实际控制的域名即可。

准备 Docker(所有实例共用,只需一次)

Debian/Ubuntu:

apt-get update apt-get install -y ca-certificates curl gnupg install -m 0755 -d /etc/apt/keyrings curl -fsSL https://download.docker.com/linux/ubuntu/gpg | gpg --dearmor -o /etc/apt/keyrings/docker.gpg chmod a+r /etc/apt/keyrings/docker.gpg echo "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.gpg] https://download.docker.com/linux/ubuntu $(. /etc/os-release && echo "$VERSION_CODENAME") stable" | tee /etc/apt/sources.list.d/docker.list > /dev/null apt-get update apt-get install -y docker-ce docker-ce-cli containerd.io docker-compose-plugin systemctl enable docker systemctl start docker

AlmaLinux/Rocky/CentOS/RHEL:

dnf -y install dnf-plugins-core dnf config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo dnf -y install docker-ce docker-ce-cli containerd.io docker-compose-plugin systemctl enable docker systemctl start docker

验证 Docker 可用:

docker --version docker run hello-world

指南还提供一个get.docker.com通用脚本路径,但明确标注它可能不适用于所有发行版(如 AlmaLinux);更多安装方式可参考 安装指南。

部署第一个实例 a0-primary

1. 创建数据目录

A0_NAME="a0-primary" A0_PATH="/opt/${A0_NAME}" mkdir -p ${A0_PATH} mkdir -p ${A0_PATH}/work_dir mkdir -p ${A0_PATH}/memory mkdir -p ${A0_PATH}/logs

2. 创建 .env 认证配置

cat > ${A0_PATH}/.env << 'EOF' # Authentication (REQUIRED for web access) AUTH_LOGIN=your_username_here AUTH_PASSWORD=your_secure_password_here EOF

指南特别强调:AUTH_LOGIN用户名,不是启用开关。AUTH_LOGIN=admin正确,AUTH_LOGIN=true错误。密码建议至少 8 位;避免在密码中使用' " \$` 等字符(或谨慎转义)。

3. 拉取镜像并启动容器

docker pull agent0ai/agent-zero:latest docker run -d \ --name a0-primary \ --restart unless-stopped \ -p 50080:80 \ -v /opt/a0-primary/.env:/a0/.env \ -v /opt/a0-primary/usr:/a0/usr \ agent0ai/agent-zero:latest

容器内监听 80 端口,映射到主机 50080;.env挂到/a0/.env/a0/usr(实例数据)挂到独立目录。

4. 验证第一个实例

docker ps | grep a0-primary docker logs a0-primary curl -I http://127.0.0.1:50080/

启用认证时的预期响应是HTTP/1.1 302 FOUNDLocation: /login(指南给出的预期输出)。

部署第二、第三个实例

重复同一流程,只改变四处值:容器名、主机端口、数据目录、.env 路径。指南附录给出的第二个实例是a0-dev、端口 50081、目录/opt/a0-dev

A0_NAME="a0-dev" A0_PATH="/opt/${A0_NAME}" mkdir -p ${A0_PATH} mkdir -p ${A0_PATH}/work_dir mkdir -p ${A0_PATH}/memory mkdir -p ${A0_PATH}/logs

/opt/a0-dev/.env写入同模板的AUTH_LOGIN/AUTH_PASSWORD(指南的 .env 模板注释说明:Copy and customize for each instance,即每个实例各配一份),然后启动:

docker run -d \ --name a0-dev \ --restart unless-stopped \ -p 50081:80 \ -v /opt/a0-dev/.env:/a0/.env \ -v /opt/a0-dev/usr:/a0/usr \ agent0ai/agent-zero:latest

第三个实例a0-backup同理:目录/opt/a0-backup,端口 50082。每个实例完成后都执行上一节的验证(docker psdocker logscurl -I http://127.0.0.1:<对应端口>/)。

为每个实例配置域名与 Apache 反向代理

启用所需模块

# Debian/Ubuntu a2enmod proxy proxy_http proxy_wstunnel ssl rewrite headers systemctl restart apache2 # AlmaLinux/CentOS(通常预载,用下面命令确认) httpd -M | grep -E "proxy|rewrite|ssl"

每个域名一个 vhost

标准 Apache(Debian/Ubuntu)下,为主实例创建/etc/apache2/sites-available/a0-primary.conf

# HTTP - Redirect to HTTPS <VirtualHost *:80> ServerName a0.example.com ServerAlias www.a0.example.com RewriteEngine On RewriteCond %{HTTPS} off RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301] </VirtualHost> # HTTPS - Proxy to Container <VirtualHost *:443> ServerName a0.example.com ServerAlias www.a0.example.com ServerAdmin webmaster@example.com SSLEngine on SSLCertificateFile /path/to/certificate.crt SSLCertificateKeyFile /path/to/private.key SSLCertificateChainFile /path/to/chain.crt ProxyPreserveHost On ProxyPass / http://127.0.0.1:50080/ ProxyPassReverse / http://127.0.0.1:50080/ # WebSocket Support (Required for real-time features) RewriteEngine On RewriteCond %{HTTP:Upgrade} websocket [NC] RewriteCond %{HTTP:Connection} upgrade [NC] RewriteRule ^/?(.*) ws://127.0.0.1:50080/$1 [P,L] ErrorLog ${APACHE_LOG_DIR}/a0-primary.error.log CustomLog ${APACHE_LOG_DIR}/a0-primary.access.log combined </VirtualHost>

第二个、第三个实例各建一份 conf,需要改的值:

  • ServerName/ServerAlias:换成该实例的子域名
  • ProxyPass/ProxyPassReverse/RewriteRule目标端口:a0-dev50081a0-backup50082
  • 日志文件名:换成各自的实例名,避免多实例共用日志

启用并检查:

a2ensite a0-primary.conf apache2ctl configtest systemctl reload apache2

SSL 证书(每个域名各签一次)

Let's Encrypt + Certbot(Debian/Ubuntu 用apt-get install certbot python3-certbot-apache,AlmaLinux/CentOS 用dnf install certbot python3-certbot-apache):

certbot --apache -d a0.example.com -d www.a0.example.com certbot renew --dry-run

对每个实例的域名重复签发;签发后 vhost 中的/path/to/certificate.crt等占位路径会由 Certbot 替换为实际证书路径。手动/商业证书则放入安全目录(指南示例:mkdir -p /etc/ssl/a0 && chmod 700 /etc/ssl/a0,证书文件chmod 600)。

可选分支:DirectAdmin 托管的 Apache

如果 VPS 使用 DirectAdmin,指南给出替代方案:把 vhost 写入/etc/httpd/conf/extra/httpd-includes.conf,并且必须绑定具体服务器 IP(如<VirtualHost 192.168.1.100:443>)而不是*:443——IP 绑定的 vhost 优先于 DirectAdmin 自己的 vhost;SSL 证书位于/usr/local/directadmin/data/users/USERNAME/domains/。也可用conf.d独立 conf 文件,但需先确认conf.d被主配置 include。

配置 DNS

每个子域名各建一条 A 记录,指向服务器 IP(指南示例,TTL 300):

类型名称
Aa0YOUR_SERVER_IP
Awww.a0YOUR_SERVER_IP

第二个实例再加对应记录(如a0-dev)。解析验证:

dig a0.example.com +short nslookup a0.example.com

应返回服务器 IP。

验证全部实例

指南的验证清单(按实例逐一执行):

# 1. 容器在运行 docker ps | grep a0-primary # 2. 查看容器日志 docker logs a0-primary --tail 50 # 3. 本机访问容器端口 curl -I http://127.0.0.1:50080/ # 预期: HTTP/1.1 302 FOUND, Location: /login # 4. Apache 配置语法 httpd -t # AlmaLinux/CentOS apache2ctl -t # Debian/Ubuntu # 5. 确认 Apache 按 Host 头代理到正确端口 curl -I http://127.0.0.1:80 -H "Host: a0.example.com" curl -Ik https://127.0.0.1:443 -H "Host: a0.example.com" # 6. 外部 HTTPS 访问 curl -I https://a0.example.com/ # 预期: HTTP/2 302 with Location: /login # 7. 登录页可加载 curl -s https://a0.example.com/login | grep -i "<title>" # 预期: <title>Login - Agent Zero</title>

第二个实例将 Host 头与 URL 换成自己的域名、容器端口换成 50081 重复执行。指南给出的预期响应(302、/login<title>Login - Agent Zero</title>)是启用认证时的参考输出。

如需验证 WebSocket 连通(指南列为可选项):

npm install -g wscat # 全局安装 wscat 命令行工具 wscat -c wss://a0.example.com/ws

常见问题处理

502 Bad Gateway——容器未运行或端口不对:

docker ps -a | grep a0-primary docker logs a0-primary docker start a0-primary netstat -tlnp | grep 50080

容器无法启动(端口冲突)——先查占用:

netstat -tlnp | grep 50080 systemctl status docker journalctl -u docker --since "1 hour ago"

指南的进一步处理是移除占用端口的容器:docker rm -f conflicting-container。注意该命令会强制删除指定容器,删除前确认该容器已不再需要。

WebSocket 连接失败——vhost 缺少代理规则,确认存在:

RewriteEngine On RewriteCond %{HTTP:Upgrade} websocket [NC] RewriteCond %{HTTP:Connection} upgrade [NC] RewriteRule ^/?(.*) ws://127.0.0.1:50080/$1 [P,L]

登录提示 Invalid Credentials——.env 配置错误,AUTH_LOGIN必须是用户名而不是布尔值:

docker exec a0-primary cat /a0/.env # 确认格式: AUTH_LOGIN=username AUTH_PASSWORD=password docker restart a0-primary

.env 修改不生效——环境变量需重启容器才重新加载:docker restart a0-primary,再用docker exec a0-primary cat /a0/.env核对。

DirectAdmin 环境下 403 Forbidden——DirectAdmin 的 vhost 覆盖了自定义代理配置;用httpd -S 2>&1 | grep your-domain检查 vhost 顺序,确保自定义配置先于directadmin-vhosts.conf加载,并使用具体 IP 绑定而非通配。

限制与后续

多实例部署后,各实例通过docker ps --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}"docker stats <实例名>监控;实例数据位于各自的/opt/<实例名>/下(.envmemory/work_dir/),指南给出的备份方式是对整个实例目录打包:tar -czvf a0-backup-$(date +%Y%m%d).tar.gz /opt/a0-primary/。镜像升级需按实例逐个执行 pull + 重建容器,详见 VPS 部署指南的 Maintenance & Updates 一节。

需要注意的边界:每新增一个实例,容器名、主机端口、数据目录、子域名、vhost 配置五者都必须唯一,任一重复都会导致端口冲突或 vhost 相互覆盖;80/443 端口由 Apache 统一占用,容器端口永远走127.0.0.1上的 50080 起的映射端口。

【免费下载链接】agent-zeroAgent Zero AI framework项目地址: https://gitcode.com/GitHub_Trending/ag/agent-zero

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/9/14 7:10:18

移动硬盘提示需要格式化怎么办?数据恢复原理与实操指南

移动硬盘插上电脑&#xff0c;屏幕弹出一句“使用驱动器中的光盘之前需要格式化”&#xff0c;这一瞬间的心跳加速&#xff0c;我太熟悉了。做了这么多年数据恢复&#xff0c;几乎每个月都有朋友被这行字吓得语无伦次&#xff0c;急急忙忙来问我&#xff1a;“我是不是应该点格…

作者头像 李华
网站建设 2026/9/14 7:08:37

Cursor接入统一API网关:从多Key混乱到模型路由实践

我最初是在一个团队内部被问到“你们到底给 Cursor 配了多少个 API Key”这种问题&#xff0c;才开始正视 AI 编程工具已经严重碎片化的现实。桌面端有 Cursor、Continue 和一堆 VS Code 插件&#xff0c;终端里有各种 Agent CLI&#xff0c;每个工具都要求填一个模型服务的 Ke…

作者头像 李华
网站建设 2026/9/14 7:06:58

Libvio.link影视爬虫实战:反爬策略与架构设计

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华
网站建设 2026/9/14 7:06:26

SpringBoot+Vue电商系统架构与性能优化实战

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华
网站建设 2026/9/14 7:03:35

Optuna 文档构建深度解析:autosummary 类模板如何剔除 __init__ 构造器

Optuna 文档构建深度解析:autosummary 类模板如何剔除 init 构造器 【免费下载链接】optuna A hyperparameter optimization framework 项目地址: https://gitcode.com/GitHub_Trending/op/optuna 本文聚焦 Optuna 文档构建管线中的一个关键定制点——Jinja2 模板 class…

作者头像 李华
网站建设 2026/9/14 7:00:41

燃料电池汽车双层凸优化能量管理策略解析

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华