Files
ailine/scripts/start.sh
root a92a220ff3
Some checks failed
构建并部署 AI Agent 服务 / deploy (push) Has been cancelled
采用向量数据库实现长期记忆
2026-04-15 23:52:13 +08:00

431 lines
14 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
# =============================================================================
# AI Agent 启动与管理脚本
# 用法: ./start.sh [check|backend|frontend|both|docker-up|docker-down]
# =============================================================================
set -e
# 颜色定义
GREEN='\033[0;32m'
BLUE='\033[0;34m'
RED='\033[0;31m'
YELLOW='\033[1;33m'
NC='\033[0m' # No Color
# 项目根目录
PROJECT_DIR="/home/huang/Study/AIProject/Agent1"
echo -e "${BLUE}========================================${NC}"
echo -e "${BLUE} AI Agent - 个人生活助手${NC}"
echo -e "${BLUE}========================================${NC}"
echo ""
# =============================================================================
# 配置检查函数
# =============================================================================
check_config() {
echo -e "${BLUE}📋 开始环境配置检查...${NC}"
echo ""
PASS=0
FAIL=0
WARN=0
# 辅助函数
check_pass() {
echo -e "${GREEN}${NC} $1"
((PASS++))
}
check_fail() {
echo -e "${RED}${NC} $1"
((FAIL++))
}
check_warn() {
echo -e "${YELLOW}${NC} $1"
((WARN++))
}
# 1. 检查 .env 文件
echo "🔍 检查配置文件..."
if [ -f "$PROJECT_DIR/.env" ]; then
check_pass ".env 文件存在"
# 检查文件格式
if grep -q "^EOF" .env 2>/dev/null; then
check_fail ".env 文件格式错误:发现多余的 EOF 标记"
else
check_pass ".env 文件格式正确"
fi
else
check_fail ".env 文件不存在"
echo " 提示: 请创建 .env 文件并配置环境变量"
return 1
fi
# 2. 检查必需的环境变量
echo ""
echo "🔑 检查环境变量..."
# 检查 ZHIPUAI_API_KEY
if grep -q "^ZHIPUAI_API_KEY=" "$PROJECT_DIR/.env" 2>/dev/null; then
API_KEY=$(grep "^ZHIPUAI_API_KEY=" "$PROJECT_DIR/.env" | head -1 | cut -d'=' -f2- | tr -d '[:space:]')
if [ ${#API_KEY} -gt 10 ]; then
check_pass "ZHIPUAI_API_KEY 已配置(长度: ${#API_KEY}"
else
check_fail "ZHIPUAI_API_KEY 配置可能无效(过短)"
fi
else
check_fail "ZHIPUAI_API_KEY 未配置或格式错误"
fi
# 检查 VLLM_LOCAL_KEY
if grep -q "^VLLM_LOCAL_KEY=" "$PROJECT_DIR/.env" 2>/dev/null; then
check_pass "VLLM_LOCAL_KEY 已配置"
else
check_warn "VLLM_LOCAL_KEY 未配置(如不使用本地模型可忽略)"
fi
# 检查 DB_URI (远程服务器)
if grep -q "^DB_URI=.*115.190.121.151" "$PROJECT_DIR/.env" 2>/dev/null; then
check_pass "DB_URI 已配置(远程服务器)"
elif grep -q "^DB_URI=" "$PROJECT_DIR/.env" 2>/dev/null; then
check_warn "DB_URI 已配置(非远程服务器地址)"
else
check_fail "DB_URI 未配置"
fi
# 检查 QDRANT_URL (远程服务器)
if grep -q "^QDRANT_URL=.*115.190.121.151" "$PROJECT_DIR/.env" 2>/dev/null; then
check_pass "QDRANT_URL 已配置(远程服务器)"
elif grep -q "^QDRANT_URL=" "$PROJECT_DIR/.env" 2>/dev/null; then
check_warn "QDRANT_URL 已配置(非远程服务器地址)"
else
check_fail "QDRANT_URL 未配置"
fi
# 3. 检查 Docker 环境
echo ""
echo "🐳 检查 Docker 环境..."
if command -v docker &> /dev/null; then
check_pass "Docker 已安装"
if docker info &> /dev/null; then
check_pass "Docker 守护进程正在运行"
else
check_fail "Docker 守护进程未运行"
echo " 提示: sudo systemctl start docker"
fi
else
check_fail "Docker 未安装"
fi
if command -v docker compose version &> /dev/null || command -v docker-compose &> /dev/null; then
check_pass "Docker Compose 已安装"
else
check_fail "Docker Compose 未安装"
fi
# 4. 检查端口占用
echo ""
echo "🔌 检查端口占用..."
for port in 8001 8501; do
if lsof -i :$port &> /dev/null; then
check_warn "端口 $port 已被占用"
else
check_pass "端口 $port 可用"
fi
done
# 5. 检查远程服务连接
echo ""
echo "🌐 检查远程服务连接..."
# 测试 PostgreSQL 连接
if command -v psql &> /dev/null; then
# 注意:这里假设密码为 mysecretpassword如果不同需调整或从 env 读取
if PGPASSWORD=mysecretpassword psql -h 115.190.121.151 -U postgres -d langgraph_db -c "SELECT 1;" &> /dev/null; then
check_pass "PostgreSQL 远程连接正常 (115.190.121.151:5432)"
else
check_fail "PostgreSQL 远程连接失败"
echo " 提示: 检查网络连接和防火墙设置"
fi
else
check_warn "psql 客户端未安装,跳过 PostgreSQL 连接测试"
fi
# 测试 Qdrant 连接
if curl -s http://115.190.121.151:6333/collections &> /dev/null; then
check_pass "Qdrant 远程连接正常 (115.190.121.151:6333)"
else
check_fail "Qdrant 远程连接失败"
echo " 提示: 检查网络连接和防火墙设置"
fi
# 总结
echo ""
echo "=========================================="
echo " 检查结果汇总"
echo "=========================================="
echo -e "${GREEN}通过: $PASS${NC}"
echo -e "${RED}失败: $FAIL${NC}"
echo -e "${YELLOW}警告: $WARN${NC}"
echo ""
if [ $FAIL -eq 0 ]; then
echo -e "${GREEN}✅ 配置检查通过!${NC}"
return 0
else
echo -e "${RED}❌ 发现 $FAIL 个错误,请修复后重试${NC}"
return 1
fi
}
# =============================================================================
# Docker 容器检查函数(仅检查 llama.cpp 服务)
# =============================================================================
check_llamacpp() {
echo -e "${BLUE}🔍 检查 llama.cpp LLM 容器...${NC}"
if ! docker ps --format '{{.Names}}' | grep -q "^gemma4-llamacpp-server$"; then
echo -e "${YELLOW}⚠️ llama.cpp LLM 容器未运行${NC}"
return 1
else
echo -e "${GREEN}✓ llama.cpp LLM 容器正在运行 (gemma4-llamacpp-server)${NC}"
return 0
fi
}
check_embedding() {
echo -e "${BLUE}🔍 检查 llama.cpp Embedding 容器...${NC}"
if ! docker ps --format '{{.Names}}' | grep -q "^embedding-server$"; then
echo -e "${YELLOW}⚠️ llama.cpp Embedding 容器未运行${NC}"
return 1
else
echo -e "${GREEN}✓ llama.cpp Embedding 容器正在运行 (embedding-server)${NC}"
return 0
fi
}
# =============================================================================
# 启动 Docker 依赖服务llama.cpp
# =============================================================================
start_llamacpp() {
echo -e "${BLUE}🚀 启动 llama.cpp LLM 容器...${NC}"
# 检查模型文件
if [ ! -f "/home/huang/Study/AIModel/GGUF/Gemma-4-E2B-Uncensored-HauhauCS-Aggressive-Q6_K_P.gguf" ]; then
echo -e "${RED}✗ 错误LLM 模型文件不存在${NC}"
exit 1
fi
if [ ! -f "/home/huang/Study/AIModel/GGUF/mmproj-Gemma-4-E2B-Uncensored-HauhauCS-Aggressive-f16.gguf" ]; then
echo -e "${RED}✗ 错误:多模态投影文件不存在${NC}"
exit 1
fi
docker run -d \
--name gemma4-llamacpp-server \
--restart=unless-stopped \
--group-add=video \
--device=/dev/kfd \
--device=/dev/dri \
-v /home/huang/Study/AIModel/GGUF:/models \
-p 8081:8080 \
ghcr.io/ggml-org/llama.cpp:server-rocm \
-m /models/Gemma-4-E2B-Uncensored-HauhauCS-Aggressive-Q6_K_P.gguf \
--mmproj /models/mmproj-Gemma-4-E2B-Uncensored-HauhauCS-Aggressive-f16.gguf \
--host 0.0.0.0 \
--port 8080 \
-ngl 99
echo -e "${GREEN}✓ llama.cpp LLM 容器已启动 (端口 8081)${NC}"
echo -e "${YELLOW}⏳ 等待模型加载(可能需要几分钟)...${NC}"
sleep 15
}
start_embedding() {
echo -e "${BLUE}🚀 启动 llama.cpp Embedding 容器...${NC}"
# 检查模型文件
if [ ! -f "/home/huang/Study/AIModel/GGUF/embeddinggemma-300M-Q8_0.gguf" ]; then
echo -e "${RED}✗ 错误Embedding 模型文件不存在${NC}"
exit 1
fi
docker run -d \
--name embedding-server \
--restart=unless-stopped \
--group-add=video \
--device=/dev/kfd \
--device=/dev/dri \
-v /home/huang/Study/AIModel/GGUF:/models \
-p 8082:8080 \
ghcr.io/ggml-org/llama.cpp:server-rocm \
-m /models/embeddinggemma-300M-Q8_0.gguf \
--host 0.0.0.0 \
--port 8080 \
-ngl 99 \
--embeddings \
-c 512
echo -e "${GREEN}✓ llama.cpp Embedding 容器已启动 (端口 8082)${NC}"
sleep 5
}
# =============================================================================
# 启动 Python 服务
# =============================================================================
start_backend() {
echo -e "\n${BLUE}🚀 启动后端服务 (端口 8003)...${NC}"
cd "$PROJECT_DIR"
# 加载 .env 文件中的环境变量
set -a
source .env 2>/dev/null || true
set +a
export PYTHONPATH="$PROJECT_DIR"
export BACKEND_PORT=8003
python app/backend.py &
BACKEND_PID=$!
echo -e "${GREEN}✓ 后端服务已启动 (PID: $BACKEND_PID)${NC}"
sleep 2
}
start_frontend() {
echo -e "\n${BLUE}🎨 启动前端界面 (端口 8501)...${NC}"
cd "$PROJECT_DIR"
# 加载 .env 文件中的环境变量
set -a
source .env 2>/dev/null || true
set +a
export PYTHONPATH="$PROJECT_DIR"
streamlit run frontend/frontend.py &
FRONTEND_PID=$!
echo -e "${GREEN}✓ 前端服务已启动 (PID: $FRONTEND_PID)${NC}"
echo -e "${GREEN}✓ 访问地址:${NC}"
echo -e " 本地开发: http://localhost:8501"
}
# =============================================================================
# Docker Compose 管理
# =============================================================================
docker_up() {
echo -e "${BLUE}🐳 使用 Docker Compose 启动所有服务...${NC}"
cd "$PROJECT_DIR/docker"
# 检查 .env 文件
if [ ! -f "../.env" ]; then
echo -e "${RED}✗ 错误:.env 文件不存在${NC}"
echo " 请先复制配置文件:"
echo " cp .env.docker .env # 服务器部署"
exit 1
fi
docker compose up -d --build
echo -e "\n${GREEN}✓ Docker Compose 服务已启动${NC}"
echo -e "${BLUE}📊 查看服务状态:${NC} docker compose ps"
echo -e "${BLUE}📝 查看日志:${NC} docker compose logs -f"
echo -e "${BLUE}🌐 访问应用:${NC} http://localhost:8501"
}
docker_down() {
echo -e "${BLUE}🛑 停止 Docker Compose 服务...${NC}"
cd "$PROJECT_DIR/docker"
docker compose down
echo -e "${GREEN}✓ 服务已停止${NC}"
}
# =============================================================================
# 清理函数
# =============================================================================
cleanup() {
echo -e "\n${RED}🛑 正在停止 Python 服务...${NC}"
if [ ! -z "$BACKEND_PID" ]; then
kill $BACKEND_PID 2>/dev/null || true
echo -e "${GREEN}✓ 后端服务已停止${NC}"
fi
if [ ! -z "$FRONTEND_PID" ]; then
kill $FRONTEND_PID 2>/dev/null || true
echo -e "${GREEN}✓ 前端服务已停止${NC}"
fi
echo -e "${YELLOW}💡 提示Docker 容器需要手动停止${NC}"
echo -e " 停止 llama.cpp LLM: docker stop gemma4-llamacpp-server"
echo -e " 停止 llama.cpp Embedding: docker stop embedding-server"
echo -e " 或使用: $0 docker-down"
exit 0
}
# 捕获 Ctrl+C
trap cleanup SIGINT SIGTERM
# =============================================================================
# 主逻辑
# =============================================================================
case "${1:-help}" in
check)
check_config
;;
backend)
check_config || exit 1
check_llamacpp || start_llamacpp
check_embedding || start_embedding
start_backend
echo -e "\n${GREEN}后端服务正在运行,按 Ctrl+C 停止${NC}"
wait $BACKEND_PID
;;
frontend)
check_config || exit 1
start_frontend
echo -e "\n${GREEN}前端服务正在运行,按 Ctrl+C 停止${NC}"
wait $FRONTEND_PID
;;
both)
check_config || exit 1
check_llamacpp || start_llamacpp
check_embedding || start_embedding
start_backend
start_frontend
echo -e "\n${GREEN}所有服务正在运行,按 Ctrl+C 停止 Python 服务${NC}"
echo -e "${YELLOW}注意Docker 容器会在后台继续运行${NC}"
wait
;;
docker-up)
check_config || exit 1
docker_up
;;
docker-down)
docker_down
;;
help|*)
echo -e "${BLUE}用法:${NC} $0 [command]"
echo ""
echo -e "${BLUE}命令:${NC}"
echo " check 检查环境配置"
echo " backend 仅启动后端服务"
echo " frontend 仅启动前端服务"
echo " both 启动前后端服务(默认)"
echo " docker-up 使用 Docker Compose 启动所有服务"
echo " docker-down 停止 Docker Compose 服务"
echo " help 显示此帮助信息"
echo ""
echo -e "${BLUE}示例:${NC}"
echo " $0 check # 检查配置"
echo " $0 both # 启动本地开发环境"
echo " $0 docker-up # 启动 Docker 部署环境"
;;
esac