feat(release): 新增开箱启动脚本 setup.sh / start.sh(P4 第一步)
为 release 开箱即用提供入口,把首启向导串进启动流程。Python/Node 均 依赖系统已装运行时(不内置解释器),便携包只带源码 + venv 创建逻辑。 - _bootstrap.sh: 共享引导逻辑(被 source) - ensure_python_env: 系统 python 建/复用 .venv,装 requirements.lock.txt - ensure_node_env: 系统 node 装 easyagent 依赖 + 前端构建(缺失才装) - has_env_file: 首启判断 - setup.sh: 初始化入口 → 备好环境 → 跑 python -m scripts.setup 向导 - start.sh: 启动入口 → 备好环境 → 无 .env 自动跑向导 → python -m server.app (透传参数给 server.app,如 --thinking-mode) - CLAUDE.md: Build & Run 增加开箱方式(./setup.sh / ./start.sh)与 requirements.lock 说明 验证:bash -n 语法通过;_bootstrap 函数逻辑(ROOT 定位 / 选系统 python / has_env_file / node_modules 已存在时跳过)实测正确;setup 向导在系统 Python 3.9 下端到端跑通(含写文件),确认 from __future__ annotations 使新式类型注解在 3.9 兼容。 注:实际「建 venv + 联网装依赖 + 解压验证」需在本机网络环境执行; 沙箱内仅做了不联网的逻辑校验。 Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
1d3703b0e5
commit
582f292114
12
CLAUDE.md
12
CLAUDE.md
@ -61,8 +61,18 @@ This file provides guidance to Claude Code (claude.ai/code) when working with co
|
||||
|
||||
### Build & Run
|
||||
```bash
|
||||
# === 开箱即用(release / 首次部署,推荐)===
|
||||
# 首次初始化:建 venv、装依赖、跑配置向导(模式/端口/管理员/密钥/模型)
|
||||
./setup.sh
|
||||
# 启动(首次无 .env 会自动跑向导,然后起服务)
|
||||
./start.sh
|
||||
# start.sh 透传参数给 server.app,例如:
|
||||
./start.sh --thinking-mode
|
||||
|
||||
# === 手动方式(开发) ===
|
||||
# 安装 Python 依赖
|
||||
pip install -r requirements.txt
|
||||
pip install -r requirements.txt # 开发用,宽松
|
||||
pip install -r requirements.lock.txt # 可复现/打包用,精确版本
|
||||
|
||||
# 构建终端镜像
|
||||
docker build -f docker/terminal.Dockerfile -t my-agent-shell:latest .
|
||||
|
||||
80
_bootstrap.sh
Executable file
80
_bootstrap.sh
Executable file
@ -0,0 +1,80 @@
|
||||
#!/usr/bin/env bash
|
||||
# 共享引导逻辑:被 setup.sh / start.sh 引用(source)。
|
||||
# 负责定位项目根、准备 Python venv 与依赖、准备 Node 依赖。
|
||||
# 不直接执行;由入口脚本 source 后调用其中的函数。
|
||||
|
||||
# 出错即停;管道任一环节失败也算失败。
|
||||
set -euo pipefail
|
||||
|
||||
# 项目根目录 = 本脚本所在目录。
|
||||
ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
VENV_DIR="$ROOT/.venv"
|
||||
VENV_PY="$VENV_DIR/bin/python"
|
||||
|
||||
# 选择系统 Python:优先 python3,回退 python。
|
||||
_pick_system_python() {
|
||||
if command -v python3 >/dev/null 2>&1; then
|
||||
echo "python3"
|
||||
elif command -v python >/dev/null 2>&1; then
|
||||
echo "python"
|
||||
else
|
||||
echo ""
|
||||
fi
|
||||
}
|
||||
|
||||
# 准备虚拟环境与 Python 依赖(依赖系统已装 Python,不内置解释器)。
|
||||
# 已存在 venv 则复用;缺失则创建并安装 requirements.lock.txt(优先)或 requirements.txt。
|
||||
ensure_python_env() {
|
||||
if [ ! -x "$VENV_PY" ]; then
|
||||
local sys_py
|
||||
sys_py="$(_pick_system_python)"
|
||||
if [ -z "$sys_py" ]; then
|
||||
echo "[error] 未找到系统 Python(需要 python3 或 python)。请先安装 Python 3.9+。" >&2
|
||||
return 1
|
||||
fi
|
||||
echo "[setup] 使用 $sys_py 创建虚拟环境:$VENV_DIR"
|
||||
"$sys_py" -m venv "$VENV_DIR"
|
||||
fi
|
||||
|
||||
echo "[setup] 升级 pip 并安装依赖..."
|
||||
"$VENV_PY" -m pip install --upgrade pip >/dev/null
|
||||
if [ -f "$ROOT/requirements.lock.txt" ]; then
|
||||
"$VENV_PY" -m pip install -r "$ROOT/requirements.lock.txt"
|
||||
elif [ -f "$ROOT/requirements.txt" ]; then
|
||||
"$VENV_PY" -m pip install -r "$ROOT/requirements.txt"
|
||||
else
|
||||
echo "[error] 找不到 requirements.lock.txt 或 requirements.txt" >&2
|
||||
return 1
|
||||
fi
|
||||
}
|
||||
|
||||
# 准备 Node 依赖(依赖系统已装 Node;不内置 Node)。
|
||||
# easyagent 仅需运行时依赖;前端需要构建产物(vite build)。
|
||||
ensure_node_env() {
|
||||
if ! command -v node >/dev/null 2>&1; then
|
||||
echo "[warn] 未找到系统 Node。子智能体(easyagent)与前端构建将不可用。" >&2
|
||||
echo " 如需完整功能,请安装 Node.js 18+ 后重跑。" >&2
|
||||
return 0
|
||||
fi
|
||||
if ! command -v npm >/dev/null 2>&1; then
|
||||
echo "[warn] 找到 node 但未找到 npm,跳过 Node 依赖安装。" >&2
|
||||
return 0
|
||||
fi
|
||||
|
||||
# easyagent 运行时依赖
|
||||
if [ -f "$ROOT/easyagent/package.json" ] && [ ! -d "$ROOT/easyagent/node_modules" ]; then
|
||||
echo "[setup] 安装 easyagent 依赖(npm ci)..."
|
||||
( cd "$ROOT/easyagent" && npm ci )
|
||||
fi
|
||||
|
||||
# 前端构建产物(static/dist 之类)。仅在缺失时构建,避免每次启动都跑。
|
||||
if [ -f "$ROOT/package.json" ] && [ ! -d "$ROOT/node_modules" ]; then
|
||||
echo "[setup] 安装前端依赖并构建(npm ci && npm run build)..."
|
||||
( cd "$ROOT" && npm ci && npm run build )
|
||||
fi
|
||||
}
|
||||
|
||||
# .env 是否存在(首次启动判断依据)。
|
||||
has_env_file() {
|
||||
[ -f "$ROOT/.env" ]
|
||||
}
|
||||
28
setup.sh
Executable file
28
setup.sh
Executable file
@ -0,0 +1,28 @@
|
||||
#!/usr/bin/env bash
|
||||
# 首次初始化入口:准备运行环境,然后运行交互式配置向导。
|
||||
#
|
||||
# 做的事:
|
||||
# 1. 创建/复用 Python 虚拟环境并安装依赖
|
||||
# 2. 准备 Node 依赖(easyagent / 前端,依赖系统已装 Node)
|
||||
# 3. 运行 python -m scripts.setup 交互式向导,写出 .env 与模型配置
|
||||
#
|
||||
# 用法:
|
||||
# ./setup.sh # 首次初始化(已存在 .env 时向导会提示备份后重配)
|
||||
# ./setup.sh --force # 跳过『已存在 .env』确认(仍会备份)
|
||||
|
||||
set -euo pipefail
|
||||
|
||||
ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
# shellcheck source=_bootstrap.sh
|
||||
source "$ROOT/_bootstrap.sh"
|
||||
|
||||
echo "========================================"
|
||||
echo " AI Agent 初始化"
|
||||
echo "========================================"
|
||||
|
||||
ensure_python_env
|
||||
ensure_node_env
|
||||
|
||||
echo ""
|
||||
echo "[setup] 启动配置向导..."
|
||||
exec "$VENV_PY" -m scripts.setup "$@"
|
||||
42
start.sh
Executable file
42
start.sh
Executable file
@ -0,0 +1,42 @@
|
||||
#!/usr/bin/env bash
|
||||
# 启动入口:准备运行环境(按需),首次运行自动跑配置向导,然后启动 Web 服务。
|
||||
#
|
||||
# 做的事:
|
||||
# 1. 确保 Python venv 与依赖就绪(缺失才安装)
|
||||
# 2. 确保 Node 依赖就绪(缺失才安装)
|
||||
# 3. 若没有 .env(首次启动),自动运行配置向导
|
||||
# 4. 启动 python -m server.app
|
||||
#
|
||||
# 端口/监听地址/模式等由 .env 决定(见 config/server.py、config/paths.py)。
|
||||
# 透传的命令行参数会传给 server.app(如 --port / --path / --thinking-mode)。
|
||||
#
|
||||
# 用法:
|
||||
# ./start.sh # 正常启动(首次会自动初始化)
|
||||
# ./start.sh --thinking-mode # 透传参数给 server.app
|
||||
|
||||
set -euo pipefail
|
||||
|
||||
ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
# shellcheck source=_bootstrap.sh
|
||||
source "$ROOT/_bootstrap.sh"
|
||||
|
||||
# 1+2) 环境就绪(已存在则很快跳过)
|
||||
ensure_python_env
|
||||
ensure_node_env
|
||||
|
||||
# 3) 首次启动:没有 .env 则先跑向导
|
||||
if ! has_env_file; then
|
||||
echo ""
|
||||
echo "[start] 未检测到 .env,进入首次初始化向导..."
|
||||
"$VENV_PY" -m scripts.setup
|
||||
if ! has_env_file; then
|
||||
echo "[start] 初始化未完成(未生成 .env),已退出。" >&2
|
||||
exit 1
|
||||
fi
|
||||
fi
|
||||
|
||||
# 4) 启动服务
|
||||
echo ""
|
||||
echo "[start] 启动 Web 服务..."
|
||||
cd "$ROOT"
|
||||
exec "$VENV_PY" -m server.app "$@"
|
||||
Loading…
Reference in New Issue
Block a user