feat: unified one-time deploy summary
This commit is contained in:
parent
8cb46863d2
commit
656ca02a14
443
docs/ai-workspace-runtime-delivery-plan.md
Normal file
443
docs/ai-workspace-runtime-delivery-plan.md
Normal file
@ -0,0 +1,443 @@
|
||||
# AI Workspace Runtime 交付规划
|
||||
|
||||
> 目标:把 `setup-ai-workspace-all-in-one.sh` 从“一组分散的基础设施 Playbook”收敛为一个**可直接使用的 AI Workspace Runtime 产品**——版本受控、运行模式可组合、对外仅暴露 Bridge、部署完成后输出一次性统一摘要。
|
||||
>
|
||||
> 本文是落地前的详细规划(设计 + 变更清单 + 提交/部署/验收方案)。实现阶段严格按本文执行,不扩大修改范围、不做大规模重构、优先复用现有实现。
|
||||
|
||||
- 状态:规划已定稿,待实现
|
||||
- 影响仓库:`ai-workspace-infra/playbooks`、`ai-workspace-lab/xworkspace-console`、`ai-workspace-lab/xworkspace-core-skills`
|
||||
- 目标主机:`root@acp-bridge.onwalk.net`
|
||||
- 对外默认域名(唯一公开服务):`acp-bridge.onwalk.net`
|
||||
|
||||
---
|
||||
|
||||
## 1. 交付目标与验收标准
|
||||
|
||||
### 1.1 总体目标
|
||||
|
||||
1. 在不扩大修改范围、不做大规模重构的前提下,完成必要调整并分别提交三个仓库。
|
||||
2. 使用 `scripts/setup-ai-workspace-all-in-one.sh` 将 AI Workspace 部署到 `root@acp-bridge.onwalk.net`。
|
||||
3. `xworkmate bridge` 统一使用 `acp-bridge.onwalk.net` 作为对外域名,且是**唯一默认公开**的服务。
|
||||
4. 交付一个完整的 AI Workspace Runtime:`xfce_desktop` + NodeJS + Playwright 全部版本受控。
|
||||
5. 运行模式 `docker / k3s / systemd` 可选、可自由组合(`docker` 与 `k3s` 互斥,`docker + systemd` 可组合)。
|
||||
6. 角色拆分:`roles/vhosts/xfce_xrdp_minimal` → `roles/vhosts/xfce_desktop_minimal_runtime` + `roles/vhosts/remote_desktop_xrdp_server`。
|
||||
7. 部署脚本结束后输出一份**面向最终用户**的统一部署摘要,重要认证信息**仅显示一次**。
|
||||
|
||||
### 1.2 验收标准(Definition of Done)
|
||||
|
||||
- [ ] 三个仓库完成代码提交,提供各自 Commit Hash。
|
||||
- [ ] `setup-ai-workspace-all-in-one.sh` 在目标主机以远程 exec 模式执行成功(无 rsync,仓库由远程主机自 GitHub pull)。
|
||||
- [ ] Bridge 对外使用 `acp-bridge.onwalk.net`,其余服务默认不公开。
|
||||
- [ ] 脚本结束输出统一部署摘要:访问入口、一次性凭据、各服务运行状态、可用 Agent CLI。
|
||||
- [ ] `xfce_desktop / NodeJS / Playwright` 版本均可在单一来源(role defaults)查到并被固定。
|
||||
|
||||
---
|
||||
|
||||
## 2. 部署执行模型(远程 exec / GitHub pull)
|
||||
|
||||
- `scripts/setup-ai-workspace-all-in-one.sh` 运行**在远程主机上**,全程 remote exec 模式。
|
||||
- **不使用 rsync**;所需仓库由远程主机直接从 GitHub `pull`:
|
||||
- Playbooks:`https://github.com/ai-workspace-infra/playbooks.git`
|
||||
- Core Skills:`https://github.com/ai-workspace-lab/xworkspace-core-skills.git`
|
||||
- Console(脚本自身所在仓库):`https://github.com/ai-workspace-lab/xworkspace-console.git`
|
||||
- QMD:`https://github.com/ai-workspace-services/qmd.git`
|
||||
- LiteLLM:`https://github.com/ai-workspace-services/litellm.git`
|
||||
- 含义:**本地提交必须推送到上述 GitHub 仓库后,远程部署才能拉到改动**。
|
||||
|
||||
> ⚠️ 注意仓库地址不一致:playbooks 本地 `origin` 当前为 `git@github.com:x-evor/playbooks.git`,而部署权威源是 `ai-workspace-infra/playbooks`。实现阶段需将脚本中的 pull 源对齐到 `ai-workspace-infra/playbooks`,并把提交推送到该仓库。
|
||||
|
||||
### 2.1 环境变量接口契约(权威)
|
||||
|
||||
bootstrap 入口固定为 console 仓库的原始脚本,所有暴露/安全/可选桌面行为均通过 `bash -` 前的环境变量控制。
|
||||
|
||||
**标准安装**(默认安全本地工作区,仅需一个统一 token):
|
||||
|
||||
```bash
|
||||
curl -sfL https://raw.githubusercontent.com/ai-workspace-lab/xworkspace-console/main/scripts/setup-ai-workspace-all-in-one.sh | bash -
|
||||
```
|
||||
|
||||
**全部参数(默认值与推荐用法):**
|
||||
|
||||
| 变量 | 默认 | 推荐用法 |
|
||||
|---|---|---|
|
||||
| `TOKEN` | 生成或复用 | 为 Bridge / Portal / LiteLLM / OpenClaw / Vault 设置**统一**认证 token |
|
||||
| `AI_WORKSPACE_SECURITY_LEVEL` | `standard` | 公网/半公网主机使用 `strict` |
|
||||
| `XWORKMATE_BRIDGE_PUBLIC_ACCESS` | `true` | Bridge 为默认唯一公开服务;如需关闭对外访问可显式设 `false` |
|
||||
| `XWORKMATE_BRIDGE_DOMAIN` | host-specific | 设置 Bridge 公网域名,例如 `acp-bridge.onwalk.net` |
|
||||
| `XWORKSPACE_CONSOLE_PUBLIC_ACCESS` | `false` | 仅当 Portal 必须公开时开启;本地优先更安全 |
|
||||
| `XWORKSPACE_CONSOLE_ENABLE_XRDP` | `false` | 仅当需要远程桌面访问时开启 |
|
||||
| `GATEWAY_OPENCLAW_PUBLIC_ACCESS` | `false` | 除非 OpenClaw 必须直接暴露,保持 false |
|
||||
| `VAULT_PUBLIC_ACCESS` | `false` | 常规部署保持 false |
|
||||
| `LITELLM_API_CADDY_STRICT_WHITELIST` | `false` | strict 且 LiteLLM 经 Caddy 暴露时开启 |
|
||||
|
||||
**进阶安装示例:**
|
||||
|
||||
```bash
|
||||
curl -sfL https://raw.githubusercontent.com/ai-workspace-lab/xworkspace-console/main/scripts/setup-ai-workspace-all-in-one.sh | \
|
||||
AI_WORKSPACE_SECURITY_LEVEL=strict \
|
||||
XWORKSPACE_CONSOLE_ENABLE_XRDP=true \
|
||||
XWORKSPACE_CONSOLE_PUBLIC_ACCESS=true \
|
||||
XWORKMATE_BRIDGE_PUBLIC_ACCESS=true \
|
||||
GATEWAY_OPENCLAW_PUBLIC_ACCESS=false \
|
||||
VAULT_PUBLIC_ACCESS=false \
|
||||
LITELLM_API_CADDY_STRICT_WHITELIST=true \
|
||||
TOKEN="your-unified-auth-token" \
|
||||
bash -
|
||||
```
|
||||
|
||||
**目标主机(ACP Bridge)示例:**
|
||||
|
||||
```bash
|
||||
curl -sfL https://raw.githubusercontent.com/ai-workspace-lab/xworkspace-console/main/scripts/setup-ai-workspace-all-in-one.sh | \
|
||||
XWORKMATE_BRIDGE_DOMAIN=acp-bridge.onwalk.net \
|
||||
XWORKMATE_BRIDGE_PUBLIC_ACCESS=true \
|
||||
AI_WORKSPACE_SECURITY_LEVEL=strict \
|
||||
bash -
|
||||
```
|
||||
|
||||
> 关键校准:`XWORKMATE_BRIDGE_PUBLIC_ACCESS` 默认 **`true`**——Bridge 是**默认唯一公开**的服务(域名经 `XWORKMATE_BRIDGE_DOMAIN` 自定义传入);其余服务(Console/OpenClaw/Vault/QMD/Hermes/PG/LiteLLM)默认 `false`,保持 `127.0.0.1` 本地监听。如需关闭 Bridge 对外访问,显式设 `XWORKMATE_BRIDGE_PUBLIC_ACCESS=false`。`TOKEN` 输出务必私密保存——不得拷入前端源码或提交到 Git。
|
||||
|
||||
### 2.2 预期最终输出(部署摘要)
|
||||
|
||||
部署成功后,脚本将**一次性**打印部署域名与 token,随后报告各服务运行状态:
|
||||
|
||||
- AI Workspace 域名与 token(仅显示一次)
|
||||
- OpenClaw
|
||||
- QMD
|
||||
- PostgreSQL
|
||||
- Vault
|
||||
- Workspace Portal / Console
|
||||
- LiteLLM
|
||||
- Hermes
|
||||
- Agent CLI:opencode、gemini、codex、claude
|
||||
|
||||
### 2.3 本地 macOS 校验模式
|
||||
|
||||
在 macOS 上脚本默认进入**本地校验模式**,在 `http://127.0.0.1:17000` 启动 Portal。若因端口占用校验失败,先停止已有本地服务或在干净会话中重试。
|
||||
|
||||
---
|
||||
|
||||
## 3. 现状分析:角色层级关系
|
||||
|
||||
`setup-ai-workspace-all-in-one.sh`(位于 console 仓库)在目标主机引导后,运行 `setup-ai-workspace-all-in-one.yml`(位于 playbooks 仓库)。其按导入顺序的角色层级:
|
||||
|
||||
```
|
||||
setup-ai-workspace-all-in-one.sh [repo: xworkspace-console/scripts]
|
||||
└─ ansible-playbook setup-ai-workspace-all-in-one.yml [repo: playbooks]
|
||||
├─1 setup-nodejs.yml → role roles/vhosts/nodejs NodeJS(22.x)+yarn
|
||||
├─2 setup-xworkspace-console.yaml WORKSPACE PORTAL/CONSOLE(内联 task,无 role)
|
||||
│ apt: caddy,xfce4,python3,golang-go,google-chrome-stable,ttyd
|
||||
│ git clone console → npm build;systemd --user: console(:17000)/api(:8788)/ttyd(:7681)/status.timer
|
||||
│ Caddy 公网站点 workspace.svc.plus ⚠ 标准模式下也公开
|
||||
├─3 setup-ai-agent-skills.yml → role roles/ai_agent_runtime AI WORKSPACE RUNTIME 核心
|
||||
│ NodeJS(24.x)+Playwright;Agent CLI: opencode/gemini/codex/claude;Python/browser/docs/fonts
|
||||
│ └─ role agent_skills → 注入 xworkspace-core-skills 市场技能
|
||||
├─4 deploy_gateway_openclaw.yml → role roles/vhosts/gateway_openclaw OpenClaw(2026.5.28)
|
||||
├─5 deploy_xworkmate_bridge_vhosts.yml BRIDGE + ACP 集群
|
||||
│ ├─ import setup-xworkspace-console.yaml(带 bridge 变量再跑一次)
|
||||
│ └─ roles: acp_server_codex / acp_server_opencode / acp_server_gemini /
|
||||
│ acp_server_hermes / xworkmate_bridge(:8787 本地,公网 Caddy)
|
||||
│ 域名默认 xworkmate-bridge.svc.plus → acp-bridge.onwalk.net
|
||||
├─6 setup-vault.yaml → role roles/vhosts/vault Vault(1.20.4) :8200
|
||||
├─7 setup-postgres-standalone.yaml → role roles/vhosts/postgres(dep: common) 原生 apt PG17 :5432
|
||||
├─8 setup-litellm.yaml → role roles/vhosts/litellm pip 安装 :4000
|
||||
├─9 deploy_QMD.yml → role roles/vhosts/qmd bun qmd, MCP :8181
|
||||
├─10 deploy_agent_hermes.yml → role roles/vhosts/acp_server_hermes ⚠ Hermes 重复部署(与步骤5重叠)
|
||||
└─11 setup-xfce-xrdp.yaml [可选] → role roles/vhosts/xfce_xrdp_minimal
|
||||
→ 拆分为 xfce_desktop_minimal_runtime + remote_desktop_xrdp_server
|
||||
```
|
||||
|
||||
### 3.1 关键发现
|
||||
|
||||
1. **公开面冲突**:步骤 2/5 在 `ai_workspace_security_level != strict` 时为 `workspace.svc.plus` 部署公网 Caddy 站点,导致 Portal 也对外暴露,与“Bridge 唯一公开”冲突。
|
||||
2. **Hermes 重复部署**:步骤 5(ACP 集群内)与步骤 10(独立)各部署一次,冗余。
|
||||
3. **版本固定点分散**:OpenClaw、Vault 已有固定变量;NodeJS 有但偏宽松(`22.x`/`24.x`);Hermes、QMD、LiteLLM 缺少显式版本/源固定。
|
||||
|
||||
---
|
||||
|
||||
## 4. 关键设计决策
|
||||
|
||||
### 4.1 对外公开面:Bridge Only
|
||||
|
||||
- **Bridge 是默认唯一公开的服务**:`XWORKMATE_BRIDGE_PUBLIC_ACCESS` 默认 `true`,公网域名由 `XWORKMATE_BRIDGE_DOMAIN` 自定义传入(目标主机 `acp-bridge.onwalk.net`)。如需关闭可显式设 `false`。
|
||||
- `xworkspace_console_public_access` 默认 `false`(仅 `XWORKSPACE_CONSOLE_PUBLIC_ACCESS=true` 时公开)。
|
||||
- `GATEWAY_OPENCLAW_PUBLIC_ACCESS` / `VAULT_PUBLIC_ACCESS` 默认 `false`;其余(QMD / Hermes / PG / LiteLLM)维持本地监听(`127.0.0.1`),不部署公网 Caddy 站点。
|
||||
- 实现方式:**最小改动**——仅调整默认值/开关并对齐 env 名称(§2.1),不删除既有 public_access 能力(保留可手动放开)。
|
||||
|
||||
### 4.2 Hermes 去重
|
||||
|
||||
- `setup-ai-workspace-all-in-one.yml` 中移除步骤 10 的独立 `deploy_agent_hermes.yml` 导入(步骤 5 的 ACP 集群已含 hermes)。
|
||||
- 保留 `deploy_agent_hermes.yml` 文件本身,供单独部署场景使用,仅从 all-in-one 聚合链里去重。
|
||||
|
||||
### 4.3 运行模式矩阵(docker / k3s / systemd)
|
||||
|
||||
引入一个**校验型**变量 `ai_workspace_runtime_modes`(列表),在 all-in-one 顶部加一段 `assert` 守卫,不重写各组件部署逻辑:
|
||||
|
||||
| 约束 | 规则 |
|
||||
|---|---|
|
||||
| 互斥 | `docker` 与 `k3s` 不可同时出现 |
|
||||
| 可组合 | `docker + systemd` 允许;`systemd` 可单独 |
|
||||
| 默认 | `['docker','systemd']`(多数 Agent 服务 systemd,PostgreSQL 走 docker compose) |
|
||||
|
||||
组件与模式映射(复用现有能力,不新增重型实现):
|
||||
|
||||
| 组件 | systemd | docker | k3s |
|
||||
|---|---|---|---|
|
||||
| Console / API / ttyd / Bridge / ACP / OpenClaw / QMD / LiteLLM | ✅ 默认 | — | — |
|
||||
| PostgreSQL | 可选 | ✅ **默认 docker compose** | 可选 |
|
||||
| Vault | `vault_deploy_mode=systemd` | — | `vault_deploy_mode=kubernetes`(k3s) |
|
||||
|
||||
守卫伪代码(放入 all-in-one 顶层 play):
|
||||
|
||||
```yaml
|
||||
- name: Validate runtime mode combination
|
||||
hosts: all
|
||||
gather_facts: false
|
||||
tasks:
|
||||
- assert:
|
||||
that:
|
||||
- not ('docker' in ai_workspace_runtime_modes and 'k3s' in ai_workspace_runtime_modes)
|
||||
- ai_workspace_runtime_modes | length > 0
|
||||
fail_msg: "docker 与 k3s 互斥;请选择 docker/k3s/systemd 的合法组合。"
|
||||
```
|
||||
|
||||
### 4.4 PostgreSQL 默认 docker compose
|
||||
|
||||
- 新增开关 `postgresql_deploy_mode`,默认 `compose`。
|
||||
- `compose` 模式:在 `roles/vhosts/postgres` 增加一条 compose 部署路径(镜像版本固定,端口/口令复用现有变量),与现有原生 apt 路径并存、互斥择一。
|
||||
- 不删除原生 apt 路径(设 `postgresql_deploy_mode=native` 可回退)。
|
||||
|
||||
### 4.5 QMD / LiteLLM 源仓库与版本固定
|
||||
|
||||
- QMD:安装源指向 `https://github.com/ai-workspace-services/qmd.git`,新增 `qmd_source_repo` / `qmd_version` 变量固定。
|
||||
- LiteLLM:安装源指向 `https://github.com/ai-workspace-services/litellm.git`,新增 `litellm_source_repo` / `litellm_version` 变量固定。
|
||||
|
||||
---
|
||||
|
||||
## 5. 详细变更清单
|
||||
|
||||
### 5.1 角色拆分:`xfce_xrdp_minimal` → 两个角色
|
||||
|
||||
按职责拆分,**逐文件映射**,行为不变;`setup-xfce-xrdp.yaml` 改为顺序组合两个新角色。
|
||||
|
||||
**`roles/vhosts/xfce_desktop_minimal_runtime`(桌面运行时)**
|
||||
|
||||
| 来源 | 去向 | 说明 |
|
||||
|---|---|---|
|
||||
| `tasks/install.yml`(仅桌面包:`xfce4-session/xfwm4/xfdesktop4/xfce4-panel/xfce4-terminal/dbus-x11/fonts-noto-cjk/xserver-xorg-core`) | `tasks/install.yml` | 移除 `xorgxrdp/xrdp` 包与 xrdp 服务启动 |
|
||||
| `tasks/browser.yml`(Google Chrome 固定版) | `tasks/browser.yml` | 原样保留 |
|
||||
| 新增 `tasks/runtime.yml` | NodeJS + Playwright(引用既有 `nodejs` / `ai_agent_runtime` 的固定版本变量) | 版本受控单一来源 |
|
||||
| `defaults/main.yml`(desktop/chrome/node/playwright 版本变量) | `defaults/main.yml` | 见 §5.2 版本表 |
|
||||
|
||||
**`roles/vhosts/remote_desktop_xrdp_server`(远程桌面 XRDP 服务)**
|
||||
|
||||
| 来源 | 去向 | 说明 |
|
||||
|---|---|---|
|
||||
| `tasks/install.yml`(`xorgxrdp/xrdp`、ssl-cert 组、daemon-reload、enable/start、unit 校验/fail) | `tasks/install.yml` | XRDP 服务层 |
|
||||
| `tasks/config.yml`(用户/口令 RDP 认证、`.xsession`、xfconf 目录) | `tasks/config.yml` | RDP 会话粘合 |
|
||||
| `handlers/main.yml`(Restart xrdp / sesman) | `handlers/main.yml` | 原样保留 |
|
||||
| `vars/main.yml`(`xfce_xrdp_services` 等)+ `xfce_rdp_port/xfce_enable_ufw` | `defaults`/`vars` | 端口/ufw |
|
||||
|
||||
**组合点 `setup-xfce-xrdp.yaml`:**
|
||||
|
||||
```yaml
|
||||
- name: Deploy XFCE desktop + optional XRDP (Optional)
|
||||
hosts: all
|
||||
become: true
|
||||
vars:
|
||||
xworkspace_console_enable_xrdp: false
|
||||
tasks:
|
||||
- include_role: { name: roles/vhosts/xfce_desktop_minimal_runtime }
|
||||
- include_role: { name: roles/vhosts/remote_desktop_xrdp_server }
|
||||
when: xworkspace_console_enable_xrdp | bool
|
||||
```
|
||||
|
||||
> 旧角色 `roles/vhosts/xfce_xrdp_minimal`:拆分完成且引用全部切换后删除(当前唯一引用即 `setup-xfce-xrdp.yaml`)。
|
||||
|
||||
### 5.2 版本固定表(单一来源)
|
||||
|
||||
| 组件 | 变量 | 当前 | 目标 | 文件 |
|
||||
|---|---|---|---|---|
|
||||
| OpenClaw | `gateway_openclaw_required_version` | `2026.5.28` | `2026.6.1` | `roles/vhosts/gateway_openclaw/defaults/main.yml:23` |
|
||||
| Vault | `vault_version`(env 默认值) | `1.20.4` | `1.21.4` | `roles/vhosts/vault/vars/main.yml:6` |
|
||||
| Hermes | `acp_hermes_version`(新增) | 无 | `0.15` | `roles/vhosts/acp_server_hermes/defaults/main.yml` |
|
||||
| QMD | `qmd_version` / `qmd_source_repo`(新增) | 无 | 取自 `ai-workspace-services/qmd` | `roles/vhosts/qmd/defaults/main.yml` |
|
||||
| LiteLLM | `litellm_version` / `litellm_source_repo`(新增) | 无 | 取自 `ai-workspace-services/litellm` | `roles/vhosts/litellm/defaults/main.yml` |
|
||||
| NodeJS | `nodejs_version` / `ai_agent_runtime_nodejs_version` | `22.x` / `24.x` | 固定明确小版本 | `roles/vhosts/nodejs/defaults` + `roles/ai_agent_runtime/defaults` |
|
||||
| Playwright | `ai_agent_runtime_playwright_version`(新增/固定) | 无显式 | 固定 | `roles/ai_agent_runtime/defaults/main.yml` |
|
||||
| Google Chrome | `xfce_google_chrome_version` | `148.0.7778.167-1` | 保持固定 | 运行时角色 `defaults/main.yml` |
|
||||
| XFCE | `xfce_packages` | 列表 | 保持(apt 发行版固定) | 运行时角色 `defaults/main.yml` |
|
||||
|
||||
### 5.3 Bridge 对外域名(自定义参数,非硬编码默认)
|
||||
|
||||
- **`acp-bridge.onwalk.net` 是 host-specific 的自定义参数**,经 `XWORKMATE_BRIDGE_DOMAIN` 在部署时传入,**不写死为 role 默认值**。
|
||||
- 实现要点(最小改动):确保 `XWORKMATE_BRIDGE_DOMAIN` 经 bootstrap 脚本 → playbook → `roles/vhosts/xworkmate_bridge` 正确透传。现有 env 覆盖链已支持:`XWORKMATE_BRIDGE_DOMAIN` → `ai_workspace_public_domain`(`SERVER_DOMAIN/ACP_BRIDGE_DOMAIN/BRIDGE_DOMAIN`)。
|
||||
- `roles/vhosts/xworkmate_bridge/defaults/main.yml:47` 的中性回退默认值(`xworkmate-bridge.svc.plus`)**保持不变**——仅作为未显式传参时的兜底;目标主机通过 `XWORKMATE_BRIDGE_DOMAIN=acp-bridge.onwalk.net` 指定真实域名。
|
||||
- 验收只要求“Bridge 使用指定域名”,由自定义参数满足,无需改动 role 默认。
|
||||
|
||||
### 5.4 部署脚本统一摘要(`setup-ai-workspace-all-in-one.sh`)
|
||||
|
||||
在现有脚本(console 仓库,约 39KB)末尾**追加**一段摘要渲染(探测主机实时状态,不硬编码),结构如下:
|
||||
|
||||
```
|
||||
================ AI Workspace 部署摘要 ================
|
||||
[访问入口]
|
||||
Workspace Portal (Console) : http://127.0.0.1:17000 (本地)
|
||||
XWorkMate Bridge : https://acp-bridge.onwalk.net ← 唯一公开
|
||||
[一次性凭据](仅显示一次)
|
||||
AI_WORKSPACE_AUTH_TOKEN : ********
|
||||
Vault root token : ********
|
||||
[服务状态]
|
||||
Portal / Bridge / OpenClaw / QMD / Hermes / PostgreSQL / Vault / LiteLLM : active/inactive
|
||||
[Agent CLI]
|
||||
opencode / gemini / codex / claude : <version | 缺失>
|
||||
======================================================
|
||||
```
|
||||
|
||||
- 状态探测复用 console 的 `generate-status.py` 逻辑与各 role 的 `validate.yml` 健康检查(`systemctl is-active` + `curl` 健康端点)。
|
||||
- 凭据“仅显示一次”:摘要从已落盘的 token 文件读取展示后,提示用户保存;脚本不重复打印。
|
||||
|
||||
### 5.5 all-in-one 聚合链调整
|
||||
|
||||
- 顶部新增 §4.3 运行模式 `assert` 守卫 play。
|
||||
- 移除步骤 10 独立 `deploy_agent_hermes.yml` 导入(去重,见 §4.2)。
|
||||
- 其余导入顺序保持不变。
|
||||
|
||||
---
|
||||
|
||||
## 6. 仓库与提交计划
|
||||
|
||||
| 仓库 | 主要改动 | Commit message(建议) | 推送目标 |
|
||||
|---|---|---|---|
|
||||
| `playbooks` | 角色拆分、版本固定、Bridge 域名、运行模式守卫、PG compose、QMD/LiteLLM 源、聚合链去重、本规划文档 | `feat: deliver versioned AI Workspace Runtime (role split, run-mode matrix, bridge domain)` | `ai-workspace-infra/playbooks` |
|
||||
| `xworkspace-console` | `setup-ai-workspace-all-in-one.sh` 统一摘要、pull 源对齐、console 默认不公开 | `feat: unified one-time deploy summary + bridge-only public surface` | `ai-workspace-lab/xworkspace-console` |
|
||||
| `xworkspace-core-skills` | (按需)技能种子/版本对齐 | `chore: align skills seed for workspace runtime` | `ai-workspace-lab/xworkspace-core-skills` |
|
||||
|
||||
> 每个仓库**独立提交**,分别记录 Commit Hash 写入最终交付说明。
|
||||
|
||||
---
|
||||
|
||||
## 7. 部署与验证
|
||||
|
||||
### 7.1 部署命令(在目标主机或对其有网络/SSH 访问的环境执行)
|
||||
|
||||
```bash
|
||||
# 远程 exec:脚本在主机上自 GitHub pull 仓库并运行 ansible 到 localhost
|
||||
# 采用 §2.1 权威环境变量契约(目标主机示例)
|
||||
ssh root@acp-bridge.onwalk.net \
|
||||
'curl -sfL https://raw.githubusercontent.com/ai-workspace-lab/xworkspace-console/main/scripts/setup-ai-workspace-all-in-one.sh | \
|
||||
XWORKMATE_BRIDGE_DOMAIN=acp-bridge.onwalk.net \
|
||||
XWORKMATE_BRIDGE_PUBLIC_ACCESS=true \
|
||||
AI_WORKSPACE_SECURITY_LEVEL=strict \
|
||||
bash -'
|
||||
```
|
||||
|
||||
### 7.2 验证清单
|
||||
|
||||
- [ ] 脚本结束输出统一摘要,且 Bridge 显示 `https://acp-bridge.onwalk.net`。
|
||||
- [ ] `curl -I https://acp-bridge.onwalk.net` 可达;其余服务端口仅 `127.0.0.1` 监听。
|
||||
- [ ] `systemctl --user is-active` 各服务为 `active`。
|
||||
- [ ] `opencode/gemini/codex/claude --version` 均可执行。
|
||||
- [ ] 凭据仅在摘要中出现一次。
|
||||
|
||||
---
|
||||
|
||||
## 8. 风险与回退
|
||||
|
||||
| 风险 | 缓解 / 回退 |
|
||||
|---|---|
|
||||
| 沙箱无法直连 GitHub/目标主机 | 本地完成代码+提交;push 与远程部署由有网络的环境执行 |
|
||||
| PG 切 compose 影响既有数据 | 保留 `postgresql_deploy_mode=native` 回退路径 |
|
||||
| 角色拆分回归 | `setup-xfce-xrdp.yaml` 组合两角色,行为等价;保留旧角色直至引用切换验证通过 |
|
||||
| 版本固定导致拉取失败 | 版本变量集中、可单点覆盖(env / `-e`) |
|
||||
|
||||
---
|
||||
|
||||
## 9. 实现顺序(落地次序)
|
||||
|
||||
1. 本规划文档入库(docs/)。
|
||||
2. 角色拆分 + `setup-xfce-xrdp.yaml` 组合。
|
||||
3. 版本固定(OpenClaw/Vault/Hermes/QMD/LiteLLM/Node/Playwright/Chrome)。
|
||||
4. Bridge 域名参数透传(`XWORKMATE_BRIDGE_DOMAIN`,自定义,不改 role 默认)。
|
||||
5. 运行模式守卫 + PG compose 默认。
|
||||
6. 聚合链去重(Hermes)+ console 默认不公开。
|
||||
7. `setup-ai-workspace-all-in-one.sh` 统一摘要。
|
||||
8. 三仓库分别提交,记录 Commit Hash。
|
||||
9. 推送 + 远程部署 + 按 §7.2 验证。
|
||||
|
||||
---
|
||||
|
||||
## 附录 A. AI Workspace All-in-One Setup(bootstrap 使用指南)
|
||||
|
||||
> 面向最终用户的官方安装指南,已合并入本规划作为单一权威来源。
|
||||
> 本附录相对上游 README 有两处校准:① `XWORKMATE_BRIDGE_PUBLIC_ACCESS` 默认 **`true`**(Bridge 为默认唯一公开服务);② `acp-bridge.onwalk.net` 为 **host-specific 自定义参数**,经 `XWORKMATE_BRIDGE_DOMAIN` 传入。
|
||||
|
||||
这是从 `xworkspace-console` 仓库安装 AI Workspace Runtime 的推荐 bootstrap 入口。脚本以该仓库为公开入口,随后通过 AI Workspace playbooks 与各组件仓库准备运行时服务。
|
||||
|
||||
### A.1 标准安装
|
||||
|
||||
适用于默认安全的本地工作区,仅需一个生成或既有的统一 token:
|
||||
|
||||
```bash
|
||||
curl -sfL https://raw.githubusercontent.com/ai-workspace-lab/xworkspace-console/main/scripts/setup-ai-workspace-all-in-one.sh | bash -
|
||||
```
|
||||
|
||||
### A.2 进阶安装
|
||||
|
||||
在 `bash -` 前用环境变量自定义暴露面、安全级别与可选桌面功能:
|
||||
|
||||
```bash
|
||||
curl -sfL https://raw.githubusercontent.com/ai-workspace-lab/xworkspace-console/main/scripts/setup-ai-workspace-all-in-one.sh | \
|
||||
AI_WORKSPACE_SECURITY_LEVEL=strict \
|
||||
XWORKSPACE_CONSOLE_ENABLE_XRDP=true \
|
||||
XWORKSPACE_CONSOLE_PUBLIC_ACCESS=true \
|
||||
XWORKMATE_BRIDGE_PUBLIC_ACCESS=true \
|
||||
GATEWAY_OPENCLAW_PUBLIC_ACCESS=false \
|
||||
VAULT_PUBLIC_ACCESS=false \
|
||||
LITELLM_API_CADDY_STRICT_WHITELIST=true \
|
||||
TOKEN="your-unified-auth-token" \
|
||||
bash -
|
||||
```
|
||||
|
||||
### A.3 推荐参数
|
||||
|
||||
| 变量 | 默认 | 推荐用法 |
|
||||
|---|---|---|
|
||||
| `TOKEN` | 生成或复用 | 为 Bridge、Portal、LiteLLM、OpenClaw、Vault 设置一个统一认证 token |
|
||||
| `AI_WORKSPACE_SECURITY_LEVEL` | `standard` | 公网/半公网主机使用 `strict` |
|
||||
| `XWORKMATE_BRIDGE_PUBLIC_ACCESS` | `true` | Bridge 为默认唯一公开服务;需关闭对外访问时显式设 `false` |
|
||||
| `XWORKMATE_BRIDGE_DOMAIN` | host-specific(自定义) | Bridge 公网域名,例如 `acp-bridge.onwalk.net` |
|
||||
| `XWORKSPACE_CONSOLE_PUBLIC_ACCESS` | `false` | 仅当 Portal 必须公开时开启;本地优先更安全 |
|
||||
| `GATEWAY_OPENCLAW_PUBLIC_ACCESS` | `false` | 除非 OpenClaw 必须直接暴露,保持 false |
|
||||
| `VAULT_PUBLIC_ACCESS` | `false` | 常规部署保持 false |
|
||||
| `LITELLM_API_CADDY_STRICT_WHITELIST` | `false` | strict 部署且 LiteLLM 经 Caddy 暴露时开启 |
|
||||
| `XWORKSPACE_CONSOLE_ENABLE_XRDP` | `false` | 仅当需要远程桌面访问时开启 |
|
||||
|
||||
### A.4 目标主机示例(当前 ACP Bridge 主机)
|
||||
|
||||
```bash
|
||||
curl -sfL https://raw.githubusercontent.com/ai-workspace-lab/xworkspace-console/main/scripts/setup-ai-workspace-all-in-one.sh | \
|
||||
XWORKMATE_BRIDGE_DOMAIN=acp-bridge.onwalk.net \
|
||||
XWORKMATE_BRIDGE_PUBLIC_ACCESS=true \
|
||||
AI_WORKSPACE_SECURITY_LEVEL=strict \
|
||||
bash -
|
||||
```
|
||||
|
||||
### A.5 预期最终输出
|
||||
|
||||
部署成功后,脚本**一次性**打印部署域名与 token,随后报告以下服务状态:
|
||||
|
||||
- AI Workspace 域名与 token
|
||||
- OpenClaw
|
||||
- QMD
|
||||
- PostgreSQL
|
||||
- Vault
|
||||
- Workspace Portal / Console
|
||||
- LiteLLM
|
||||
- Agent CLI:opencode、gemini、codex、claude
|
||||
|
||||
> Token 输出务必私密保存,不得拷入前端源码或提交到 Git。
|
||||
|
||||
### A.6 本地 macOS 校验
|
||||
|
||||
在 macOS 上脚本默认进入本地校验模式,在 `http://127.0.0.1:17000` 启动 Portal。若因端口占用导致校验失败,先停止已有本地服务或在干净会话中重试。
|
||||
@ -15,6 +15,8 @@ set -euo pipefail
|
||||
# GATEWAY_OPENCLAW_PUBLIC_ACCESS
|
||||
# VAULT_PUBLIC_ACCESS
|
||||
# XWORKSPACE_CONSOLE_ENABLE_XRDP
|
||||
# AI_WORKSPACE_RUNTIME_MODES (docker,systemd by default; docker and k3s are mutually exclusive)
|
||||
# POSTGRESQL_DEPLOY_MODE (compose by default; native for apt/systemd)
|
||||
# AI_WORKSPACE_AUTH_TOKEN / XWORKSPACE_CONSOLE_AUTH_TOKEN
|
||||
# / XWORKMATE_BRIDGE_AUTH_TOKEN / BRIDGE_AUTH_TOKEN / INTERNAL_SERVICE_TOKEN
|
||||
# / DEPLOY_TOKEN
|
||||
@ -577,78 +579,102 @@ service_status_line() {
|
||||
local unit_patterns=$2
|
||||
local port=${3:-}
|
||||
local detail="not detected"
|
||||
local state="DOWN"
|
||||
local state="inactive"
|
||||
|
||||
if command -v systemctl >/dev/null 2>&1; then
|
||||
local unit
|
||||
for unit in $unit_patterns; do
|
||||
if systemctl --user is-active --quiet "$unit" 2>/dev/null; then
|
||||
state="active"
|
||||
detail="systemd-user:$unit"
|
||||
break
|
||||
fi
|
||||
if systemctl is-active --quiet "$unit" 2>/dev/null; then
|
||||
state="OK"
|
||||
state="active"
|
||||
detail="systemd:$unit"
|
||||
break
|
||||
fi
|
||||
done
|
||||
fi
|
||||
|
||||
if [ "$state" != "OK" ] && [ -n "$port" ]; then
|
||||
if [ "$state" != "active" ] && [ -n "$port" ]; then
|
||||
if command -v ss >/dev/null 2>&1 && ss -ltn "( sport = :$port )" 2>/dev/null | grep -q ":$port"; then
|
||||
state="OK"
|
||||
state="active"
|
||||
detail="port:$port"
|
||||
elif command -v lsof >/dev/null 2>&1 && lsof -nP -iTCP:"$port" -sTCP:LISTEN >/dev/null 2>&1; then
|
||||
state="OK"
|
||||
state="active"
|
||||
detail="port:$port"
|
||||
fi
|
||||
fi
|
||||
|
||||
printf ' - %-28s %s (%s)\n' "$label" "$state" "$detail"
|
||||
printf ' %-28s : %-8s (%s)\n' "$label" "$state" "$detail"
|
||||
}
|
||||
|
||||
cli_status_line() {
|
||||
local label=$1
|
||||
local bin=$2
|
||||
local state="MISSING"
|
||||
local state="missing"
|
||||
local detail="not in PATH"
|
||||
|
||||
if command -v "$bin" >/dev/null 2>&1; then
|
||||
state="OK"
|
||||
detail="$(command -v "$bin")"
|
||||
state="available"
|
||||
detail="$("$bin" --version 2>/dev/null | head -n 1 || command -v "$bin")"
|
||||
fi
|
||||
|
||||
printf ' - %-28s %s (%s)\n' "$label" "$state" "$detail"
|
||||
printf ' %-28s : %-9s (%s)\n' "$label" "$state" "$detail"
|
||||
}
|
||||
|
||||
print_deployment_summary() {
|
||||
local domain=${SERVER_DOMAIN:-${XWORKMATE_BRIDGE_DOMAIN:-${BRIDGE_DOMAIN:-${ACP_BRIDGE_DOMAIN:-acp-bridge.onwalk.net}}}}
|
||||
local token=$1
|
||||
local vault_token="${VAULT_SERVER_ROOT_ACCESS_TOKEN:-$token}"
|
||||
local vault_token_display="$vault_token"
|
||||
local bridge_url="https://${domain}"
|
||||
local portal_url="http://127.0.0.1:17000"
|
||||
|
||||
if [ "${XWORKMATE_BRIDGE_PUBLIC_ACCESS:-true}" != "true" ]; then
|
||||
bridge_url="http://127.0.0.1:8787"
|
||||
fi
|
||||
if [ "$vault_token" = "$token" ]; then
|
||||
vault_token_display="same as AI_WORKSPACE_AUTH_TOKEN"
|
||||
fi
|
||||
|
||||
cat <<EOF
|
||||
|
||||
AI Workspace Deployment Summary
|
||||
Domain: ${domain}
|
||||
Token: ${token}
|
||||
XWorkMate Bridge: https://${domain}
|
||||
================ AI Workspace Deployment Summary ================
|
||||
[Access]
|
||||
Workspace Portal (Console) : ${portal_url}
|
||||
XWorkMate Bridge : ${bridge_url}
|
||||
|
||||
AI workspace (runtime desktop/browser):
|
||||
[One-time Credentials]
|
||||
AI_WORKSPACE_AUTH_TOKEN : ${token}
|
||||
Vault root token : ${vault_token_display}
|
||||
|
||||
[Service Status]
|
||||
EOF
|
||||
service_status_line "Runtime desktop/browser" "xworkspace-shell.service xworkspace-console.service display-manager.service gdm.service lightdm.service" "17000"
|
||||
service_status_line "Workspace portal (console)" "xworkspace-console.service xworkspace-api.service" "17000"
|
||||
service_status_line "XWorkMate Bridge (public)" "xworkmate-bridge.service xworkspace-bridge.service" "8787"
|
||||
service_status_line "Portal / Console" "xworkspace-console.service xworkspace-api.service" "17000"
|
||||
service_status_line "XWorkMate Bridge" "xworkmate-bridge.service xworkspace-bridge.service" "8787"
|
||||
service_status_line "OpenClaw" "xworkspace-openclaw.service openclaw-gateway.service openclaw.service" "18789"
|
||||
service_status_line "QMD" "qmd-mcp.service xworkspace-qmd.service qmd.service qdrant.service" "8181"
|
||||
service_status_line "Hermes" "acp-hermes.service xworkspace-hermes.service hermes.service" "3920"
|
||||
service_status_line "PG" "postgresql.service postgresql@16-main.service postgresql@15-main.service xworkspace-postgres.service" "5432"
|
||||
service_status_line "PostgreSQL" "postgresql.service postgresql@17-main.service postgresql@16-main.service postgresql@15-main.service xworkspace-postgres.service" "5432"
|
||||
service_status_line "Vault" "xworkspace-vault.service vault.service" "8200"
|
||||
service_status_line "LiteLLM" "xworkspace-litellm.service litellm-proxy.service litellm.service" "4000"
|
||||
service_status_line "Runtime desktop/browser" "xworkspace-shell.service display-manager.service gdm.service lightdm.service" ""
|
||||
|
||||
cat <<'EOF'
|
||||
|
||||
Agent CLI:
|
||||
[Agent CLI]
|
||||
EOF
|
||||
cli_status_line "opencode" "opencode"
|
||||
cli_status_line "gemini" "gemini"
|
||||
cli_status_line "codex" "codex"
|
||||
cli_status_line "claude" "claude"
|
||||
printf '\n'
|
||||
cat <<'EOF'
|
||||
===============================================================
|
||||
|
||||
Save the one-time credentials above in a private location.
|
||||
EOF
|
||||
}
|
||||
|
||||
deploy_launch_agent() {
|
||||
@ -899,6 +925,7 @@ if [ "$OS_NAME" = "darwin" ] && [ "${AI_WORKSPACE_DARWIN_MODE:-local}" = "local"
|
||||
export VAULT_SERVER_ROOT_ACCESS_TOKEN="${VAULT_SERVER_ROOT_ACCESS_TOKEN:-$UNIFIED_AUTH_TOKEN}"
|
||||
export VAULT_ADMIN_PASSWORD="${VAULT_ADMIN_PASSWORD:-$UNIFIED_AUTH_TOKEN}"
|
||||
deploy_macos_local "$UNIFIED_AUTH_TOKEN"
|
||||
print_deployment_summary "$UNIFIED_AUTH_TOKEN"
|
||||
exit 0
|
||||
fi
|
||||
|
||||
@ -960,11 +987,14 @@ append_var "AI_WORKSPACE_SECURITY_LEVEL" "ai_workspace_security_level"
|
||||
append_var "LITELLM_API_CADDY_STRICT_WHITELIST" "litellm_api_caddy_strict_whitelist"
|
||||
append_var "XWORKSPACE_CONSOLE_PUBLIC_ACCESS" "xworkspace_console_public_access"
|
||||
append_var "XWORKMATE_BRIDGE_PUBLIC_ACCESS" "xworkmate_bridge_public_access"
|
||||
append_var "XWORKMATE_BRIDGE_DOMAIN" "xworkmate_bridge_domain"
|
||||
append_var "XWORKMATE_BRIDGE_VALIDATION_BASE_URL" "xworkmate_bridge_validation_base_url"
|
||||
append_var "GATEWAY_OPENCLAW_PUBLIC_ACCESS" "gateway_openclaw_public_access"
|
||||
append_var "VAULT_PUBLIC_ACCESS" "vault_public_access"
|
||||
append_var "VAULT_DEPLOY_MODE" "vault_deploy_mode"
|
||||
append_var "XWORKSPACE_CONSOLE_ENABLE_XRDP" "xworkspace_console_enable_xrdp"
|
||||
append_var "AI_WORKSPACE_RUNTIME_MODES" "ai_workspace_runtime_modes"
|
||||
append_var "POSTGRESQL_DEPLOY_MODE" "postgresql_deploy_mode"
|
||||
|
||||
# 4. Resolve one auth token for the bridge and downstream service UIs/APIs.
|
||||
UNIFIED_AUTH_TOKEN="$(resolve_unified_auth_token)"
|
||||
|
||||
Loading…
Reference in New Issue
Block a user