File size: 8,844 Bytes
06c11b0 | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 | #!/bin/bash
# 后台运行脚本 - 统一管理 HistoryBench Gradio 服务器
# 使用方法: bash run_background.sh [start|stop|status|restart|logs]
# 获取脚本所在目录,然后定位到 gradio 目录
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
GRADIO_DIR="$(cd "$SCRIPT_DIR/.." && pwd)"
cd "$GRADIO_DIR"
# Micromamba 环境路径
MICROMAMBA_ENV="/data/hongzefu/maniskillenv1120"
# 日志目录(放在 gradio 目录中)
LOG_DIR="$GRADIO_DIR/logs"
PID_FILE="$GRADIO_DIR/server.pid"
# 合并日志文件(包含所有输出:标准输出 + 错误输出)
LOG_FILE="$LOG_DIR/server.log"
# 创建日志目录
mkdir -p "$LOG_DIR"
# 函数:启动服务器
start_server() {
# 检查是否已经在运行
if [ -f "$PID_FILE" ]; then
OLD_PID=$(cat "$PID_FILE")
if ps -p "$OLD_PID" > /dev/null 2>&1; then
echo "⚠️ 服务器已经在运行中 (PID: $OLD_PID)"
echo " 如需重启,请使用: bash $0 restart"
return 1
else
echo "清理旧的 PID 文件..."
rm -f "$PID_FILE"
fi
fi
# 检查 micromamba 环境是否存在
if [ ! -d "$MICROMAMBA_ENV" ]; then
echo "❌ 错误: Micromamba 环境不存在: $MICROMAMBA_ENV"
return 1
fi
# 检查 Python 可执行文件
PYTHON_EXE="$MICROMAMBA_ENV/bin/python"
if [ ! -f "$PYTHON_EXE" ]; then
echo "❌ 错误: Python 可执行文件不存在: $PYTHON_EXE"
return 1
fi
# 启动服务器
echo "🚀 正在后台启动服务器..."
echo " Micromamba 环境: $MICROMAMBA_ENV"
echo " Python 可执行文件: $PYTHON_EXE"
echo " 工作目录: $GRADIO_DIR"
echo " 日志文件: $LOG_FILE"
echo ""
# 使用环境中的 Python 直接运行服务器
# 使用 nohup 在后台运行,并将所有输出重定向到日志文件
# 设置环境变量以确保使用环境中的包和正确的输出行为
# 使用 unbuffered 模式 (-u) 和 PYTHONUNBUFFERED=1 确保输出立即写入,不缓冲
# 使用 stdbuf -oL -eL 确保行缓冲输出(如果可用)
# 将标准输出和错误输出合并到一个文件 (2>&1),这样所有日志都会完整显示
# 使用 >> 追加模式,确保日志不会覆盖
# 检查是否可以使用 stdbuf(Linux 系统通常有)
if command -v stdbuf >/dev/null 2>&1; then
# 使用 stdbuf 确保行缓冲输出,所有 print 和日志都会实时写入
nohup env PATH="$MICROMAMBA_ENV/bin:$PATH" \
PYTHONUNBUFFERED=1 \
PYTHONIOENCODING=utf-8 \
stdbuf -oL -eL "$PYTHON_EXE" -u "$GRADIO_DIR/main.py" >> "$LOG_FILE" 2>&1 &
else
# 如果没有 stdbuf,使用 Python 的 unbuffered 模式
# 仍然设置所有必要的环境变量确保输出实时写入
nohup env PATH="$MICROMAMBA_ENV/bin:$PATH" \
PYTHONUNBUFFERED=1 \
PYTHONIOENCODING=utf-8 \
"$PYTHON_EXE" -u "$GRADIO_DIR/main.py" >> "$LOG_FILE" 2>&1 &
fi
# 保存进程ID
SERVER_PID=$!
echo $SERVER_PID > "$PID_FILE"
# 等待一下,检查进程是否成功启动
sleep 3
if ps -p "$SERVER_PID" > /dev/null 2>&1; then
echo "✅ 服务器已成功在后台启动!"
echo " PID: $SERVER_PID"
echo " Micromamba 环境: $MICROMAMBA_ENV"
echo " 日志文件: $LOG_FILE"
echo ""
echo "📋 常用命令:"
echo " 查看实时日志: bash $0 logs"
echo " 查看状态: bash $0 status"
echo " 停止服务器: bash $0 stop"
echo ""
echo "💡 提示:"
echo " - 所有输出都保存在 $LOG_FILE(包括所有 print、uvicorn 日志等)"
echo " - 日志实时写入,与前台运行完全一致"
echo " - 即使关闭SSH连接,服务器也会继续运行"
echo " - 使用 PYTHONUNBUFFERED=1 和 stdbuf 确保日志实时写入"
echo ""
echo "🌐 服务器启动后,请查看日志文件获取访问地址:"
echo " bash $0 logs"
return 0
else
echo "❌ 服务器启动失败!"
echo " 请查看完整日志: $LOG_FILE"
rm -f "$PID_FILE"
return 1
fi
}
# 函数:停止服务器
stop_server() {
# 检查PID文件是否存在
if [ ! -f "$PID_FILE" ]; then
echo "⚠️ 未找到 PID 文件,服务器可能未运行"
return 1
fi
# 读取PID
SERVER_PID=$(cat "$PID_FILE")
# 检查进程是否存在
if ! ps -p "$SERVER_PID" > /dev/null 2>&1; then
echo "⚠️ 进程 $SERVER_PID 不存在,可能已经停止"
rm -f "$PID_FILE"
return 1
fi
# 停止进程
echo "🛑 正在停止服务器 (PID: $SERVER_PID)..."
kill "$SERVER_PID"
# 等待进程结束(最多等待10秒)
for i in {1..10}; do
if ! ps -p "$SERVER_PID" > /dev/null 2>&1; then
echo "✅ 服务器已成功停止"
rm -f "$PID_FILE"
return 0
fi
sleep 1
done
# 如果还在运行,强制杀死
if ps -p "$SERVER_PID" > /dev/null 2>&1; then
echo "⚠️ 进程未响应,强制终止..."
kill -9 "$SERVER_PID"
sleep 1
if ! ps -p "$SERVER_PID" > /dev/null 2>&1; then
echo "✅ 服务器已强制停止"
rm -f "$PID_FILE"
return 0
else
echo "❌ 无法停止服务器,请手动检查"
return 1
fi
fi
}
# 函数:查看服务器状态
status_server() {
echo "📊 服务器状态信息"
echo "=========================================="
# 检查PID文件
if [ ! -f "$PID_FILE" ]; then
echo "❌ 服务器未运行 (未找到 PID 文件)"
return 1
fi
SERVER_PID=$(cat "$PID_FILE")
# 检查进程是否存在
if ps -p "$SERVER_PID" > /dev/null 2>&1; then
echo "✅ 服务器正在运行"
echo " PID: $SERVER_PID"
echo ""
# 显示进程信息
echo "📋 进程信息:"
ps -p "$SERVER_PID" -o pid,ppid,user,%cpu,%mem,etime,cmd
echo ""
# 显示日志文件信息
if [ -f "$LOG_FILE" ]; then
LOG_SIZE=$(du -h "$LOG_FILE" | cut -f1)
LOG_LINES=$(wc -l < "$LOG_FILE" 2>/dev/null || echo "0")
echo "📄 日志文件信息:"
echo " 文件: $LOG_FILE"
echo " 大小: $LOG_SIZE"
echo " 行数: $LOG_LINES"
echo " 最后修改: $(stat -c %y "$LOG_FILE" 2>/dev/null || stat -f %Sm "$LOG_FILE" 2>/dev/null || echo "未知")"
fi
# 显示最后几行日志
if [ -f "$LOG_FILE" ]; then
echo ""
echo "📝 最近的日志输出 (最后10行):"
echo "----------------------------------------"
tail -n 10 "$LOG_FILE"
fi
return 0
else
echo "❌ 服务器未运行 (进程 $SERVER_PID 不存在)"
echo " 清理 PID 文件..."
rm -f "$PID_FILE"
return 1
fi
}
# 函数:重启服务器
restart_server() {
echo "🔄 正在重启服务器..."
stop_server
sleep 2
start_server
}
# 函数:查看日志
view_logs() {
if [ ! -f "$LOG_FILE" ]; then
echo "⚠️ 日志文件不存在: $LOG_FILE"
return 1
fi
echo "📝 查看服务器日志 (按 Ctrl+C 退出)"
echo "=========================================="
tail -f "$LOG_FILE"
}
# 函数:显示帮助信息
show_help() {
echo "HistoryBench 服务器管理脚本"
echo ""
echo "使用方法:"
echo " bash $0 [命令]"
echo ""
echo "可用命令:"
echo " start - 启动服务器(后台运行)"
echo " stop - 停止服务器"
echo " status - 查看服务器状态"
echo " restart - 重启服务器"
echo " logs - 查看实时日志(按 Ctrl+C 退出)"
echo " help - 显示此帮助信息"
echo ""
echo "示例:"
echo " bash $0 start # 启动服务器"
echo " bash $0 status # 查看状态"
echo " bash $0 logs # 查看日志"
echo " bash $0 stop # 停止服务器"
echo ""
}
# 主逻辑:根据命令行参数执行相应操作
case "${1:-help}" in
start)
start_server
;;
stop)
stop_server
;;
status)
status_server
;;
restart)
restart_server
;;
logs)
view_logs
;;
help|--help|-h)
show_help
;;
*)
echo "❌ 未知命令: $1"
echo ""
show_help
exit 1
;;
esac
exit $?
|