From 57819950bba24b6c5d8c7fd404bc4d72359f5377 Mon Sep 17 00:00:00 2001 From: Tw93 Date: Thu, 11 Dec 2025 16:41:17 +0800 Subject: [PATCH] Scan a large number of files for optimization --- bin/clean.sh | 12 ++++++++++++ lib/clean/user.sh | 33 +++++++++++++++++++++------------ mole | 2 +- 3 files changed, 34 insertions(+), 13 deletions(-) diff --git a/bin/clean.sh b/bin/clean.sh index b8605a2..54adca3 100755 --- a/bin/clean.sh +++ b/bin/clean.sh @@ -323,6 +323,11 @@ safe_clean() { read -r size count < "$result_file" 2> /dev/null || true if [[ "$count" -gt 0 && "$size" -gt 0 ]]; then if [[ "$DRY_RUN" != "true" ]]; then + # Update spinner to show cleaning progress + if [[ -t 1 ]] && ((idx % 5 == 0)); then + stop_inline_spinner + MOLE_SPINNER_PREFIX=" " start_inline_spinner "Cleaning items ($idx/$total_paths)..." + fi # Handle symbolic links separately (only remove the link, not the target) if [[ -L "$path" ]]; then rm "$path" 2> /dev/null || true @@ -344,6 +349,7 @@ safe_clean() { local total_paths=${#existing_paths[@]} if [[ -t 1 ]]; then MOLE_SPINNER_PREFIX=" " start_inline_spinner "Scanning $total_paths items..."; fi + local idx=0 for path in "${existing_paths[@]}"; do local size_bytes size_bytes=$(get_path_size_kb "$path") @@ -351,6 +357,11 @@ safe_clean() { # Optimization: Skip expensive file counting if [[ "$size_bytes" -gt 0 ]]; then if [[ "$DRY_RUN" != "true" ]]; then + # Update spinner to show cleaning progress for slow operations + if [[ -t 1 ]]; then + stop_inline_spinner + MOLE_SPINNER_PREFIX=" " start_inline_spinner "Cleaning $description..." + fi # Handle symbolic links separately (only remove the link, not the target) if [[ -L "$path" ]]; then rm "$path" 2> /dev/null || true @@ -362,6 +373,7 @@ safe_clean() { ((total_count += 1)) removed_any=1 fi + ((idx++)) done fi diff --git a/lib/clean/user.sh b/lib/clean/user.sh index e722f7c..f75a723 100644 --- a/lib/clean/user.sh +++ b/lib/clean/user.sh @@ -97,7 +97,26 @@ clean_sandboxed_app_caches() { safe_clean ~/Library/Containers/com.apple.mediaanalysisd/Data/Library/Caches/* "Media analysis cache" safe_clean ~/Library/Containers/com.apple.AppStore/Data/Library/Caches/* "App Store cache" safe_clean ~/Library/Containers/com.apple.configurator.xpc.InternetService/Data/tmp/* "Apple Configurator temp files" - safe_clean ~/Library/Containers/*/Data/Library/Caches/* "Sandboxed app caches" + + # Clean sandboxed app caches - iterate to avoid shell expansion hang + # Check container protection BEFORE expanding cache files to prevent + # redundant protection checks on each file (Issue #116) + local containers_dir="$HOME/Library/Containers" + [[ ! -d "$containers_dir" ]] && return 0 + + for container_dir in "$containers_dir"/*; do + [[ -d "$container_dir" ]] || continue + + # Extract bundle ID and check protection status early + local bundle_id=$(basename "$container_dir") + if should_protect_data "$bundle_id"; then + debug_log "Protecting system container: $bundle_id" + continue + fi + + local cache_dir="$container_dir/Data/Library/Caches" + [[ -d "$cache_dir" ]] && safe_clean "$cache_dir"/* "Sandboxed app caches" + done } # Clean browser caches (Safari, Chrome, Edge, Firefox, etc.) @@ -166,20 +185,10 @@ clean_application_support_logs() { return 0 fi - # Clean log directories and cache patterns with iteration limit - # Reduced from 200 to 50 to prevent hanging on large directories - local iteration_count=0 - local max_iterations=50 - + # Clean log directories and cache patterns for app_dir in ~/Library/Application\ Support/*; do [[ -d "$app_dir" ]] || continue - # Safety: limit iterations - ((iteration_count++)) - if [[ $iteration_count -gt $max_iterations ]]; then - break - fi - app_name=$(basename "$app_dir") # Skip system and protected apps (case-insensitive) diff --git a/mole b/mole index 3383672..d47b6ff 100755 --- a/mole +++ b/mole @@ -22,7 +22,7 @@ SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" source "$SCRIPT_DIR/lib/core/common.sh" # Version info -VERSION="1.12.8" +VERSION="1.12.9" MOLE_TAGLINE="can dig deep to clean your Mac." # Check if Touch ID is already configured