mysql全屏终端全量、部分备份、恢复脚本

思路:

备份前会自动校验是否有需要清理的文件


两种使用方式:

./mysql_backup.sh 进入终端交互模式

./mysql_backup.sh 参数 ,案例:./mysql_backup.sh 1 ,执行全量备份


后台运行,查看日志案例:

bash 复制代码
# 后台运行全量备份,日志输出到文件
nohup ./mysql_backup.sh 1 > mysql_backup.log 2>&1 &





bash 复制代码
touch mysql_backup.sh && chmod +x mysql_backup.sh
bash 复制代码
#!/bin/bash

# MySQL备份恢复脚本
# 支持全量备份、部分库备份、备份恢复、自动清理
# Author: System Administrator
# Version: 1.0

# ===============================================
# 配置参数 - 请根据实际环境修改
# ===============================================

# MySQL连接配置
MYSQL_USER="root"           # MySQL用户名
MYSQL_PASS="cnmsb123"           # MySQL密码
MYSQL_HOST="localhost"      # MySQL主机地址,默认本机
MYSQL_PORT="3306"           # MySQL端口,默认3306

# 备份配置
BACKUP_DIR="/opt"           # 备份文件存储目录
RETENTION_DAYS=7            # 备份文件保留天数,超过此天数的备份将被自动清理

# 部分备份排除数据库配置
# 在进行部分备份时,以下数据库将被排除(不进行备份)
# 可以根据需要修改此列表,多个数据库用逗号分隔,例如:a,b,c      #代表排除a,b,c再备份
EXCLUDE_DATABASES=""

# 备份选项配置
MYSQLDUMP_OPTIONS="--single-transaction --routines --triggers --set-gtid-purged=OFF"  # mysqldump额外选项

# 颜色定义
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
PURPLE='\033[0;35m'
CYAN='\033[0;36m'
WHITE='\033[1;37m'
NC='\033[0m' # No Color

# 动画字符
SPINNER='|/-\'

# 打印带颜色的文本
print_color() {
    local color=$1
    local text=$2
    echo -e "${color}${text}${NC}"
}

# 清屏并移动光标到顶部
clear_screen() {
    clear
    printf "\033[H"
}

# 获取终端尺寸
get_terminal_size() {
    TERM_COLS=$(tput cols 2>/dev/null || echo 80)
    TERM_ROWS=$(tput lines 2>/dev/null || echo 24)
}

# 居中显示文本
center_text() {
    local text="$1"
    local color="$2"
    local padding=$(( (TERM_COLS - ${#text}) / 2 ))
    printf "%*s" $padding ""
    print_color "$color" "$text"
}

# 绘制分隔线
draw_line() {
    local char="${1:-═}"
    local color="${2:-$CYAN}"
    printf "${color}"
    for ((i=1; i<=TERM_COLS; i++)); do
        printf "$char"
    done
    printf "${NC}\n"
}

# 绘制边框
draw_border() {
    local title="$1"
    draw_line "═" "$CYAN"
    echo ""
    center_text "$title" "$WHITE"
    echo ""
    draw_line "═" "$CYAN"
}

# 全屏标题
print_title() {
    clear_screen
    get_terminal_size
    
    echo ""
    draw_border "MySQL 备份恢复管理工具 v1.0"
    echo ""
    
    # 显示系统信息
    center_text "🖥️  系统: $(uname -s) $(uname -r)" "$CYAN"
    center_text "📅 时间: $(date '+%Y-%m-%d %H:%M:%S')" "$CYAN"
    center_text "👤 用户: $(whoami)@$(hostname)" "$CYAN"
    echo ""
    draw_line "─" "$BLUE"
}

# 高级进度条动画
show_progress() {
    local message=$1
    local process_pid=$2
    local spinner_chars="⠋⠙⠹⠸⠼⠴⠦⠧⠇⠏"
    local delay=0.1
    local spin_i=0
    
    echo -n -e "${YELLOW}${message}${NC} "
    
    # 如果提供了进程PID,监控进程状态
    if [ -n "$process_pid" ]; then
        while kill -0 $process_pid 2>/dev/null; do
            printf "\b${CYAN}%s${NC}" "${spinner_chars:spin_i++%${#spinner_chars}:1}"
            sleep $delay
        done
    else
        # 简单的固定时间动画
        for i in {1..30}; do
            printf "\b${CYAN}%s${NC}" "${spinner_chars:spin_i++%${#spinner_chars}:1}"
            sleep $delay
        done
    fi
    
    echo -e "\b${GREEN}✓${NC}"
}

# 计时器函数
start_timer() {
    START_TIME=$(date +%s)
}

end_timer() {
    END_TIME=$(date +%s)
    DURATION=$((END_TIME - START_TIME))
    
    local hours=$((DURATION / 3600))
    local minutes=$(((DURATION % 3600) / 60))
    local seconds=$((DURATION % 60))
    
    if [ $hours -gt 0 ]; then
        echo "${hours}小时${minutes}分${seconds}秒"
    elif [ $minutes -gt 0 ]; then
        echo "${minutes}分${seconds}秒"
    else
        echo "${seconds}秒"
    fi
}

# 检查MySQL连接
check_mysql_connection() {
    print_color $BLUE "🔍 检查MySQL连接状态..."
    
    if mysql -h"$MYSQL_HOST" -P"$MYSQL_PORT" -u"$MYSQL_USER" -p"$MYSQL_PASS" -e "SELECT 1;" >/dev/null 2>&1; then
        print_color $GREEN "✅ MySQL连接成功"
        print_color $CYAN "   连接信息: ${MYSQL_USER}@${MYSQL_HOST}:${MYSQL_PORT}"
        return 0
    else
        print_color $RED "❌ MySQL连接失败,请检查连接配置"
        print_color $YELLOW "   主机: ${MYSQL_HOST}:${MYSQL_PORT}"
        print_color $YELLOW "   用户: ${MYSQL_USER}"
        exit 1
    fi
}

# 创建备份目录
create_backup_dir() {
    if [ ! -d "$BACKUP_DIR" ]; then
        print_color $YELLOW "📁 创建备份目录: $BACKUP_DIR"
        mkdir -p "$BACKUP_DIR"
    fi
}

# 清理过期备份
cleanup_old_backups() {
    print_color $BLUE "🧹 清理 ${RETENTION_DAYS} 天前的备份文件..."
    
    local deleted_count=0
    while IFS= read -r -d '' file; do
        rm -f "$file"
        deleted_count=$((deleted_count + 1))
        print_color $YELLOW "  删除: $(basename "$file")"
    done < <(find "$BACKUP_DIR" -name "*.sql" -type f -mtime +$RETENTION_DAYS -print0 2>/dev/null)
    
    # 清理过期的gz文件
    while IFS= read -r -d '' file; do
        rm -f "$file"
        deleted_count=$((deleted_count + 1))
        print_color $YELLOW "  删除: $(basename "$file")"
    done < <(find "$BACKUP_DIR" -name "*.gz" -type f -mtime +$RETENTION_DAYS -print0 2>/dev/null)
    
    if [ $deleted_count -eq 0 ]; then
        print_color $GREEN "✅ 没有需要清理的过期备份文件"
    else
        print_color $GREEN "✅ 已清理 ${deleted_count} 个过期备份文件"
    fi
}

# 压缩备份文件
compress_backup() {
    local sql_file=$1
    local gz_file="${sql_file}.gz"
    
    print_color $BLUE "📦 压缩备份文件..."
    
    if command -v gzip >/dev/null 2>&1; then
        if gzip "$sql_file"; then
            local size=$(du -h "$gz_file" | cut -f1)
            print_color $GREEN "✅ 压缩完成!"
            print_color $GREEN "   压缩文件: $(basename "$gz_file")"
            print_color $GREEN "   文件大小: ${size}"
            echo "$gz_file"
        else
            print_color $RED "❌ 压缩失败"
            return 1
        fi
    else
        print_color $YELLOW "⚠️  系统未安装gzip命令,跳过压缩"
        echo "$sql_file"
    fi
}

# 获取所有数据库列表(排除系统数据库)
get_all_databases() {
    mysql -h"$MYSQL_HOST" -P"$MYSQL_PORT" -u"$MYSQL_USER" -p"$MYSQL_PASS" -e "SHOW DATABASES;" 2>/dev/null | grep -Ev "^(Database|information_schema|performance_schema|mysql|sys)$"
}

# 全量备份
full_backup() {
    # 备份前先执行清理
    print_color $BLUE "🧹 备份前清理过期文件..."
    cleanup_old_backups
    
    local timestamp=$(date +"%Y%m%d_%H%M%S")
    local backup_file="${BACKUP_DIR}/full_backup_${timestamp}.sql"
    
    print_color $BLUE "🚀 开始全量备份..."
    print_color $CYAN "   备份文件: $(basename "$backup_file")"
    
    # 开始计时
    start_timer
    
    # 后台执行备份命令
    mysqldump -h"$MYSQL_HOST" -P"$MYSQL_PORT" -u"$MYSQL_USER" -p"$MYSQL_PASS" --all-databases $MYSQLDUMP_OPTIONS > "$backup_file" 2>/dev/null &
    local backup_pid=$!
    
    # 显示进度条
    show_progress "正在执行全量备份" $backup_pid
    
    # 等待备份完成并检查结果
    wait $backup_pid
    local backup_result=$?
    
    # 结束计时
    local elapsed_time=$(end_timer)
    
    if [ $backup_result -eq 0 ] && [ -s "$backup_file" ]; then
        print_color $GREEN "✅ 全量备份完成!耗时: ${elapsed_time}"
        
        # 压缩备份文件
        local final_file=$(compress_backup "$backup_file")
        if [ $? -eq 0 ]; then
            print_color $GREEN "   保存路径: ${final_file}"
        else
            print_color $GREEN "   保存路径: ${backup_file}"
        fi
    else
        print_color $RED "❌ 全量备份失败,耗时: ${elapsed_time}"
        rm -f "$backup_file"
        return 1
    fi
}

# 部分库备份(排除预设的数据库)
partial_backup() {
    # 检查是否配置了排除数据库
    if [ -z "$EXCLUDE_DATABASES" ]; then
        print_color $RED "❌ 未配置排除数据库列表"
        print_color $YELLOW "   请在脚本顶部的 EXCLUDE_DATABASES 变量中配置要排除的数据库"
        print_color $YELLOW "   示例: EXCLUDE_DATABASES=\"test_db,log_db,temp_db\""
        return 1
    fi
    
    print_color $CYAN "📋 配置的排除数据库: $EXCLUDE_DATABASES"
    
    # 将逗号分隔的字符串转换为数组
    IFS=',' read -ra exclude_array <<< "$EXCLUDE_DATABASES"
    
    # 获取所有数据库并排除指定的
    local all_dbs=$(get_all_databases)
    local backup_dbs=""
    
    if [ -z "$all_dbs" ]; then
        print_color $RED "❌ 未找到任何用户数据库"
        return 1
    fi
    
    print_color $BLUE "📊 分析数据库列表..."
    print_color $CYAN "   发现用户数据库: $(echo $all_dbs | tr '\n' ' ')"
    
    # 处理排除逻辑
    local excluded_dbs=""
    for db in $all_dbs; do
        local skip=false
        
        for exclude_db in "${exclude_array[@]}"; do
            # 去除可能的空格和特殊字符
            exclude_db=$(echo "$exclude_db" | xargs | tr -d '\r\n')
            
            if [ "$db" = "$exclude_db" ]; then
                skip=true
                excluded_dbs="$excluded_dbs $db"
                break
            fi
        done
        
        if [ "$skip" = false ]; then
            backup_dbs="$backup_dbs $db"
        fi
    done
    
    # 显示处理结果
    if [ -n "$excluded_dbs" ]; then
        print_color $YELLOW "   已排除数据库:$excluded_dbs"
    fi
    print_color $GREEN "   将备份数据库:$backup_dbs"
    
    if [ -z "$backup_dbs" ]; then
        print_color $RED "❌ 排除后没有需要备份的数据库"
        return 1
    fi
    
    echo ""
    echo -n -e "${YELLOW}确认执行备份?(y/N): ${NC}"
    read -r confirm
    
    if [[ ! "$confirm" =~ ^[Yy]$ ]]; then
        print_color $YELLOW "⏹️  备份已取消"
        return 0
    fi
    
    # 备份前先执行清理
    print_color $BLUE "🧹 备份前清理过期文件..."
    cleanup_old_backups
    
    local timestamp=$(date +"%Y%m%d_%H%M%S")
    local backup_file="${BACKUP_DIR}/partial_backup_${timestamp}.sql"
    
    print_color $BLUE "🚀 开始部分库备份..."
    print_color $CYAN "   备份文件: $(basename "$backup_file")"
    
    # 开始计时
    start_timer
    
    # 后台执行备份命令
    mysqldump -h"$MYSQL_HOST" -P"$MYSQL_PORT" -u"$MYSQL_USER" -p"$MYSQL_PASS" --databases $backup_dbs $MYSQLDUMP_OPTIONS > "$backup_file" 2>/dev/null &
    local backup_pid=$!
    
    # 显示进度条
    show_progress "正在执行部分库备份" $backup_pid
    
    # 等待备份完成并检查结果
    wait $backup_pid
    local backup_result=$?
    
    # 结束计时
    local elapsed_time=$(end_timer)
    
    if [ $backup_result -eq 0 ] && [ -s "$backup_file" ]; then
        print_color $GREEN "✅ 部分库备份完成!耗时: ${elapsed_time}"
        
        # 压缩备份文件
        local final_file=$(compress_backup "$backup_file")
        if [ $? -eq 0 ]; then
            print_color $GREEN "   保存路径: ${final_file}"
        else
            print_color $GREEN "   保存路径: ${backup_file}"
        fi
    else
        print_color $RED "❌ 部分库备份失败,耗时: ${elapsed_time}"
        rm -f "$backup_file"
        return 1
    fi
}

# 列出备份文件
list_backups() {
    print_color $BLUE "📋 可用的备份文件:"
    echo ""
    
    local backup_files=($(find "$BACKUP_DIR" \( -name "*.sql" -o -name "*.gz" \) -type f -printf "%T@ %p\n" 2>/dev/null | sort -rn | cut -d' ' -f2-))
    
    if [ ${#backup_files[@]} -eq 0 ]; then
        print_color $YELLOW "⚠️  没有找到备份文件"
        return 1
    fi
    
    local index=1
    for file in "${backup_files[@]}"; do
        local filename=$(basename "$file")
        local size=$(du -h "$file" 2>/dev/null | cut -f1)
        local date=$(date -r "$file" "+%Y-%m-%d %H:%M:%S" 2>/dev/null)
        printf "${CYAN}%2d.${NC} %-40s ${GREEN}%8s${NC} ${YELLOW}%s${NC}\n" "$index" "$filename" "$size" "$date"
        index=$((index + 1))
    done
    
    return 0
}

# 恢复备份
restore_backup() {
    if ! list_backups; then
        return 1
    fi
    
    echo ""
    echo -n -e "${YELLOW}请选择要恢复的备份文件编号: ${NC}"
    read -r selection
    
    if ! [[ "$selection" =~ ^[0-9]+$ ]]; then
        print_color $RED "❌ 请输入有效的数字"
        return 1
    fi
    
    local backup_files=($(find "$BACKUP_DIR" \( -name "*.sql" -o -name "*.gz" \) -type f -printf "%T@ %p\n" 2>/dev/null | sort -rn | cut -d' ' -f2-))
    local selected_index=$((selection - 1))
    
    if [ $selected_index -lt 0 ] || [ $selected_index -ge ${#backup_files[@]} ]; then
        print_color $RED "❌ 选择的编号超出范围"
        return 1
    fi
    
    local backup_file="${backup_files[$selected_index]}"
    local filename=$(basename "$backup_file")
    
    print_color $YELLOW "⚠️  警告:恢复操作将覆盖现有数据库!"
    print_color $CYAN "选择的备份文件: $filename"
    echo -n -e "${RED}确认执行恢复操作?(y/N): ${NC}"
    read -r confirm
    
    if [[ ! "$confirm" =~ ^[Yy]$ ]]; then
        print_color $YELLOW "⏹️  恢复已取消"
        return 0
    fi
    
    print_color $BLUE "🔄 开始恢复数据库..."
    print_color $CYAN "   恢复文件: $filename"
    
    show_progress 5 "正在执行数据库恢复"
    
    # 如果是gz文件,先解压
    local actual_file="$backup_file"
    if [[ "$backup_file" == *.gz ]]; then
        print_color $BLUE "📦 解压备份文件..."
        local temp_sql="${backup_file%.*}"
        if gunzip -c "$backup_file" > "$temp_sql"; then
            actual_file="$temp_sql"
        else
            print_color $RED "❌ 解压失败"
            return 1
        fi
    fi
    
    if mysql -h"$MYSQL_HOST" -P"$MYSQL_PORT" -u"$MYSQL_USER" -p"$MYSQL_PASS" < "$actual_file" 2>/dev/null; then
        print_color $GREEN "✅ 数据库恢复完成!"
        # 如果是临时解压的文件,删除它
        if [[ "$backup_file" == *.gz ]] && [ "$actual_file" != "$backup_file" ]; then
            rm -f "$actual_file"
        fi
    else
        print_color $RED "❌ 数据库恢复失败"
        # 如果是临时解压的文件,删除它
        if [[ "$backup_file" == *.gz ]] && [ "$actual_file" != "$backup_file" ]; then
            rm -f "$actual_file"
        fi
        return 1
    fi
}

# 显示帮助信息
show_help() {
    print_color $CYAN "用法:"
    print_color $WHITE "  $0                    # 交互式模式"
    print_color $WHITE "  $0 [选项]             # 命令行模式"
    echo ""
    print_color $CYAN "选项:"
    print_color $WHITE "  1                     # 全量备份"
    print_color $WHITE "  2                     # 部分库备份(排除指定数据库)"
    print_color $WHITE "  3                     # 恢复备份"
    print_color $WHITE "  4                     # 查看备份文件"
    print_color $WHITE "  5                     # 退出"
    print_color $WHITE "  -h, --help           # 显示此帮助信息"
    echo ""
    print_color $CYAN "示例:"
    print_color $WHITE "  $0 1                 # 直接执行全量备份"
    print_color $WHITE "  $0 2                 # 直接执行部分库备份"
    print_color $WHITE "  $0 4                 # 查看备份文件列表"
    echo ""
}

# 显示状态栏
show_status_bar() {
    echo ""
    draw_line "─" "$BLUE"
    printf "${CYAN}状态: ${GREEN}✅ 已连接${NC}"
    printf "${CYAN} | 备份目录: ${YELLOW}${BACKUP_DIR}${NC}"
    printf "${CYAN} | 保留天数: ${YELLOW}${RETENTION_DAYS}天${NC}\n"
    draw_line "─" "$BLUE"
}

# 显示菜单选项
show_menu_item() {
    local num=$1
    local icon=$2
    local text=$3
    local desc=$4
    
    # 计算总宽度为50个字符,确保在边框内对齐
    printf "  ${WHITE}[${CYAN}%s${WHITE}]${NC} %s ${WHITE}%-16s${NC} ${YELLOW}%-20s${NC}" "$num" "$icon" "$text" "$desc"
}

# 全屏显示菜单
show_menu() {
    echo ""
    echo ""
    center_text "📋 主菜单 - 请选择操作" "$BLUE"
    echo ""
    echo ""
    
    # 创建菜单框 - 使用固定宽度来确保对齐
    local menu_width=56
    local menu_start=$(( (TERM_COLS - menu_width) / 2 ))
    
    # 顶部边框
    printf "%*s${CYAN}┌" $menu_start ""
    for ((i=1; i<=menu_width-2; i++)); do printf "─"; done
    printf "┐${NC}\n"
    
    # 空行
    printf "%*s${CYAN}│" $menu_start ""
    printf "%*s${CYAN}│${NC}\n" $((menu_width-1)) ""
    
    # 菜单项
    printf "%*s${CYAN}│${NC}" $menu_start ""
    show_menu_item "1" "🗃️ " "全量备份" "备份所有数据库"
    printf "${CYAN}│${NC}\n"
    
    printf "%*s${CYAN}│${NC}" $menu_start ""
    printf "%*s${CYAN}│${NC}\n" $((menu_width-1)) ""
    
    printf "%*s${CYAN}│${NC}" $menu_start ""
    show_menu_item "2" "📦" "部分库备份" "排除指定数据库后备份"
    printf "${CYAN}│${NC}\n"
    
    printf "%*s${CYAN}│${NC}" $menu_start ""
    printf "%*s${CYAN}│${NC}\n" $((menu_width-1)) ""
    
    printf "%*s${CYAN}│${NC}" $menu_start ""
    show_menu_item "3" "🔄" "恢复备份" "从备份文件恢复数据库"
    printf "${CYAN}│${NC}\n"
    
    printf "%*s${CYAN}│${NC}" $menu_start ""
    printf "%*s${CYAN}│${NC}\n" $((menu_width-1)) ""
    
    printf "%*s${CYAN}│${NC}" $menu_start ""
    show_menu_item "4" "📋" "查看备份" "列出所有备份文件"
    printf "${CYAN}│${NC}\n"
    
    printf "%*s${CYAN}│${NC}" $menu_start ""
    printf "%*s${CYAN}│${NC}\n" $((menu_width-1)) ""
    
    printf "%*s${CYAN}│${NC}" $menu_start ""
    show_menu_item "5" "🚪" "退出程序" "安全退出备份工具"
    printf "${CYAN}│${NC}\n"
    
    # 空行
    printf "%*s${CYAN}│" $menu_start ""
    printf "%*s${CYAN}│${NC}\n" $((menu_width-1)) ""
    
    # 底部边框
    printf "%*s${CYAN}└" $menu_start ""
    for ((i=1; i<=menu_width-2; i++)); do printf "─"; done
    printf "┘${NC}\n"
    
    echo ""
    show_status_bar
    echo ""
}

# 执行指定的操作
execute_operation() {
    local choice=$1
    
    case $choice in
        1)
            print_color $BLUE "🚀 执行全量备份..."
            full_backup
            ;;
        2)
            print_color $BLUE "📦 执行部分库备份..."
            partial_backup
            ;;
        3)
            print_color $BLUE "🔄 执行备份恢复..."
            restore_backup
            ;;
        4)
            print_color $BLUE "📋 查看备份文件..."
            list_backups
            ;;
        5)
            print_color $GREEN "👋 感谢使用MySQL备份恢复工具!"
            exit 0
            ;;
        *)
            print_color $RED "❌ 无效选择: $choice"
            print_color $YELLOW "请使用 1-5 之间的数字,或运行 $0 --help 查看帮助"
            exit 1
            ;;
    esac
}

# 显示输入提示
show_input_prompt() {
    echo ""
    center_text "请输入您的选择 [1-5]" "$YELLOW"
    echo ""
    printf "%*s${CYAN}➤ ${NC}" $(( (TERM_COLS - 10) / 2 )) ""
}

# 显示操作结果页面
show_result_page() {
    local title="$1"
    local status="$2"
    
    clear_screen
    get_terminal_size
    
    echo ""
    draw_border "$title"
    echo ""
    
    if [ "$status" = "success" ]; then
        center_text "✅ 操作完成" "$GREEN"
    else
        center_text "❌ 操作失败" "$RED"
    fi
    
    echo ""
    echo ""
    center_text "按任意键返回主菜单..." "$CYAN"
}

# 交互式模式
interactive_mode() {
    while true; do
        clear_screen
        print_title
        show_menu
        show_input_prompt
        
        read -r choice
        
        case "$choice" in
            1|2|3|4|5)
                clear_screen
                print_title
                execute_operation "$choice"
                
                if [ "$choice" != "5" ]; then
                    if [ "$choice" != "4" ]; then
                        echo ""
                        echo ""
                        center_text "操作完成,按任意键返回主菜单..." "$CYAN"
                        read -r
                    else
                        echo ""
                        echo ""
                        center_text "按任意键返回主菜单..." "$CYAN"
                        read -r
                    fi
                fi
                ;;
            *)
                clear_screen
                print_title
                echo ""
                center_text "❌ 无效选择,请输入 1-5 之间的数字" "$RED"
                echo ""
                center_text "按任意键返回主菜单..." "$CYAN"
                read -r
                ;;
        esac
    done
}

# 主函数
main() {
    # 处理命令行参数
    if [ $# -gt 0 ]; then
        case "$1" in
            -h|--help)
                print_title
                show_help
                exit 0
                ;;
            1|2|3|4|5)
                # 命令行模式 - 直接执行指定操作
                print_title
                
                # 初始化检查
                check_mysql_connection
                create_backup_dir
                
                # 执行指定操作
                execute_operation "$1"
                exit 0
                ;;
            *)
                print_color $RED "❌ 无效参数: $1"
                echo ""
                show_help
                exit 1
                ;;
        esac
    fi
    
    # 交互式模式
    # 检查是否为root用户或有sudo权限
    if [ "$EUID" -ne 0 ] && ! sudo -n true 2>/dev/null; then
        print_color $YELLOW "⚠️  建议使用root权限运行此脚本"
    fi
    
    print_title
    
    # 初始化检查
    check_mysql_connection
    create_backup_dir
    
    # 进入交互式模式
    interactive_mode
}

# 信号处理
trap 'echo -e "\n${YELLOW}👋 程序已中断退出${NC}"; exit 1' INT TERM

# 运行主程序
main "$@"
相关推荐
理智的煎蛋2 小时前
基于 Celery 的分布式文件监控系统
redis·分布式·python·mysql·mongodb
蜀中廖化2 小时前
Android Studio 导入 opencv
android·opencv·android studio
奋斗的小鹰2 小时前
ASM Bytecode Viewer 插件查看kotlin和java文件的字节码
android·kotlin·asm
Albert Edison5 小时前
【MySQL】表的操作
数据库·mysql·oracle
欢喜躲在眉梢里5 小时前
mysql中的日志
android·运维·数据库·mysql·adb·日志·mysql日志
合作小小程序员小小店5 小时前
web开发,在线%校园,论坛,社交管理%系统,基于html,css,python,django,mysql
数据库·后端·mysql·django·web app
路上^_^6 小时前
安卓基础组件019-引导页布局001
android·安卓
梦终剧7 小时前
【Android之路】UI消息循环机制
android·ui
zh_xuan7 小时前
Android android.util.LruCache源码阅读
android·源码阅读·lrucache
梦终剧7 小时前
【Android之路】安卓资源与编译初步
android