#!/bin/bash set -e # --- Configuration & Colors --- RED='\e[31m' GREEN='\e[32m' YELLOW='\e[33m' BLUE='\e[34m' NC='\e[0m' if [[ $EUID -ne 0 ]]; then echo -e "${RED}Error: This script must be run as root.${NC}" exit 1 fi echo -e "${BLUE}=== Debian 12 to 13 (Trixie) Upgrade Suite ===${NC}" # --- 1. HEALTH CHECKS --- echo -e "${YELLOW}[1/6] Running system health checks...${NC}" if dpkg --get-selections | grep -q 'hold'; then echo -e "${RED}Error: You have packages on hold. Unhold them before upgrading.${NC}" exit 1 fi apt update && apt upgrade -y apt autoremove -y # --- 2. UPDATE SOURCES (Standard Format) --- echo -e "${YELLOW}[2/6] Updating APT sources to Trixie...${NC}" cp /etc/apt/sources.list /etc/apt/sources.list.bak # Swap codenames sed -i 's/bookworm/trixie/g' /etc/apt/sources.list find /etc/apt/sources.list.d/ -type f -name "*.list" -exec sed -i 's/bookworm/trixie/g' {} + # Enforce non-free-firmware sed -i '/^deb .* main/ { /non-free-firmware/ ! s/$/ non-free-firmware/ }' /etc/apt/sources.list # --- 3. ATTEMPT MODERNIZATION (Skip on failure) --- echo -e "${YELLOW}[3/6] Attempting to modernize sources...${NC}" # Try to update apt binary first to unlock the command apt update || true apt install -y apt python3-debian || true if apt modernize-sources --assume-yes 2>/dev/null; then echo -e "${GREEN}Successfully modernized sources to DEB822 format.${NC}" [ -f /etc/apt/sources.list ] && mv /etc/apt/sources.list /etc/apt/sources.list.modernized else echo -e "${RED}Warning: 'apt modernize-sources' not supported yet. Continuing with standard format...${NC}" fi # --- 4. TAILSCALE SPECIAL HANDLING --- echo -e "${YELLOW}[4/6] Finalizing Tailscale configuration...${NC}" # Refresh Keyring mkdir -p /usr/share/keyrings curl -fsSL https://pkgs.tailscale.com/stable/debian/trixie.noarmor.gpg -o /usr/share/keyrings/tailscale-archive-keyring.gpg || \ curl -fsSL https://pkgs.tailscale.com/stable/debian/bookworm.noarmor.gpg -o /usr/share/keyrings/tailscale-archive-keyring.gpg # Remove legacy list file to prevent duplicates rm -f /etc/apt/sources.list.d/tailscale.list # Create/Overwrite modern DEB822 file cat < /etc/apt/sources.list.d/tailscale.sources Types: deb URIs: https://pkgs.tailscale.com/stable/debian/ Suites: trixie Components: main Signed-By: /usr/share/keyrings/tailscale-archive-keyring.gpg EOF # --- 5. MINIMAL UPGRADE --- echo -e "${BLUE}[5/6] Performing Minimal Upgrade...${NC}" apt update DEBIAN_FRONTEND=noninteractive apt upgrade -y --without-new-pkgs -o Dpkg::Options::="--force-confold" # --- 6. FULL SYSTEM UPGRADE --- echo -e "${BLUE}[6/6] Performing Full System Upgrade...${NC}" DEBIAN_FRONTEND=noninteractive apt full-upgrade -y -o Dpkg::Options::="--force-confold" # Final Cleanup apt autoremove -y && apt clean echo -e "${GREEN}Upgrade complete!${NC}" read -p "Reboot now? (y/N) " answer if [[ "$answer" =~ ^[Yy]$ ]]; then reboot fi