#!/bin/bash # ParentFlow Production Stop Script # Stops all production services gracefully set -e # Color codes RED='\033[0;31m' GREEN='\033[0;32m' YELLOW='\033[1;33m' BLUE='\033[0;34m' CYAN='\033[0;36m' NC='\033[0m' log() { echo -e "${BLUE}[$(date +'%Y-%m-%d %H:%M:%S')]${NC} $1" } error() { echo -e "${RED}[ERROR]${NC} $1" >&2 } success() { echo -e "${GREEN}✓${NC} $1" } warning() { echo -e "${YELLOW}⚠${NC} $1" } # Header echo "" echo "==========================================" echo " Stopping ParentFlow Production " echo "==========================================" echo "" # Step 1: Stop PM2 processes log "${CYAN}Step 1: Stopping PM2 services...${NC}" if command -v pm2 &> /dev/null; then # Show current status echo "Current PM2 processes:" pm2 list # Stop all PM2 processes pm2 stop all 2>/dev/null || warning "No PM2 processes were running" # Delete all PM2 processes pm2 delete all 2>/dev/null || warning "No PM2 processes to delete" # Kill PM2 daemon pm2 kill success "PM2 services stopped" else warning "PM2 not found" fi # Step 2: Stop Docker services log "${CYAN}Step 2: Stopping Docker services...${NC}" DEPLOY_DIR="/root/parentflow-production" # Try to find docker-compose file if [ -f "$DEPLOY_DIR/docker-compose.production.yml" ]; then cd "$DEPLOY_DIR" if docker compose version &> /dev/null; then docker compose -f docker-compose.production.yml down else docker-compose -f docker-compose.production.yml down fi success "Docker services stopped" elif [ -f "./docker-compose.production.yml" ]; then if docker compose version &> /dev/null; then docker compose -f docker-compose.production.yml down else docker-compose -f docker-compose.production.yml down fi success "Docker services stopped" else warning "Docker compose file not found, skipping..." fi # Step 3: Kill any remaining Node processes on production ports log "${CYAN}Step 3: Cleaning up remaining processes...${NC}" kill_port() { local port=$1 local name=$2 if lsof -i:$port > /dev/null 2>&1; then log "Stopping $name on port $port..." lsof -ti:$port | xargs -r kill -9 success "$name stopped" else echo " $name not running on port $port" fi } kill_port 3020 "Backend API" kill_port 3030 "Frontend" kill_port 3335 "Admin Dashboard" # Step 4: Clean up temporary files log "${CYAN}Step 4: Cleaning up temporary files...${NC}" rm -rf /tmp/pm2-* 2>/dev/null || true rm -rf /tmp/next-* 2>/dev/null || true success "Temporary files cleaned" # Step 5: Verify all services are stopped log "${CYAN}Step 5: Verifying all services are stopped...${NC}" check_port() { local port=$1 local name=$2 if lsof -i:$port > /dev/null 2>&1; then warning "$name still running on port $port" return 1 else success "$name stopped (port $port free)" return 0 fi } ALL_STOPPED=true check_port 3020 "Backend API" || ALL_STOPPED=false check_port 3030 "Frontend" || ALL_STOPPED=false check_port 3335 "Admin Dashboard" || ALL_STOPPED=false check_port 6379 "Redis" || true # Redis might be used by other services check_port 27017 "MongoDB" || true # MongoDB might be used by other services check_port 9000 "MinIO" || true # MinIO might be used by other services # Final summary echo "" echo "==========================================" if [ "$ALL_STOPPED" = true ]; then echo -e "${GREEN} All Services Stopped Successfully! ${NC}" else echo -e "${YELLOW} Services Stopped (Check Warnings) ${NC}" fi echo "==========================================" echo "" echo "To restart services, run:" echo " ./start-production.sh" echo "" log "Services stopped at $(date)"