#!/usr/bin/env bash # # ThrillWiki Systemd Service Configuration Fix # Addresses SSH authentication issues and systemd service installation problems # set -e # Script configuration SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" PROJECT_DIR="$(cd "$SCRIPT_DIR/../.." && pwd)" # Colors for output RED='\033[0;31m' GREEN='\033[0;32m' YELLOW='\033[1;33m' BLUE='\033[0;34m' CYAN='\033[0;36m' BOLD='\033[1m' NC='\033[0m' # Configuration REMOTE_HOST="${1:-192.168.20.65}" REMOTE_USER="${2:-thrillwiki}" REMOTE_PORT="${3:-22}" SSH_KEY="${4:-$HOME/.ssh/thrillwiki_vm}" REMOTE_PATH="/home/$REMOTE_USER/thrillwiki" # Improved SSH options with key authentication SSH_OPTS="-i $SSH_KEY -o IdentitiesOnly=yes -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null -o ConnectTimeout=30 -o PasswordAuthentication=no" echo -e "${BOLD}${CYAN}🔧 ThrillWiki Systemd Service Fix${NC}" echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━" echo "" echo "Target: ${REMOTE_USER}@${REMOTE_HOST}:${REMOTE_PORT}" echo "SSH Key: $SSH_KEY" echo "Remote Path: $REMOTE_PATH" echo "" # Function to run remote commands with proper SSH key authentication run_remote() { local cmd="$1" local description="$2" local use_sudo="${3:-false}" echo -e "${YELLOW}🔧 ${description}${NC}" if [ "$use_sudo" = "true" ]; then # Use sudo with cached credentials (will prompt once if needed) ssh $SSH_OPTS -p $REMOTE_PORT -t $REMOTE_USER@$REMOTE_HOST "sudo $cmd" else ssh $SSH_OPTS -p $REMOTE_PORT $REMOTE_USER@$REMOTE_HOST "$cmd" fi if [ $? -eq 0 ]; then echo -e "${GREEN}✅ Success: ${description}${NC}" return 0 else echo -e "${RED}❌ Failed: ${description}${NC}" return 1 fi } # Function to initialize sudo session (ask for password once) init_sudo_session() { echo -e "${YELLOW}🔐 Initializing sudo session (you may be prompted for password)${NC}" if ssh $SSH_OPTS -p $REMOTE_PORT -t $REMOTE_USER@$REMOTE_HOST "sudo -v"; then echo -e "${GREEN}✅ Sudo session initialized${NC}" return 0 else echo -e "${RED}❌ Failed to initialize sudo session${NC}" return 1 fi } echo "=== Step 1: SSH Authentication Test ===" echo "" # Test SSH connectivity if ! run_remote "echo 'SSH connection test successful'" "Testing SSH connection"; then echo -e "${RED}❌ SSH connection failed. Please check:${NC}" echo "1. SSH key exists and has correct permissions: $SSH_KEY" echo "2. SSH key is added to remote host: $REMOTE_USER@$REMOTE_HOST" echo "3. Remote host is accessible: $REMOTE_HOST:$REMOTE_PORT" exit 1 fi # Initialize sudo session once (ask for password here) if ! init_sudo_session; then echo -e "${RED}❌ Cannot initialize sudo session. Systemd operations require sudo access.${NC}" exit 1 fi echo "" echo "=== Step 2: Create Missing Scripts ===" echo "" # Create smart-deploy.sh script echo -e "${YELLOW}🔧 Creating smart-deploy.sh script${NC}" cat > /tmp/smart-deploy.sh << 'EOF' #!/bin/bash # # ThrillWiki Smart Deployment Script # Automated repository synchronization and Django server management # set -e PROJECT_DIR="/home/thrillwiki/thrillwiki" LOG_FILE="$PROJECT_DIR/logs/smart-deploy.log" LOCK_FILE="/tmp/smart-deploy.lock" # Logging function smart_log() { local level="$1" local message="$2" local timestamp="$(date '+%Y-%m-%d %H:%M:%S')" echo "[$timestamp] [$level] $message" | tee -a "$LOG_FILE" } # Create lock to prevent multiple instances if [ -f "$LOCK_FILE" ]; then smart_log "WARNING" "Smart deploy already running (lock file exists)" exit 0 fi echo $$ > "$LOCK_FILE" trap 'rm -f "$LOCK_FILE"' EXIT smart_log "INFO" "Starting smart deployment cycle" cd "$PROJECT_DIR" # Pull latest changes smart_log "INFO" "Pulling latest repository changes" if git pull origin main; then smart_log "SUCCESS" "Repository updated successfully" else smart_log "ERROR" "Failed to pull repository changes" exit 1 fi # Check if dependencies need updating if [ -f "pyproject.toml" ]; then smart_log "INFO" "Updating dependencies with UV" if uv sync; then smart_log "SUCCESS" "Dependencies updated" else smart_log "WARNING" "Dependency update had issues" fi fi # Run Django migrations smart_log "INFO" "Running Django migrations" if uv run manage.py migrate --no-input; then smart_log "SUCCESS" "Migrations completed" else smart_log "WARNING" "Migration had issues" fi # Collect static files smart_log "INFO" "Collecting static files" if uv run manage.py collectstatic --no-input; then smart_log "SUCCESS" "Static files collected" else smart_log "WARNING" "Static file collection had issues" fi smart_log "SUCCESS" "Smart deployment cycle completed" EOF # Upload smart-deploy.sh if scp $SSH_OPTS -P $REMOTE_PORT /tmp/smart-deploy.sh $REMOTE_USER@$REMOTE_HOST:$REMOTE_PATH/scripts/smart-deploy.sh; then echo -e "${GREEN}✅ smart-deploy.sh uploaded successfully${NC}" else echo -e "${RED}❌ Failed to upload smart-deploy.sh${NC}" exit 1 fi # Make smart-deploy.sh executable run_remote "chmod +x $REMOTE_PATH/scripts/smart-deploy.sh" "Making smart-deploy.sh executable" # Create logs directory run_remote "mkdir -p $REMOTE_PATH/logs" "Creating logs directory" echo "" echo "=== Step 3: Deploy Systemd Service Files ===" echo "" # Upload systemd service files echo -e "${YELLOW}🔧 Uploading systemd service files${NC}" # Upload thrillwiki-deployment.service if scp $SSH_OPTS -P $REMOTE_PORT $PROJECT_DIR/scripts/systemd/thrillwiki-deployment.service $REMOTE_USER@$REMOTE_HOST:/tmp/; then echo -e "${GREEN}✅ thrillwiki-deployment.service uploaded${NC}" else echo -e "${RED}❌ Failed to upload thrillwiki-deployment.service${NC}" exit 1 fi # Upload thrillwiki-smart-deploy.service if scp $SSH_OPTS -P $REMOTE_PORT $PROJECT_DIR/scripts/systemd/thrillwiki-smart-deploy.service $REMOTE_USER@$REMOTE_HOST:/tmp/; then echo -e "${GREEN}✅ thrillwiki-smart-deploy.service uploaded${NC}" else echo -e "${RED}❌ Failed to upload thrillwiki-smart-deploy.service${NC}" exit 1 fi # Upload thrillwiki-smart-deploy.timer if scp $SSH_OPTS -P $REMOTE_PORT $PROJECT_DIR/scripts/systemd/thrillwiki-smart-deploy.timer $REMOTE_USER@$REMOTE_HOST:/tmp/; then echo -e "${GREEN}✅ thrillwiki-smart-deploy.timer uploaded${NC}" else echo -e "${RED}❌ Failed to upload thrillwiki-smart-deploy.timer${NC}" exit 1 fi # Upload environment file if scp $SSH_OPTS -P $REMOTE_PORT $PROJECT_DIR/scripts/systemd/thrillwiki-deployment***REMOVED*** $REMOTE_USER@$REMOTE_HOST:$REMOTE_PATH/scripts/systemd/; then echo -e "${GREEN}✅ thrillwiki-deployment***REMOVED*** uploaded${NC}" else echo -e "${RED}❌ Failed to upload thrillwiki-deployment***REMOVED***${NC}" exit 1 fi echo "" echo "=== Step 4: Install Systemd Services ===" echo "" # Copy service files to systemd directory run_remote "cp /tmp/thrillwiki-deployment.service /etc/systemd/system/" "Installing thrillwiki-deployment.service" true run_remote "cp /tmp/thrillwiki-smart-deploy.service /etc/systemd/system/" "Installing thrillwiki-smart-deploy.service" true run_remote "cp /tmp/thrillwiki-smart-deploy.timer /etc/systemd/system/" "Installing thrillwiki-smart-deploy.timer" true # Set proper permissions run_remote "chmod 644 /etc/systemd/system/thrillwiki-*.service /etc/systemd/system/thrillwiki-*.timer" "Setting service file permissions" true # Set environment file permissions run_remote "chmod 600 $REMOTE_PATH/scripts/systemd/thrillwiki-deployment***REMOVED***" "Setting environment file permissions" run_remote "chown $REMOTE_USER:$REMOTE_USER $REMOTE_PATH/scripts/systemd/thrillwiki-deployment***REMOVED***" "Setting environment file ownership" echo "" echo "=== Step 5: Enable and Start Services ===" echo "" # Reload systemd daemon run_remote "systemctl daemon-reload" "Reloading systemd daemon" true # Enable services run_remote "systemctl enable thrillwiki-deployment.service" "Enabling thrillwiki-deployment.service" true run_remote "systemctl enable thrillwiki-smart-deploy.timer" "Enabling thrillwiki-smart-deploy.timer" true # Start services run_remote "systemctl start thrillwiki-deployment.service" "Starting thrillwiki-deployment.service" true run_remote "systemctl start thrillwiki-smart-deploy.timer" "Starting thrillwiki-smart-deploy.timer" true echo "" echo "=== Step 6: Validate Service Operation ===" echo "" # Check service status echo -e "${YELLOW}🔧 Checking service status${NC}" if run_remote "systemctl is-active thrillwiki-deployment.service" "Checking thrillwiki-deployment.service status" true; then echo -e "${GREEN}✅ thrillwiki-deployment.service is active${NC}" else echo -e "${RED}❌ thrillwiki-deployment.service is not active${NC}" run_remote "systemctl status thrillwiki-deployment.service" "Getting service status details" true fi if run_remote "systemctl is-active thrillwiki-smart-deploy.timer" "Checking thrillwiki-smart-deploy.timer status" true; then echo -e "${GREEN}✅ thrillwiki-smart-deploy.timer is active${NC}" else echo -e "${RED}❌ thrillwiki-smart-deploy.timer is not active${NC}" run_remote "systemctl status thrillwiki-smart-deploy.timer" "Getting timer status details" true fi # Test smart-deploy script echo -e "${YELLOW}🔧 Testing smart-deploy script${NC}" if run_remote "$REMOTE_PATH/scripts/smart-deploy.sh" "Testing smart-deploy script execution"; then echo -e "${GREEN}✅ smart-deploy script executed successfully${NC}" else echo -e "${RED}❌ smart-deploy script execution failed${NC}" fi echo "" echo -e "${BOLD}${GREEN}🎉 Systemd Service Fix Completed!${NC}" echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━" echo "" echo -e "${CYAN}📋 Service Management Commands:${NC}" echo "" echo "Monitor services:" echo " ssh -i $SSH_KEY $REMOTE_USER@$REMOTE_HOST 'sudo systemctl status thrillwiki-deployment.service'" echo " ssh -i $SSH_KEY $REMOTE_USER@$REMOTE_HOST 'sudo systemctl status thrillwiki-smart-deploy.timer'" echo "" echo "View logs:" echo " ssh -i $SSH_KEY $REMOTE_USER@$REMOTE_HOST 'sudo journalctl -u thrillwiki-deployment -f'" echo " ssh -i $SSH_KEY $REMOTE_USER@$REMOTE_HOST 'sudo journalctl -u thrillwiki-smart-deploy -f'" echo " ssh -i $SSH_KEY $REMOTE_USER@$REMOTE_HOST 'tail -f $REMOTE_PATH/logs/smart-deploy.log'" echo "" echo "Control services:" echo " ssh -i $SSH_KEY $REMOTE_USER@$REMOTE_HOST 'sudo systemctl restart thrillwiki-deployment.service'" echo " ssh -i $SSH_KEY $REMOTE_USER@$REMOTE_HOST 'sudo systemctl restart thrillwiki-smart-deploy.timer'" echo "" # Cleanup temp files rm -f /tmp/smart-deploy.sh echo -e "${GREEN}✅ All systemd service issues have been resolved!${NC}"