Files
auto_control/scripts/start.sh
T

85 lines
4.1 KiB
Bash
Executable File
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
#!/bin/bash
# 容器启动脚本:依赖安装(仅首次/缺失时)+ 环境修复 + 启动 web_server。
# compose 的 python-app 服务 command 指向本脚本(不要在 compose 里再跑 pip,
# 否则每次容器重启都重装依赖——实测每轮重新下载 opencv 5.0(73MB) 并破坏 cv2)。
#
# 为什么需要环境修复(必须在 pip install 之后):
# rapidocr_onnxruntime 的依赖声明是 opencv-python(GUI 版),pip 解析依赖时
# 会强制装回它;而 GUI 版依赖 X11 库(libxcb),python:slim 容器里 import cv2
# 直接崩溃 → RapidOCR 不可用 → 条件判断的 OCR 步骤抛异常 → 任务失败退出。
# 因此在安装完 requirements 后,最后强制卸载 GUI 版并装 headless(幂等)。
# 本地 Mac 有 GUI 环境不受影响。
# ---- 依赖就绪守卫:flask/u2/uiautodev/rapidocr/cv2 全部可用则跳过安装 ----
# (容器重启秒级启动;只有首次部署或依赖缺失时才走完整安装)
python3 - <<'PY'
import importlib.util, sys
mods = ("flask", "flask_login", "flask_sqlalchemy", "apscheduler",
"uiautomator2", "uiautodev", "rapidocr_onnxruntime", "PIL",
"fastmcp", "pymysql", "qrcode")
if all(importlib.util.find_spec(m) for m in mods):
try:
import cv2
ok = hasattr(cv2, "__version__") and cv2.__file__ is not None
except Exception:
ok = False
sys.exit(0 if ok else 1)
sys.exit(1)
PY
if [ $? -ne 0 ]; then
echo "[start] 依赖缺失或 cv2 异常,执行安装与环境修复(首次启动较慢)..."
if [ -f requirements.txt ]; then
pip install --no-cache-dir -i https://pypi.tuna.tsinghua.edu.cn/simple -r requirements.txt
fi
# 环境修复:最后强制 headless(覆盖 rapidocr 拉回的 GUI 版)
pip uninstall -y -q opencv-python 2>/dev/null || true
pip install -q -i https://pypi.tuna.tsinghua.edu.cn/simple "opencv-python-headless>=4.8,<5" # 5.x wheel 无 cv2 模块,锁定 4.x
# pip 24.0 解压 abi3 wheel 偶发丢根文件(site-packages/cv2 只剩子目录,
# cv2.abi3.so / __init__.py 缺失 → import cv2 成空壳,OCR 全挂)。
# 手动解压兜底在部分环境修不好(解压后仍无 cv2.__version__),
# 实测 pip --force-reinstall 完整安装有效(220 验证 cv2 4.14.0 恢复)。
python3 - <<'PY'
import subprocess, sys
def cv2_ok():
try:
import cv2
return hasattr(cv2, "__version__") and cv2.__file__ is not None
except Exception:
return False
if cv2_ok():
sys.exit(0)
print("cv2 异常,pip 强制重装 opencv-python-headless...")
r = subprocess.run(["pip", "install", "--force-reinstall", "-q",
"-i", "https://pypi.tuna.tsinghua.edu.cn/simple",
"opencv-python-headless>=4.8,<5"])
if r.returncode == 0:
import cv2
print(f"cv2 {cv2.__version__} 重装修复完成")
sys.exit(r.returncode)
PY
else
echo "[start] 依赖已就绪(cv2 $(python3 -c 'import cv2; print(cv2.__version__)' 2>/dev/null)),跳过安装"
fi
# 启动 MCP server(后台,AI 控制台/外部客户端经 127.0.0.1:8033 调用)。
# web_server.py 内 agent 依赖它,容器重启必须自动拉起(MCP_ENABLED=0 可关)。
# 平台账号:MCP_PLATFORM_USER 默认 admin;密码优先取环境变量(compose/.env),
# 兜底 admin123 与部署时的手动启动参数一致。
if [ -f mcp_server/mcp_server.py ] && [ "${MCP_ENABLED:-1}" = "1" ]; then
echo "[start] 启动 MCP server..."
MCP_ALLOW_WRITE=1 \
MCP_PLATFORM_USER="${MCP_PLATFORM_USER:-admin}" \
MCP_PLATFORM_PASS="${MCP_PLATFORM_PASS:-admin123}" \
MCP_AUDIT_FILE="${MCP_AUDIT_FILE:-/tmp/mcp_audit.log}" \
python3 -m mcp_server.mcp_server > /tmp/mcp_server.log 2>&1 &
fi
# 启动前把"连的是哪个库"打在最显眼的位置(web_server 启动横幅是权威,
# 这里再报一次是防止日志只截到容器入口这几行时看不出环境)
echo "[start] DEPLOY_ENV=${DEPLOY_ENV:-<未设置,默认 dev>} DB_NAME=${DB_NAME:-<未设置>} DB_HOST=${DB_HOST:-<未设置>}"
exec python -u web_server.py