如何编写批量清理无效软链接脚本

wen 实用脚本 31

基础版 - 查找并删除

#!/bin/bash
# 基本删除所有无效软链接
find /path/to/search -type l ! -exec test -e {} \; -delete
# 带确认提示的版本
find /path/to/search -type l ! -exec test -e {} \; -print -delete

安全版 - 先预览再删除

#!/bin/bash
# 设置搜索路径
SEARCH_DIR="${1:-.}"
echo "正在扫描无效软链接..."
INVALID_LINKS=$(find "$SEARCH_DIR" -type l ! -exec test -e {} \; 2>/dev/null)
if [ -z "$INVALID_LINKS" ]; then
    echo "未发现无效软链接"
    exit 0
fi
echo "发现以下无效软链接:"
echo "-------------------"
echo "$INVALID_LINKS"
echo "-------------------"
read -p "是否删除这些无效链接? (y/n): " CONFIRM
if [[ $CONFIRM == [yY] ]]; then
    echo "$INVALID_LINKS" | while read -r link; do
        rm "$link" && echo "已删除: $link"
    done
    echo "清理完成!"
else
    echo "已取消操作"
fi

带日志的版本

#!/bin/bash
# 配置
SEARCH_DIR="${1:-.}"
LOG_FILE="/var/log/clean_symlinks_$(date +%Y%m%d).log"
DRY_RUN=false
# 解析参数
while [[ $# -gt 0 ]]; do
    case $1 in
        --dry-run) DRY_RUN=true; shift ;;
        --log=*) LOG_FILE="${1#*=}"; shift ;;
        *) SEARCH_DIR="$1"; shift ;;
    esac
done
echo "=================================" | tee -a "$LOG_FILE"
echo "清理无效软链接 - $(date)" | tee -a "$LOG_FILE"
echo "搜索目录: $SEARCH_DIR" | tee -a "$LOG_FILE"
echo "日志文件: $LOG_FILE" | tee -a "$LOG_FILE"
DELETED_COUNT=0
ERROR_COUNT=0
while IFS= read -r -d '' link; do
    if [ ! -e "$link" ]; then
        TARGET=$(readlink "$link")
        if [ "$DRY_RUN" = true ]; then
            echo "[DRY RUN] 将删除: $link -> $TARGET" | tee -a "$LOG_FILE"
        else
            if rm "$link" 2>/dev/null; then
                echo "[DELETED] $link -> $TARGET" | tee -a "$LOG_FILE"
                ((DELETED_COUNT++))
            else
                echo "[ERROR] 无法删除: $link" | tee -a "$LOG_FILE"
                ((ERROR_COUNT++))
            fi
        fi
    fi
done < <(find "$SEARCH_DIR" -type l -print0 2>/dev/null)
echo "=================================" | tee -a "$LOG_FILE"
echo "统计信息:" | tee -a "$LOG_FILE"
if [ "$DRY_RUN" = true ]; then
    echo "模拟运行 - 将删除 $DELETED_COUNT 个链接" | tee -a "$LOG_FILE"
else
    echo "已删除: $DELETED_COUNT" | tee -a "$LOG_FILE"
    echo "失败: $ERROR_COUNT" | tee -a "$LOG_FILE"
fi

交互式选择版

#!/bin/bash
# 交互式选择要删除的链接
SEARCH_DIR="${1:-.}"
echo "扫描无效软链接..."
declare -a INVALID_LINKS=()
while IFS= read -r -d '' link; do
    if [ ! -e "$link" ]; then
        INVALID_LINKS+=("$link")
    fi
done < <(find "$SEARCH_DIR" -type l -print0 2>/dev/null)
if [ ${#INVALID_LINKS[@]} -eq 0 ]; then
    echo "未发现无效软链接"
    exit 0
fi
echo "发现 ${#INVALID_LINKS[@]} 个无效软链接:"
echo "----------------------------------------"
for i in "${!INVALID_LINKS[@]}"; do
    echo "[$((i+1))] ${INVALID_LINKS[$i]} -> $(readlink "${INVALID_LINKS[$i]}")"
done
echo "----------------------------------------"
echo "请选择操作:"
echo "a) 全部删除"
echo "s) 选择删除"
echo "q) 退出"
read -p "选择: " CHOICE
case $CHOICE in
    a|A)
        for link in "${INVALID_LINKS[@]}"; do
            rm "$link" && echo "已删除: $link"
        done
        echo "全部删除完成"
        ;;
    s|S)
        read -p "输入要删除的编号(逗号分隔,如 1,3,5): " NUMBERS
        IFS=',' read -ra SELECTED <<< "$NUMBERS"
        for num in "${SELECTED[@]}"; do
            index=$((num-1))
            if [ $index -ge 0 ] && [ $index -lt ${#INVALID_LINKS[@]} ]; then
                rm "${INVALID_LINKS[$index]}" && echo "已删除: ${INVALID_LINKS[$index]}"
            else
                echo "无效编号: $num"
            fi
        done
        ;;
    q|Q)
        echo "退出"
        exit 0
        ;;
    *)
        echo "无效选择"
        exit 1
        ;;
esac

归档无效链接(安全删除前)

#!/bin/bash
# 将无效链接移动到备份目录
SEARCH_DIR="${1:-.}"
BACKUP_DIR="./backup_symlinks_$(date +%Y%m%d_%H%M%S)"
mkdir -p "$BACKUP_DIR"
COUNT=0
while IFS= read -r -d '' link; do
    if [ ! -e "$link" ]; then
        # 创建备份路径
        REL_PATH="${link#./}"
        BACKUP_PATH="$BACKUP_DIR/$REL_PATH"
        mkdir -p "$(dirname "$BACKUP_PATH")"
        # 保存链接信息
        echo "原始路径: $link" > "${BACKUP_PATH}.info"
        echo "目标路径: $(readlink "$link")" >> "${BACKUP_PATH}.info"
        # 移动链接
        mv "$link" "$BACKUP_PATH" 2>/dev/null && ((COUNT++))
    fi
done < <(find "$SEARCH_DIR" -type l -print0 2>/dev/null)
echo "已归档 $COUNT 个无效链接到 $BACKUP_DIR"
echo "如需恢复,请使用 restore_backup.sh 脚本"

使用说明

  1. 基本使用
    # 直接运行
    ./clean_symlinks.sh /path/to/search

在当前目录执行

./clean_symlinks.sh

如何编写批量清理无效软链接脚本


2. **权限要求**:
```bash
# 添加执行权限
chmod +x clean_symlinks.sh
# 可能需要sudo权限
sudo ./clean_symlinks.sh /system/path
  1. 安全建议
  • 首次使用添加 --dry-run 参数预览结果
  • 建议先在测试目录验证
  • 对系统目录操作时务必谨慎

这些脚本覆盖了从简单到复杂的各种需求,你可以根据实际情况选择使用。

抱歉,评论功能暂时关闭!