- U0:新建 plantai-rag-new-venv(3.12.13,130 包),torch 2.13.0+cpu/cython 3.2.8/faiss 1.14.3/openai 3.3.1,requirements.lock 固化 - U1:四树全 venv 重编译(sdk 15/qa 45/methodology 28/legacy 283 .so 全 cp312),audit 双审计过 - U2:备用端口影子对照:金标 search evidence 30/30 与生产一致、SDK pytest 125 过、五上游绿 - U3:统一树切终态 8091/8092/8093 + BFF 8090(venv),停旧服务(容器/进程不删,30 天窗) - U4:minerupy311→minerupy312 断链修复、GF_PYTHON_ENV 回退统一、start-dev/run/bff_restart 去 conda、server.env/README 更新 Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
132 lines
6.2 KiB
Bash
Executable File
132 lines
6.2 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
# build_all.sh —— 一键将 4 部分最新版本编译打包为安装目录 + 部署脚本。
|
|
# 流水线:编译 SDK+3 agent → 双审计 → 冒烟 → (定版后:KB 加密打包)→ 组装 → SHA256SUMS → 泄露门禁
|
|
# 用法:bash tooling/build_all.sh [版本] (版本默认读 tooling.env VERSION)
|
|
set -euo pipefail
|
|
umask 027
|
|
|
|
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|
PROJECT_ROOT="$(cd "$SCRIPT_DIR/.." && pwd)"
|
|
. "$SCRIPT_DIR/tooling.env"
|
|
VERSION="${1:-$VERSION}"
|
|
BUILD_ROOT="$SCRIPT_DIR/build/$VERSION"
|
|
RELEASE_ROOT="$BUILD_ROOT/install"
|
|
|
|
echo "== build_all.sh $VERSION =="
|
|
echo "工程根: $PROJECT_ROOT"
|
|
mkdir -p "$BUILD_ROOT"
|
|
|
|
# ---- 1. 编译四部分 ----
|
|
echo "[1/6] 编译 SDK + 3 agent"
|
|
"$SDK_PYTHON" -c 'import Cython' || { echo "SDK_PYTHON 缺 Cython" >&2; exit 1; }
|
|
"$QA_PYTHON" -c 'import Cython' || { echo "QA_PYTHON 缺 Cython" >&2; exit 1; }
|
|
"$LEGACY_PYTHON" -c 'import Cython' || { echo "LEGACY_PYTHON 缺 Cython" >&2; exit 1; }
|
|
|
|
rm -rf "$BUILD_ROOT/compiled"
|
|
mkdir -p "$BUILD_ROOT/compiled"
|
|
bash "$SCRIPT_DIR/compile/compile_sdk.sh" \
|
|
"$PROJECT_ROOT/sdk" "$BUILD_ROOT/compiled/sdk" "$SDK_PYTHON"
|
|
bash "$SCRIPT_DIR/compile/compile_qa.sh" \
|
|
"$PROJECT_ROOT/agent/qa" "$BUILD_ROOT/compiled/qa" "$QA_PYTHON"
|
|
bash "$SCRIPT_DIR/compile/compile_methodology.sh" \
|
|
"$PROJECT_ROOT/agent/methodology" "$BUILD_ROOT/compiled/methodology" "$METHODOLOGY_PYTHON"
|
|
bash "$SCRIPT_DIR/compile/compile_legacy.sh" \
|
|
"$PROJECT_ROOT/agent/legacy-rag" "$BUILD_ROOT/compiled/legacy-rag" "$LEGACY_PYTHON"
|
|
|
|
# ---- 2. 双审计(各树用编译时的 Python——ABI 后缀必须匹配) ----
|
|
echo "[2/6] 编译树审计"
|
|
AUDIT="$SCRIPT_DIR/compile/tools/audit_compiled_tree.py"
|
|
declare -A TREE_PY=( [sdk]="$SDK_PYTHON" [qa]="$QA_PYTHON" [methodology]="$METHODOLOGY_PYTHON" [legacy-rag]="$LEGACY_PYTHON" )
|
|
for tree in sdk qa methodology legacy-rag; do
|
|
py="${TREE_PY[$tree]}"
|
|
"$py" "$AUDIT" --tree "$BUILD_ROOT/compiled/$tree" --project "$tree" --write-marker \
|
|
| python3 -c "import json,sys; r=json.load(sys.stdin); print(f' $tree: ok={r[\"ok\"]} exts={r[\"extension_count\"]}'); sys.exit(0 if r['ok'] else 1)" \
|
|
|| { echo "$tree 审计失败" >&2; exit 2; }
|
|
"$py" "$AUDIT" --tree "$BUILD_ROOT/compiled/$tree" --project "$tree" --require-marker \
|
|
>/dev/null || { echo "$tree marker 校验失败" >&2; exit 2; }
|
|
done
|
|
|
|
# ---- 3. 冒烟(起服务探 /health,全 .so import 检查) ----
|
|
echo "[3/6] 冒烟(import 检查,服务起停由部署脚本承担)"
|
|
for tree in sdk qa methodology legacy-rag; do
|
|
py="$SDK_PYTHON"; [ "$tree" = "qa" ] && py="$QA_PYTHON"; [ "$tree" = "methodology" ] && py="$METHODOLOGY_PYTHON"; [ "$tree" = "legacy-rag" ] && py="$LEGACY_RUN_PYTHON"
|
|
if [ "$tree" = "sdk" ]; then
|
|
( cd "$BUILD_ROOT/compiled/sdk" && PYTHONPATH=. "$py" -c "import app.main" )
|
|
elif [ "$tree" = "qa" ]; then
|
|
( cd "$BUILD_ROOT/compiled/qa" && PYTHONPATH=.:./src "$py" -c "import scripts.qa_v1_1_73_server" )
|
|
elif [ "$tree" = "methodology" ]; then
|
|
( cd "$BUILD_ROOT/compiled/methodology" && PYTHONPATH=. "$py" -c "import scripts.methodology_server" )
|
|
else
|
|
( cd "$BUILD_ROOT/compiled/legacy-rag" && PYTHONPATH=. "$py" -c "import api.app" )
|
|
fi
|
|
echo " $tree import OK"
|
|
done
|
|
|
|
# ---- 4. KB(定版后 SKIP_KB=0 启用) ----
|
|
if [ "${SKIP_KB:-1}" = "0" ]; then
|
|
echo "[4/6] KB 加密打包(定版后)"
|
|
KB_KEY_FILE="${KB_KEY_FILE:-$BUILD_ROOT/kb.key}"
|
|
[ -f "$KB_KEY_FILE" ] || { echo "缺 KB 密钥: $KB_KEY_FILE" >&2; exit 1; }
|
|
KB_KEY_FILE="$KB_KEY_FILE" bash "$SCRIPT_DIR/kb/encrypt_kb.sh" "$VERSION"
|
|
else
|
|
echo "[4/6] KB 跳过(SKIP_KB=1,数据库未定版;操作见 tooling/KB_ENCRYPT_GUIDE.md)"
|
|
fi
|
|
|
|
# ---- 5. 组装安装目录 ----
|
|
echo "[5/6] 组装安装目录"
|
|
rm -rf "$RELEASE_ROOT"
|
|
mkdir -p "$RELEASE_ROOT"
|
|
cp -r "$BUILD_ROOT/compiled/sdk" "$RELEASE_ROOT/sdk"
|
|
cp -r "$BUILD_ROOT/compiled/qa" "$RELEASE_ROOT/qa"
|
|
cp -r "$BUILD_ROOT/compiled/methodology" "$RELEASE_ROOT/methodology"
|
|
cp -r "$BUILD_ROOT/compiled/legacy-rag" "$RELEASE_ROOT/legacy-rag"
|
|
# UI 产物
|
|
( cd "$PROJECT_ROOT/ui" && npm run build --silent ) || { echo "ui build 失败" >&2; exit 5; }
|
|
mkdir -p "$RELEASE_ROOT/ui"
|
|
cp -r "$PROJECT_ROOT/ui/dist" "$RELEASE_ROOT/ui/dist"
|
|
# 启动脚本模板
|
|
cp "$PROJECT_ROOT/agent/qa/scripts/"*.sh "$RELEASE_ROOT/qa/scripts/" 2>/dev/null || true
|
|
cp "$PROJECT_ROOT/agent/methodology/scripts/"*.sh "$RELEASE_ROOT/methodology/scripts/" 2>/dev/null || true
|
|
cp "$PROJECT_ROOT/agent/legacy-rag/scripts/"*.sh "$RELEASE_ROOT/legacy-rag/scripts/" 2>/dev/null || true
|
|
# env 模板
|
|
for t in qa methodology legacy-rag; do
|
|
cp "$PROJECT_ROOT/agent/$t/env/prod.env.example" "$RELEASE_ROOT/$t/env/prod.env.example" 2>/dev/null || true
|
|
done
|
|
cp "$PROJECT_ROOT/sdk/.env.example" "$RELEASE_ROOT/sdk/.env.example" 2>/dev/null || true
|
|
# KB 包(定版后)
|
|
[ -f "$BUILD_ROOT/knowledge-$VERSION.tar" ] && cp "$BUILD_ROOT/knowledge-$VERSION.tar"* "$RELEASE_ROOT/"
|
|
# 部署脚本
|
|
cat > "$RELEASE_ROOT/start_all.sh" <<'DEPLOY'
|
|
#!/usr/bin/env bash
|
|
# start_all.sh —— 安装目录一键启动(端口 8090 段)
|
|
# 用法:bash start_all.sh [bind] (bind 默认 0.0.0.0)
|
|
set -euo pipefail
|
|
ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|
BIND="${1:-0.0.0.0}"
|
|
echo "== 启动 PlantAI-rag-new 四服务 =="
|
|
bash "$ROOT/qa/scripts/start.sh" 8091 || true
|
|
bash "$ROOT/methodology/scripts/start.sh" 8092 || true
|
|
bash "$ROOT/legacy-rag/scripts/start.sh" 8093 app || true
|
|
sleep 3
|
|
( cd "$ROOT/sdk" && setsid python -m uvicorn app.main:app --host "$BIND" --port 8090 \
|
|
> /tmp/plantai-sdk.log 2>&1 < /dev/null & )
|
|
echo "BFF 启动中(8090),5 秒后自检:"
|
|
sleep 5
|
|
curl -s --max-time 15 http://127.0.0.1:8090/api/health | head -c 300
|
|
echo
|
|
DEPLOY
|
|
chmod +x "$RELEASE_ROOT/start_all.sh"
|
|
|
|
# ---- 6. SHA256SUMS + 泄露门禁 ----
|
|
echo "[6/6] SHA256SUMS + 泄露检查"
|
|
( cd "$RELEASE_ROOT" && find . -type f -exec sha256sum {} \; | sort -k2 > SHA256SUMS )
|
|
LEAKS=$(grep -rnE "BEGIN (RSA |EC |OPENSSH )?PRIVATE KEY|sk-[a-zA-Z0-9]{20}|kb\.key" "$RELEASE_ROOT" 2>/dev/null | grep -v SHA256SUMS | head -5 || true)
|
|
if [ -n "$LEAKS" ]; then
|
|
echo "泄露门禁失败:" >&2; echo "$LEAKS" >&2; exit 6
|
|
fi
|
|
echo "泄露检查: 净"
|
|
echo
|
|
echo "== 构建完成: $RELEASE_ROOT =="
|
|
du -sh "$RELEASE_ROOT"
|
|
echo "下一步:空目录全新安装验收(备用端口 8094/8095/8096/8097)"
|