#!/bin/bash set -e PROJECT_DIR="$(cd "$(dirname "$0")" && pwd)" BACKEND_DIR="$PROJECT_DIR/backend" FRONTEND_DIR="$PROJECT_DIR/frontend" PID_FILE="$PROJECT_DIR/.pids" # Colors GREEN='\033[0;32m' YELLOW='\033[1;33m' RED='\033[0;31m' NC='\033[0m' BACKEND_PORT=8000 FRONTEND_PORT=5173 stop_services() { echo -e "${YELLOW}Stopping services...${NC}" local stopped=0 # Kill by PID file first if [ -f "$PID_FILE" ]; then while read -r pid; do if kill -0 "$pid" 2>/dev/null; then kill "$pid" 2>/dev/null && stopped=1 echo -e " Killed process $pid (from PID file)" fi done < "$PID_FILE" rm -f "$PID_FILE" fi # Kill anything still on our ports for port in $BACKEND_PORT $FRONTEND_PORT; do local pids pids=$(lsof -ti :"$port" 2>/dev/null || true) if [ -n "$pids" ]; then for pid in $pids; do kill "$pid" 2>/dev/null && stopped=1 echo -e " Killed process $pid on port $port" done fi done # Wait a moment for ports to free up if [ "$stopped" -eq 1 ]; then sleep 1 fi # Verify ports are free local still_busy=0 for port in $BACKEND_PORT $FRONTEND_PORT; do if lsof -ti :"$port" >/dev/null 2>&1; then echo -e "${RED} Port $port still in use! Sending SIGKILL...${NC}" kill -9 $(lsof -ti :"$port") 2>/dev/null || true still_busy=1 fi done [ "$still_busy" -eq 1 ] && sleep 1 echo -e "${GREEN}Services stopped.${NC}" } start_services() { # Check if ports are busy for port in $BACKEND_PORT $FRONTEND_PORT; do if lsof -ti :"$port" >/dev/null 2>&1; then echo -e "${RED}Port $port is already in use!${NC}" echo -e "${YELLOW}Use '$0 restart' to restart or '$0 stop' to stop first.${NC}" exit 1 fi done # Backend setup echo -e "${GREEN}[Backend] Setting up...${NC}" if [ ! -d "$BACKEND_DIR/venv" ]; then python3 -m venv "$BACKEND_DIR/venv" source "$BACKEND_DIR/venv/bin/activate" pip install -q -r "$BACKEND_DIR/requirements.txt" else source "$BACKEND_DIR/venv/bin/activate" fi # Seed DB if empty if [ ! -f "$BACKEND_DIR/space_booking.db" ]; then echo -e "${GREEN}[Backend] Seeding database...${NC}" cd "$BACKEND_DIR" && python seed_db.py fi echo -e "${GREEN}[Backend] Starting on :${BACKEND_PORT}${NC}" cd "$BACKEND_DIR" && uvicorn app.main:app --reload --host 0.0.0.0 --port $BACKEND_PORT & BACKEND_PID=$! # Frontend setup echo -e "${GREEN}[Frontend] Setting up...${NC}" if [ ! -d "$FRONTEND_DIR/node_modules" ]; then cd "$FRONTEND_DIR" && npm install --silent fi echo -e "${GREEN}[Frontend] Starting on :${FRONTEND_PORT}${NC}" cd "$FRONTEND_DIR" && npm run dev -- --host 0.0.0.0 & FRONTEND_PID=$! # Save PIDs echo "$BACKEND_PID" > "$PID_FILE" echo "$FRONTEND_PID" >> "$PID_FILE" echo -e "\n${GREEN}=== Space Booking Running ===${NC}" echo -e " Backend: http://localhost:${BACKEND_PORT}" echo -e " Frontend: http://localhost:${FRONTEND_PORT}" echo -e " API Docs: http://localhost:${BACKEND_PORT}/docs" echo -e "${YELLOW} Press Ctrl+C to stop${NC}\n" trap 'stop_services; exit 0' EXIT INT TERM wait } # --- Main --- case "${1:-start}" in start) start_services ;; stop) stop_services ;; restart) stop_services echo "" start_services ;; *) echo "Usage: $0 {start|stop|restart}" exit 1 ;; esac