#!/bin/bash

# =============================================================================
# SCRIPT: setup-weekly-update-cron.sh
# PURPOSE: Create timezone-aware inline crontab for Sunday 2:00 AM local updates
# LAST UPDATED: June 29, 2025
# KEY ENHANCEMENT: Generates inline crontab entry with full command chain
# SERVICES: Local system maintenance with timezone awareness
# =============================================================================

set -e  # Exit on any error

# Colors for output
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
RED='\033[0;31m'
NC='\033[0m' # No Color

log_info() {
    echo -e "${BLUE}ℹ $1${NC}"
}

log_success() {
    echo -e "${GREEN}✔ $1${NC}"
}

log_warning() {
    echo -e "${YELLOW}⚠ $1${NC}"
}

log_error() {
    echo -e "${RED}❌ $1${NC}"
}

# Check if we can modify root's crontab
if ! sudo -n crontab -l >/dev/null 2>&1 && [[ $EUID -ne 0 ]]; then
   log_error "This script needs to modify root's crontab."
   if [[ -t 0 ]]; then
       # Running interactively
       log_error "Please run with sudo: sudo $0"
   else
       # Running via pipe (stdin is not a terminal)
       log_error "When running via pipe, use: wget -qO- URL | sudo bash"
       log_error "Or download first: wget URL && chmod +x script.sh && sudo ./script.sh"
   fi
   exit 1
fi

log_info "Setting up timezone-aware weekly update crontab..."

# =============================================================================
# TIMEZONE CALCULATION
# =============================================================================

# Get current timezone information
CURRENT_TZ=$(timedatectl show --property=Timezone --value)
log_info "Current timezone: $CURRENT_TZ"

# Target: Sunday 2:00 AM local time
TARGET_LOCAL_HOUR=2
TARGET_LOCAL_DAY=0  # Sunday

# Get current timezone offset (format: +HHMM or -HHMM)
OFFSET=$(date +%z)
OFFSET_HOURS=${OFFSET:1:2}
OFFSET_MINUTES=${OFFSET:3:2}
OFFSET_SIGN=${OFFSET:0:1}

log_info "Target local time: Sunday ${TARGET_LOCAL_HOUR}:00 AM"
log_info "Current timezone offset: $OFFSET"

# Calculate UTC hour using manual offset calculation
if [ "$OFFSET_SIGN" = "-" ]; then
    # Negative offset (behind UTC) - add offset to get UTC
    UTC_HOUR=$((TARGET_LOCAL_HOUR + OFFSET_HOURS))
    OFFSET_DIRECTION="behind"
else
    # Positive offset (ahead of UTC) - subtract offset to get UTC  
    UTC_HOUR=$((TARGET_LOCAL_HOUR - OFFSET_HOURS))
    OFFSET_DIRECTION="ahead of"
fi

# Handle hour overflow/underflow and day changes
UTC_DAY_NUM=$TARGET_LOCAL_DAY
if [ $UTC_HOUR -ge 24 ]; then
    UTC_HOUR=$((UTC_HOUR - 24))
    UTC_DAY_NUM=$(((UTC_DAY_NUM + 1) % 7))
elif [ $UTC_HOUR -lt 0 ]; then
    UTC_HOUR=$((UTC_HOUR + 24))
    UTC_DAY_NUM=$(((UTC_DAY_NUM + 6) % 7))  # Subtract 1 day (mod 7)
fi

log_info "Calculated UTC time: Day ${UTC_DAY_NUM} at ${UTC_HOUR}:00"
log_info "Timezone: ${OFFSET_HOURS} hours ${OFFSET_DIRECTION} UTC"

# Determine day name for display
case $UTC_DAY_NUM in
    0) UTC_DAY_NAME="Sunday" ;;
    1) UTC_DAY_NAME="Monday" ;;
    2) UTC_DAY_NAME="Tuesday" ;;
    3) UTC_DAY_NAME="Wednesday" ;;
    4) UTC_DAY_NAME="Thursday" ;;
    5) UTC_DAY_NAME="Friday" ;;
    6) UTC_DAY_NAME="Saturday" ;;
esac

if [ $UTC_DAY_NUM -ne 0 ]; then
    log_warning "Note: Due to timezone offset, local Sunday 2:00 AM occurs on $UTC_DAY_NAME in UTC"
fi

# =============================================================================
# CREATE THE CRONTAB ENTRY
# =============================================================================

# Build the inline command chain
CRON_COMMAND="/usr/bin/sudo /usr/bin/apt update && /usr/bin/sudo /usr/bin/apt upgrade -y && /usr/bin/sudo /usr/bin/apt autoremove -y && /usr/bin/sudo /usr/sbin/reboot"
CRON_LINE="0 ${UTC_HOUR} * * ${UTC_DAY_NUM} ${CRON_COMMAND}"

log_info "Creating inline crontab entry..."
echo
echo "Generated crontab entry:"
echo "$CRON_LINE"
echo

# Check if similar crontab entry already exists (check for apt update pattern)
if sudo crontab -l 2>/dev/null | grep -q "/usr/bin/apt update"; then
    log_warning "Existing apt update crontab entry found"
    log_info "Current crontab entries with apt:"
    sudo crontab -l 2>/dev/null | grep "apt" || echo "  (none found)"
    echo
    read -p "Remove existing apt-related entries and add new one? (y/N): " -n 1 -r
    echo
    if [[ $REPLY =~ ^[Yy]$ ]]; then
        # Remove existing apt entries
        sudo crontab -l 2>/dev/null | grep -v "/usr/bin/apt" | sudo crontab -
        log_info "Removed existing apt-related crontab entries"
    else
        log_warning "Keeping existing entries. You may want to manually review your crontab."
    fi
fi

# Add new crontab entry
(sudo crontab -l 2>/dev/null || true; echo "$CRON_LINE") | sudo crontab -

log_success "Crontab entry added successfully"

# =============================================================================
# VERIFICATION AND SUMMARY
# =============================================================================

echo
log_success "Weekly update cron job configured successfully!"
echo
echo "=== CONFIGURATION SUMMARY ==="
echo "Local Target Time: Sunday ${TARGET_LOCAL_HOUR}:00 AM ($CURRENT_TZ)"
echo "UTC Execution Time: $UTC_DAY_NAME ${UTC_HOUR}:00 UTC"
echo "Crontab Entry: $CRON_LINE"
echo
echo "=== WHAT THIS DOES ==="
echo "• Updates package lists (apt update)"
echo "• Installs security and package updates (apt upgrade)"
echo "• Removes unused packages (apt autoremove)"
echo "• Immediately reboots after updates"
echo
echo "=== WHAT THIS DOES NOT DO ==="
echo "• No apt full-upgrade (avoids major release upgrades like 24.04 → 26.04)"
echo "• No logging (output goes to system mail or /dev/null)"
echo "• No conditional reboot checking"
echo
echo "=== VERIFICATION COMMANDS ==="
echo "View crontab: sudo crontab -l"
echo "Test individual commands manually:"
echo "  sudo /usr/bin/apt update"
echo "  sudo /usr/bin/apt upgrade -y"
echo "  sudo /usr/bin/apt autoremove -y"
echo "Next execution: $(date -d "next sunday ${TARGET_LOCAL_HOUR}:00" '+%Y-%m-%d %H:%M %Z')"
echo

# Show current crontab for verification
echo "=== CURRENT ROOT CRONTAB ==="
sudo crontab -l 2>/dev/null || echo "No crontab entries found"
echo

log_info "Setup complete!"