1e1e5957e8
- Ips.vue: el-select 添加 width: 280px,修复网段下拉框过窄 - Ips.vue: query 参数 networkId → network_id(与 FastAPI snake_case 一致) - Scan.vue: el-select 用 network.id 代替整个 network 对象作为 value,修复切换网段不生效 - enhanced_scan_service.py: 替换失效的 scapy ARP 扫描为 arp-scan 命令;扫描结果自动创建缺失 IP 记录
228 lines
6.3 KiB
Bash
Executable File
228 lines
6.3 KiB
Bash
Executable File
#!/bin/bash
|
|
# IPAM 管理系统一键启动脚本
|
|
|
|
echo "=========================================="
|
|
echo " IPAM 管理系统启动脚本"
|
|
echo "=========================================="
|
|
echo ""
|
|
|
|
# 颜色定义
|
|
RED='\033[0;31m'
|
|
GREEN='\033[0;32m'
|
|
YELLOW='\033[1;33m'
|
|
NC='\033[0m' # No Color
|
|
|
|
# 项目根目录
|
|
BASE_DIR="/root/ipam"
|
|
BACKEND_DIR="$BASE_DIR/backend"
|
|
FRONTEND_DIR="$BASE_DIR/frontend"
|
|
|
|
# 端口配置
|
|
API_PORT=8008
|
|
FRONTEND_PORT=3000
|
|
|
|
# 检查 Docker 容器状态
|
|
check_docker_containers() {
|
|
echo "🔍 检查 Docker 容器..."
|
|
|
|
# 检查 MySQL
|
|
if [ "$(docker inspect -f '{{.State.Running}}' ipam-mysql 2>/dev/null)" != "true" ]; then
|
|
echo -e "${YELLOW}MySQL 容器未运行,正在启动...${NC}"
|
|
docker start ipam-mysql 2>/dev/null || {
|
|
echo -e "${YELLOW}创建 MySQL 容器...${NC}"
|
|
docker run -d --name ipam-mysql -p 3308:3306 \
|
|
-e MYSQL_ROOT_PASSWORD=*** \
|
|
-e MYSQL_DATABASE=ipam \
|
|
-e MYSQL_USER=ipam \
|
|
-e MYSQL_PASSWORD=*** \
|
|
mysql:8.0 --default-authentication-plugin=mysql_native_password
|
|
}
|
|
fi
|
|
echo -e "${GREEN}✅ MySQL 运行正常${NC}"
|
|
|
|
# 检查 Redis
|
|
if [ "$(docker inspect -f '{{.State.Running}}' ipam-redis 2>/dev/null)" != "true" ]; then
|
|
echo -e "${YELLOW}Redis 容器未运行,正在启动...${NC}"
|
|
docker start ipam-redis 2>/dev/null || {
|
|
echo -e "${YELLOW}创建 Redis 容器...${NC}"
|
|
docker run -d --name ipam-redis -p 6379:6379 redis:7-alpine
|
|
}
|
|
fi
|
|
echo -e "${GREEN}✅ Redis 运行正常${NC}"
|
|
echo ""
|
|
}
|
|
|
|
# 检查并杀死已占用的端口
|
|
kill_port() {
|
|
local port=$1
|
|
local pid=$(lsof -t -i:$port 2>/dev/null || netstat -tlnp 2>/dev/null | grep ":$port" | awk '{print $7}' | cut -d'/' -f1)
|
|
if [ -n "$pid" ]; then
|
|
echo -e "${YELLOW}端口 $port 被占用 (PID $pid),正在关闭...${NC}"
|
|
kill -9 $pid 2>/dev/null
|
|
sleep 2
|
|
fi
|
|
}
|
|
|
|
# 启动后端 API
|
|
start_backend() {
|
|
echo "🚀 启动后端 API 服务..."
|
|
|
|
# 检查虚拟环境
|
|
if [ ! -d "$BACKEND_DIR/venv" ]; then
|
|
echo -e "${YELLOW}创建 Python 虚拟环境...${NC}"
|
|
cd $BACKEND_DIR
|
|
python3 -m venv venv
|
|
fi
|
|
|
|
# 激活虚拟环境并启动
|
|
cd $BACKEND_DIR
|
|
source venv/bin/activate
|
|
|
|
# 检查端口并清理
|
|
kill_port $API_PORT
|
|
|
|
# 后台启动 uvicorn
|
|
nohup uvicorn app.main:app --host 0.0.0.0 --port $API_PORT > /tmp/ipam-backend.log 2>&1 &
|
|
BACKEND_PID=$!
|
|
|
|
# 等待服务启动
|
|
sleep 5
|
|
|
|
# 检查是否启动成功
|
|
if curl -s http://localhost:$API_PORT/health > /dev/null; then
|
|
echo -e "${GREEN}✅ 后端 API 启动成功 (端口 $API_PORT)${NC}"
|
|
echo " PID: $BACKEND_PID"
|
|
echo " 日志: /tmp/ipam-backend.log"
|
|
return 0
|
|
else
|
|
echo -e "${RED}❌ 后端 API 启动失败${NC}"
|
|
echo " 查看日志: tail -50 /tmp/ipam-backend.log"
|
|
return 1
|
|
fi
|
|
echo ""
|
|
}
|
|
|
|
# 启动 Celery Worker
|
|
start_celery() {
|
|
echo "🚀 启动 Celery Worker..."
|
|
|
|
cd $BACKEND_DIR
|
|
source venv/bin/activate
|
|
|
|
# 检查是否已有 celery 进程
|
|
pkill -f "celery.*app.tasks.celery_app" 2>/dev/null
|
|
sleep 1
|
|
|
|
# 后台启动 celery
|
|
nohup celery -A app.tasks.celery_app worker --loglevel=info --concurrency=4 > /tmp/ipam-celery.log 2>&1 &
|
|
CELERY_PID=$!
|
|
|
|
sleep 3
|
|
|
|
if ps -p $CELERY_PID > /dev/null; then
|
|
echo -e "${GREEN}✅ Celery Worker 启动成功${NC}"
|
|
echo " PID: $CELERY_PID"
|
|
echo " 日志: /tmp/ipam-celery.log"
|
|
return 0
|
|
else
|
|
echo -e "${RED}❌ Celery Worker 启动失败${NC}"
|
|
echo " 查看日志: tail -50 /tmp/ipam-celery.log"
|
|
return 1
|
|
fi
|
|
echo ""
|
|
}
|
|
|
|
# 启动前端
|
|
start_frontend() {
|
|
echo "🚀 启动前端服务..."
|
|
|
|
cd $FRONTEND_DIR
|
|
|
|
# 检查 node_modules
|
|
if [ ! -d "node_modules" ]; then
|
|
echo -e "${YELLOW}安装前端依赖...${NC}"
|
|
npm install
|
|
fi
|
|
|
|
# 检查端口并清理
|
|
kill_port $FRONTEND_PORT
|
|
|
|
# 后台启动前端
|
|
nohup npm run dev -- --host 0.0.0.0 --port $FRONTEND_PORT > /tmp/ipam-frontend.log 2>&1 &
|
|
FRONTEND_PID=$!
|
|
|
|
sleep 8
|
|
|
|
if curl -s http://localhost:$FRONTEND_PORT > /dev/null; then
|
|
echo -e "${GREEN}✅ 前端服务启动成功 (端口 $FRONTEND_PORT)${NC}"
|
|
echo " PID: $FRONTEND_PID"
|
|
echo " 日志: /tmp/ipam-frontend.log"
|
|
return 0
|
|
else
|
|
echo -e "${RED}❌ 前端服务启动失败${NC}"
|
|
echo " 查看日志: tail -50 /tmp/ipam-frontend.log"
|
|
return 1
|
|
fi
|
|
echo ""
|
|
}
|
|
|
|
# 显示服务状态
|
|
show_status() {
|
|
echo ""
|
|
echo "=========================================="
|
|
echo " 🎉 IPAM 系统启动完成!"
|
|
echo "=========================================="
|
|
echo ""
|
|
echo "📊 服务状态:"
|
|
echo " - MySQL: 127.0.0.1:3308 ✅"
|
|
echo " - Redis: 127.0.0.1:6379 ✅"
|
|
echo " - 后端 API: http://$(hostname -I | awk '{print $1}'):$API_PORT ✅"
|
|
echo " - Celery: 后台运行 ✅"
|
|
echo " - 前端界面: http://$(hostname -I | awk '{print $1}'):$FRONTEND_PORT ✅"
|
|
echo ""
|
|
echo "📖 访问地址:"
|
|
echo " - 管理界面: http://$(hostname -I | awk '{print $1}'):$FRONTEND_PORT"
|
|
echo " - API 文档: http://$(hostname -I | awk '{print $1}'):$API_PORT/docs"
|
|
echo ""
|
|
echo "🛑 停止服务命令:"
|
|
echo " pkill -f 'uvicorn|celery|vite'"
|
|
echo ""
|
|
}
|
|
|
|
# 主程序
|
|
main() {
|
|
# 检查是否是 root 用户
|
|
if [ "$EUID" -ne 0 ]; then
|
|
echo -e "${RED}请使用 root 权限运行此脚本${NC}"
|
|
exit 1
|
|
fi
|
|
|
|
# 检查 Docker 是否安装
|
|
if ! command -v docker &> /dev/null; then
|
|
echo -e "${RED}Docker 未安装,请先安装 Docker${NC}"
|
|
exit 1
|
|
fi
|
|
|
|
# 检查 Python
|
|
if ! command -v python3 &> /dev/null; then
|
|
echo -e "${RED}Python3 未安装${NC}"
|
|
exit 1
|
|
fi
|
|
|
|
# 检查 Node.js
|
|
if ! command -v node &> /dev/null; then
|
|
echo -e "${RED}Node.js 未安装${NC}"
|
|
exit 1
|
|
fi
|
|
|
|
echo ""
|
|
check_docker_containers
|
|
start_backend
|
|
start_celery
|
|
start_frontend
|
|
show_status
|
|
}
|
|
|
|
# 运行主程序
|
|
main
|