Рейтинг:2

Сценарий Bash: условное удаление старых файлов с сохранением последних копий

флаг kp

Примечание. Хотя есть ответ от Джеффа Шаллера, это зависит от зш; поэтому я хотел бы получить ответ на основе Баш.

Мне нравится создавать скрипт Bash для условного удаления старых файлов из резервного каталога.

Есть 2 условия для 2 отдельных резервных копий файлов:

1, сохраните последнюю копию Edge_Profile_*.tgz, и удалить остальные Edge_Profile_*.tgz только если они старше 5 дней.

2, сохраните последнюю копию Firefox_Profile_*.tgz, и удалить остальные Firefox_Profile_*.tgz, не важно сколько им лет.

Вот как я изменил этот ответ AskUbuntu: https://askubuntu.com/a/933098/928088

Скрипт:

#!/бин/баш

LOG_FILE="/home/admn/Cleanup.log"
TEMP_LOG="/tmp/Temp_Cleanup.log"

мв $LOG_FILE $TEMP_LOG

{

cd /home/admn/Загрузки/Тест;

echo "Журнал очистки:" `дата`

find /home/admn/Downloads/Test/Edge_Profile_*.tgz -type f \( -mtime +5 -printf 'Y\t' -o -printf 'N\t' \) -printf '%A@\t% р\0' |
    сортировать -zk2,2 | голова -зн -1 | при чтении -r -d '' флаг _ файла; делать \
        регистр "$flag" в 
            'Y') echo rm "$file" 
               ;; 
            *) echo "пропуск $file (слишком новый)"
               ;; 
        эсак;
сделано

эхо

find /home/admn/Downloads/Test/Firefox_Profile_*.tgz -type f \( -printf 'Y\t' -o -printf 'N\t' \) -printf '%A@\t%p\0' |
    сортировать -zk2,2 | голова -зн -1 | при чтении -r -d '' флаг _ файла; делать \
        регистр "$flag" в 
            'Y') echo rm "$file" 
               ;; 
            *) echo "пропуск $file (слишком новый)"
               ;; 
        эсак        
сделано

} &>> $LOG_FILE

кот $TEMP_LOG >>$LOG_FILE

выход;

Вывод в лог-файл с эхо:

/usr/локальные/скрипты/cleanup.sh

rm /home/admn/Загрузки/Test/Edge_Profile_Jul_06_2021_00-35.tgz
rm /home/admn/Загрузки/Test/Edge_Profile_Jul_07_2021_00-35.tgz
....
пропуская /home/admn/Downloads/Test/Edge_Profile_Jul_12_2021_00-35.tgz (слишком новый)
пропуская /home/admn/Downloads/Test/Edge_Profile_Jul_13_2021_00-35.tgz (слишком новый)
....

rm /home/admn/Загрузки/Test/Firefox_Profile_Jul_01_2021_00-35.tgz
rm /home/admn/Загрузки/Test/Firefox_Profile_Jul_02_2021_00-35.tgz
....

Вывод в лог-файл во время фактического запуска скрипта, без эхо:

/home/admn/Downloads/cleanup.sh: строка 24: пропуск /home/admn/Downloads/Test/Edge_Profile_Jul_12_2021_00-35.tgz (слишком новый): нет такого файла или каталога
/home/admn/Downloads/cleanup.sh: строка 24: пропуск /home/admn/Downloads/Test/Edge_Profile_Jul_13_2021_00-35.tgz (слишком новый): нет такого файла или каталога
....

Всего файлов в каталоге: 20 файлов

1, Edge_Profile_*.tgz: с 06 по 17 июля: 12 файлов

2, Firefox_Profile_*.tgz: с 01 по 08 июля: 8 файлов

Проблемы:

(1) я считать скрипт вроде работает, но я не уверен, так как я изменил большую часть, не зная, что происходит.

(2) Вывод в файл журнала:

Я бы предпочел тот же вывод в файле журнала, который я получаю с помощью эхо, за исключением только имен файлов (не с полным путем), например:

rm Edge_Profile_Jul_11_2021_00-35.tgz

пропуск Edge_Profile_Jul_12_2021_00-35.tgz (слишком новый)

ОС: Ubuntu MATE 21.04

Большое спасибо.

Рейтинг:1
флаг ru

Манипулировать файлами в зависимости от времени их модификации намного проще в оболочке, которая позволяет вам обращаться к ним напрямую. zsh — одна из таких оболочек. Просто sudo apt установить zsh установить его. Поскольку ваши файлы находятся в одном каталоге, этот ответ не является рекурсивным. Сначала продемонстрируем более простой случай:

  • Чтобы сохранить последнюю копию Firefox_Profile_*.tgz и удалить остальные, независимо от их возраста:

    эхо будет rm -v -- Firefox_Profile_*.tgz(.om[2,-1])
    

    Удалить эхо бы часть, если она выглядит правильно. Это использует квалификатор glob (шаблон) внутри скобок, чтобы сделать три вещи:

    • выберите только простые файлы (не каталоги, сокеты и т. д.) с помощью .
    • упорядочить (сортировать) файлы по времени их модификации, от новых к старым, с ом
    • выберите фрагмент результирующего списка, начиная со второго элемента и до конца, пропуская первый (самый новый) файл с [2,-1]

    Если соответствующих файлов нет, zsh остановится и выдаст сообщение "zsh: совпадений не найдено" и не будет выполнять г.м..

  • Чтобы сохранить последнюю копию Edge_Profile_*.tgz и удалить остальные, только если они старше 5 дней, сначала мы берем самую последнюю:

    новейший=(Edge_Profile_*.tgz(.om[1]))
    

    ... а затем получаем те, что старше пяти дней:

    старше=(Edge_Profile_*.tgz(.m+5))
    

    Новая часть здесь +5 на м модификатор. Это выбирает файлы старше 5 дней. После этого мы убеждаемся, что самого нового нет в списке для удаления:

    удалить=("${(@)более старые:|новейшие}")
    

    Новая часть здесь — символ вычитания массива :|; это задокументировано в Раздел «Расширение параметров» руководства zsh. Он выбирает элементы «более старых», которых нет в «новейших». Наконец, мы удаляем этот список файлов:

    эхо будет rm -v -- "${remove[@]}"
    
Jags avatar
флаг kp
Спасибо за ответ, но мне нравится использовать `Bash`. «Потому что в прошлый раз, когда я устанавливал `zsh`, я закончил с форматированием и чистой установкой.
Jeff Schaller avatar
флаг ru
Вам не нужно использовать его как повседневную оболочку; просто установите его и используйте для этого скрипта.
Jags avatar
флаг kp
о, ладно, позже я попробую это, сначала в виртуальной машине. Еще раз спасибо.

Ответить или комментировать

Большинство людей не понимают, что склонность к познанию нового открывает путь к обучению и улучшает межличностные связи. В исследованиях Элисон, например, хотя люди могли точно вспомнить, сколько вопросов было задано в их разговорах, они не чувствовали интуитивно связи между вопросами и симпатиями. В четырех исследованиях, в которых участники сами участвовали в разговорах или читали стенограммы чужих разговоров, люди, как правило, не осознавали, что задаваемый вопрос повлияет — или повлиял — на уровень дружбы между собеседниками.