Показаны сообщения с ярлыком cron. Показать все сообщения
Показаны сообщения с ярлыком cron. Показать все сообщения

понедельник, 31 октября 2022 г.

Внесение в cron нескольких заданий через bash

Возникла необходимость внесения двух заданий в в cron. Например, одно задание должно выполняться ежедневно каждую 1 минуту часа с 18 до 21 часов, а второе задание также должно выполняться ежедневно, но в 21 час. 5 минут.

Если компьютер свой, то назначить эти задания можно через команду терминала crontab -e (см. пользовательское задание cron):

01 18-21 * * * /home/minter/.config/scripts/cron1.sh

05 21 * * * /home/minter/.config/scripts/cron2.sh

Но если компьютер не свой (вы кому-то помогаете дистанционно) или каждый раз просто лень постоянно вносить изменения в сron через  crontab -e ?

К счастью, решение имеется. Достаточно выполнить скрипт, который перезапишет пользовательский cron содержанием готового файла, в который заранее внесены все необходимые команды. 

Создадим скрипт, который "обнулит" текущий cron пользователя и запишет новый cron из подготовленного файла. 

🔰   Примечание. Приём заимствован из арсенала администраторов Linux, но с успехом работает и в системе только с одним пользователем. 

Пример:

#!/bin/bash
crontab -r
crontab -u minter /home/minter/Shared/cronjob
exit

-u minter  указывает на то, что новый cron будет назначен для пользователя системы с логином minter. Если пользователь имеет логин user, то будет -u user

/home/minter/Shared/cronjob  указывает полный путь к файлу cronjob

Сохраните данный скрипт как исполняемый файл sh, например newcron.sh 

Файл cronjob (или любое другое имя) представляет из себя обычный текстовый файл. Пример:

#
01 18-21 * * * /home/minter/.config/scripts/cron1.sh
05 21 * * * /home/minter/.config/scripts/cron2.sh

Обратите внимание, что в данном текстовом файле нет необходимости делать перевод каретки на новую строку, как это предписано при редактировании через crontab -e

Попробуйте выполнить созданный скрипт.  Откройте на редактирование cron (crontab -e) и убедитесь, что синтакис cron соблюдён, то есть пустая строка в конце присутствует.

пятница, 10 сентября 2021 г.

Адаптер wifi usb теряет связь с роутером по случайному закону

Проблема возникла при использовании на Linux подключаемого по usb wifi адаптера Realtek r8188eu (производства КНР) и роутера MikroTik 931-2nD r2. Сначала под подозрением оказался сам роутер MikroTik. Впоследствии выяснилось, что он "не виновен". Далее под подозрение попало устройство Realtek r8188eu в привязке именно к рассматриваемому компьютеру. Аналогичные r8188eu, подключаемые к другим компьютерам Windows и Linux, "вели себя" штатно.

Внешнее проявление выражалось в пропадании в какой-то момент времени связи с Интернет. При этом сам значок сетевого соединения на панели наличие соединения по wifi показывал, информация об IP-адресе и скорости соединения с точкой wifi присутствовала. Но команда ping роутера приводила к отрицательному результату, хотя ping своего IP-адреса,  полученного от DHCP роутера, выдавал положительный ответ. 

"Танцы с бубном" по поводу настроек энергосбережения устройств, подключаемых по usb, к результату не привели.

Было обнаружено, что если через значок менеджера сетевых соединений выключить и затем снова включить либо поддержку сети, либо Wi-Fi, связь компьютера с роутером восстанавливается.

Может быть сам r8188eu оказался немного дефектным, может быть он не совсем "дружит" с конкретным железом, может быть требуется осуществить ряд тонких настроек точки wifi роутера – это вопросы теоретических изысканий и долгого разбирательства. А причин может быть, как говорят, воз и маленькая тележка. Поэтому было принято решение оттолкнуться от результата выключения/включения поддержки сети и сделать такие действия выполняемыми автоматически при условии пропадания соединения с роутером. 

✔  Примечание. Решение было создано для своих нужд и не претендует как на корректность реализации, так и на изящность кода команд на bash.

Проверка состояния "видимости" роутера

✔  Примечание. Так как для запуска инструмента управления роутером MikroTik – winbox – в Linux требуется установка дополнительного ПО wine, то для управления роутером используется доступ через браузер и на MikroTik запущена служба www, хотя из соображений безопасности её не всегда рекомендуется использовать. Однако поскольку доступ к роутеру по www ограничен конкретной сетью (192.168.190.0/28), то её включение на MikroTik было сочтено приемлемым.

Сам роутер через DHCP выдаёт домен vot и в DNS имеет запись router.vot  Поэтому был создан сценарий, запускаемый через cron каждые 20 минут, который при отсутствии ответа от узла router.vot выполняет какое-то действие:

#!/bin/bash
echo -e "GET http://router.vot HTTP/1.0\n\n" | nc router.vot 80 > /dev/null 2>&1
if [ $? -eq 0 ]; then
     :
  else
     действие
fi
exit

Для внесения в cron задания выполните в терминале команду 

crontab -e

впишите новую строку

*/20 * * * * путь к сценарию sh

осуществите перевод каретки на новую строку и сохраните внесённые изменения.

✔  Примечание.  Если сценарий дополнить записью результата проверки в протокол, то получится, например:

#!/bin/bash
day=`date '+%d'`
log=/home/minter/Reports/system/$day.txt
echo -e "GET http://router.vot HTTP/1.0\n\n" | nc router.vot 80 > /dev/null 2>&1
if [ $? -eq 0 ]; then
  :
else
  echo "$(date '+%H.%M.%S') -- wifi is not active" >> $log
fi
exit

А в самом протоколе будет иметься запись, например:

13.00.12 -- wifi is not active

Действия при отсутствии ответа от роутера

К сожалению, планировавшиеся изначально остановка и последующий запуск сети к желаемому результату не привели:

/etc/init.d/networking stop

/etc/init.d/networking up

Поэтому было решено выключать wifi, а затем включать его снова.

Требуется указание на конкретную wifi, которое и было получено из ifconfig (или iwconfig). В моём случае этим wifi явилось устройство wlx000b819543a2 

Перед повторным включением wifi была задана пауза в 20 секунд.

Действия выполняются по сценарию sh:

#!/bin/bash
ifconfig wlx000b819543a2 down
sleep 20
ifconfig wlx000b819543a2 up
exit

который необходимо запускать под правами root.

Чтобы пароль не запрашивался, через команду sudo xed /etc/sudoers в файл sudoers была внесена строка:

minter ALL=NOPASSWD: путь с сценарию sh

minter – это моё имя пользователя в системе.

Итог

#!/bin/bash
day=`date '+%d'`
log=/home/minter/Reports/system/$day.txt
echo -e "GET http://router.vot HTTP/1.0\n\n" | nc router.vot 80 > /dev/null 2>&1
if [ $? -eq 0 ]; then
  :
else
  echo "$(date '+%H.%M.%S') -- wifi is not active" >> $log
  sudo /home/minter/Dropbox/scripts/modules/connect-net.sh
  echo "$(date '+%H.%M.%S') -- wifi restarted" >> $log
fi
exit

connect-net.sh – это сценарий перезапуска wifi

log – это файл протокола, из которого будет понятно в какое примерно время с точностью до 20 минут пропала связь с роутером.

✔   Примечание.  При тесте перезапуска wifi значок состояния сети на панели не изменялся. 

При тестировании сценария перезапуска wifi в логах роутера были получены записи:

00:0B:81:95:43:A2@wlan: disconnected, received deauth: sending station leaving (3)
00:0B:81:95:43:A2@wlan: connected, signal strength -58

Через 2 часа после публикации данной заметки состоялось практическая проверка реализации предложенного решения. Из протокола работы системы:

17.20.12 -- no wifi exists
17.20.12 -- wifi is not active
17.20.33 -- network restarted

Из лога MikroTik:

Sep/10/2021 17:06:13
00:0B:81:95:43:A2@wlan: disconnected, extensive data loss
Sep/10/2021 17:20:35
00:0B:81:95:43:A2@wlan: connected, signal strength -54

После этого связь с Интернет была восстановлена.

воскресенье, 10 февраля 2019 г.

Автоматизация процессов в Linux: периодический запуск Dropbox в указанный период времени

Выполнение указанной задачи может быть обусловлено необходимостью отслеживания появления новых файлов (папок) в папке общего доступа (обмена) Dropbox.

В частности, с 19 до 22 часов Dropbox должен запускаться на 10 минут. При этом период между данными запусками должен составить 30 минут.

При завершении этого 10-минутного сеанса работы папка общего доступа (обмена) должна быть проверена на наличие новых файлов/папок. Если такие файлы/папки имеются, то они подлежат перемещению в другую папку. Затем папка назначения открывается сопоставленным менеджером файлов (nautilus, nemo, caja, thunar).

Так как готового решения, на первый взгляд, не существует, то пришлось создать "самопальное" решение на bash. Может быть, кому-нибудь пригодится это решение или его отдельные элементы.


Задача является комплексной и состоит из нескольких отдельных задач:

– проверка наличия уже существующего процесса Dropbox;

– запуск 10-минутного сеанса работы;

– проверка наличия файлов/папок в папке общего доступа;

– назначение периодического пользовательского задания cron.


Проверка существования запущенного сеанса Dropbox обусловлена тем, что в назначенное время Dropbox может быть запущен вручную для выполнения какой-либо синхронизации. Если Dropbox уже запущен, то он должен быть остановлен.

Основным процессом Dropbox является выполняемая задача

dropbox-dist/dropbox-lnx.x86_64-.../dropbox , где в качестве многоточния указана версия используемого в настоящее время клиента. Но момент написания данной публикации такой версией является 66.4.84, поэтому в диспетчере задач необходимо произвести поиск задачи

dropbox-dist/dropbox-lnx.x86_64-66.4.84/dropbox

C течением времени клиент обновляется, поэтому версия будет постоянно меняться. По этой причине выполняющий данную проверку скрипт будет использовать несколько переменных.

1. Определяется текущая версия ПО Dropbox

ver=`cat ~/.dropbox-dist/VERSION`

2. Нас основании текущей версии указывается имя задачи для поиска

task=dropbox-dist/dropbox-lnx.x86_64-$ver/dropbox

3. Осуществляется поиск задачи Dropbox. Результат имеет два варианта: 0 – Dropbox не запущен, 1 – Dropbox запущен. Результат записывается в файл dropbox.txt  Расположение данного файла указано для моих нужд, у Вас оно определяется Вами. При выводе результата в файл dropbox.txt предыдущее значение заменяется новым, поэтому необходимости в последующем удалении данного файла не имеется.

ps ax | grep -v grep | grep $task | wc -l > ~/scripts/dropbox.txt

4. Для следующей операции сравнения "если ... то ..." производится считывание значения, записанного в файл dropbox.txt

value=`cat ~/scripts/dropbox.txt`

5. Если Dropbox не запущен (в dropbox.txt записан 0), то никаких действий не производится. В противном случае (Dropbox запущен) выдаётся команда остановки Dropbox.

 if [ $value -eq 0 ];
then
:
else
dropbox stop
fi

В результате получился следующий скрипт bash, которому условно назначено имя exist.sh

#!/bin/bash
ver=`cat ~/.dropbox-dist/VERSION`
task=dropbox-dist/dropbox-lnx.x86_64-$ver/dropbox
ps ax | grep -v grep | grep $task | wc -l > ~/scripts/dropbox.txt
value=`cat ~/scripts/dropbox.txt`
if [ $value -eq 0 ];
then
:
else
dropbox stop
fi
sleep 5 && exit

Команда 5 секундной паузы введена для "перестраховки", так как после команды остановки Dropbox необходимо 3-5 секунд для закрытия всех открытых подключений.


Проверка наличия в папке обмена новых файлов/папок. Автоматический перенос данных в другую папку.

Определяются переменные: H-1 – общая папка (обмена) Dropbox, H-2 – папка назначения, в которую будут переноситься данные.

D1=/home/user/Dropbox/H-1
D2=/home/user/Work/H-2

Производится подсчёт файлов (соответственно и папок, в которых будут расположены файлы):

count=`find $D1 -type f | wc -l`

Если в результате поиска выдано значение 0 (нет никаких файлов), то не производится никаких действий:

if [ $count -eq 0 ];
then
:

В противном случае всё содержимое папки общего доступа Dropbox копируется в другую папку (назначения):
 
else
cp -r $D1/* $D2

В папке источника данные подлежат удалению. Так как папка общего доступа Dropbox может иметь скрытый файл .dropbox, то он из процесса удаления должен быть исключён. То есть, в папке источника найти все данные и удалить их за исключением файла .dropbox:

find $D1/* ! -name '.dropbox' -delete

В папке назначения наоборот – найти и удалить скопированный из папки источника файл .dropbox, так как команда cp -r будет копировать всё, в том числе и скрытые файлы/папки: 

find $D2 -name '.dropbox' -delete

Завершить цикл и открыть папку назначения в файловом менеджере:

fi
xdg-open $D2

Листинг скрипта (например, do.sh) на bash:

#!/bin/bash
D1=/home/user/Dropbox/H-1
D2=/home/user/Work/H-2
count=`find $D1 -type f | wc -l`
if [ $count -eq 0 ];
then
:
else
cp -r $D1/* $D2
find $D1/* ! -name '.dropbox' -delete
find $D2 -name '.dropbox' -delete
fi
xdg-open $D2
exit

Если соответствующая переменной D1 папка является вложенной папкой общей папки Dropbox, то в ней файл .dropbox будет отсутствовать. В таком случае скрипт упрощается:

#!/bin/bash
D1=/home/user/Dropbox/H-1
D2=/home/user/Work/H-2
count=`find $D1 -type f | wc -l`
if [ $count -eq 0 ];
then
:
else
cp -r $D1/* $D2
find $D1/* -delete
fi
xdg-open $D2
exit

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


Отображение в Linux Mint 18.3 xfce


Отображение в Linux Mint 19.1 xfce

В этом случае можно использовать скрипт:

#!/bin/bash
DIR=/home/user/Dropbox/H-1
count=`find $DIR -type f | wc -l`
if [ $count -eq 0 ];
then
:
else
zenity --width=200 --height=50 --info --text "\nВ каталоге H-1 имеются данные" 2>/dev/null
fi
exit

Команда zenity вызывает отображение сообщения на экране монитора, которое будет отображаться до тех пор, пока пользователь не нажмёт кнопку OK.

--width=200 --height=50 указывает на ширину и высоту отображаемого окна. В Linux Mint 18.3 в этом не было необходимости, а в Linux Mint 19.1 такие параметры уже пришлось ввести.

Символ \n соответствует команде "перейти на новую строку". Введено для более лучшего визуального восприятия сообщения.



Скрипт 10-минутного сеанса работы Dropbox состоит из двух вышеописанных и команд запуска/остановки Dropbox.

#!/bin/bash
~/scripts/exist.sh
dropbox start -i
sleep 600
~/scripts/do.sh
dropbox stop
sleep 5 && exit

Команда 5 секундной паузы введена для "перестраховки", так как после команды остановки Dropbox необходимо 3-5 секунд для закрытия всех открытых подключений.


Периодический запуск Dropbox в указанный промежуток времени осуществляется через пользовательское задание cron. Запустите в терминале crontab -e и назначьте задание. Для описанной задачи, например:

*/30 19-22 * * * export DISPLAY=:0 && /путь_к_скрипту

вторник, 3 апреля 2018 г.

Выключение компьютера Linux через cron


После успешного применения назначения выполнения пользовательских задач через планировщик заданий cron (см. публикацию на эту тему) возникла необходимость в реализации ежедневного выключения компьютера по расписанию через задание cron.

К сожалению, пользовательское задание в виде исполняемого файла с содержанием:

#!/bin/bash
shutdown

не срабатывает. Для того, чтобы такая задача выполнялась через cron, задание необходимо создать для пользователя root:

 sudo crontab -e

Чтобы в Linux Mint вместо текстового редактора nano был запущен редактор mcedit, команда должна быть такой:

 sudo EDITOR=mcedit crontab -e

В п.2 публикации про пользовательские задания cron указывался способ назначения редактора заданий для редактирования заданий cron пользователя. Но в Linux Mint по умолчанию вход в систему под пользователем root не осуществляется, соответственно – домашний каталог пользователя root не создаётся, что делает невозможным внести необходимые изменения в файл .bashrc

Командой выключения от имени root является не shutdown, а  /sbin/poweroff.

Таким образом, например, для выполнения ежедневного выключения компьютера в 23:30 необходимо записать строку

 30 23 * * * /sbin/poweroff

Примечание. Не забывайте, что после неё необходимо добавить пустую строку.

Проверить существование задания можно командой sudo crontab -l

или в Linux Mint – sudo EDITOR=mcedit crontab -l ,

а самого файла задания – через sudo mc или sudo Ваш_менеджер_файлов, обратившись с каталогу /var/spool/cron/crontabs, в котором будет присутствовать файл root:


Если в дальнейшем необходимость в таком задании исчезнет, то удалите файл root командой терминала sudo crontab - r

четверг, 22 марта 2018 г.

Удаление по расписанию из Thunar


В процессе поиска материалов о возможности создания заданий cron от имени пользователя на форуме русскоязычного сообщества Ubuntu была найдена ветка обсуждений "Контекстное меню Thunar. Делимся своими конфигами". Меня заинтересовало сообщение с пояснением "Этим скриптом можно удалить файлы по расписанию:".

Текст скрипта приводится следующий:

Удаление по расписанию
<action>
<icon>appointment-new</icon>
<name>Удалить позже...</name>
<command>z=$(zenity --forms --title=&quot;Удалить в указанное время.&quot; --text=&quot;(Полученое задание: crontab -l)&quot; --separator=&quot;.&quot; --add-entry=&quot;Час, 0-23&quot; --add-entry=&quot;Мин, 0-59&quot; --add-calendar=&quot;День,&quot; --add-list=Удалить --list-values=&apos;В корзину|Безвозвратно|Спросить&apos;); if [ -n &quot;$z&quot; ]; then c=&quot;$HOME/tmp$(date +%s).cron&quot;;crontab -l &gt;&quot;$c&quot; ;echo &apos;## Задание Thunar&apos; &gt;&gt;$c ;h=$(echo $z|awk -F. &apos;{print $1}&apos;); m=$(echo $z|awk -F. &apos;{print $2}&apos;); if [ &quot;$h&quot; -lt &quot;24&quot; -a &quot;$m&quot; -lt &quot;60&quot; ]; then echo -n $m $h $(echo $z|awk -F. &apos;{print $3 &quot; &quot; $4 }&apos;) &apos;* &apos;&gt;&gt;$c;case &quot;$(echo $z|awk -F. &apos;{print $6}&apos;)&quot; in &quot;Спросить&quot;) echo &quot;if /usr/bin/zenity --display=:0 --list --timeout=90 --title=&apos;Расписание&apos; --text=&apos;Удалить следующие файлы?&apos; --hide-header --column=&apos;&apos; %N ;then gvfs-trash -f %F;fi&quot;&gt;&gt;$c;; &quot;В корзину&quot;) echo &quot;gvfs-trash -f %F&quot;&gt;&gt;$c;; &quot;Безвозвратно&quot;) echo &quot;gvfs-rm -f %F&quot;&gt;&gt;$c;; esac;echo &gt;&gt;$c;crontab $c;rm -v $c;for z in %F;do gvfs-set-attribute &quot;$z&quot; -t stringv metadata::emblems emblem-danger;done;notify-send -i info &quot;Задача добавлена.&quot; &quot;Для просмотра используйте: crontab -l&quot;;fi;fi</command>
<description>Удаление файлов по расписанию</description>
<patterns>*</patterns>
<directories/>
<audio-files/>
<image-files/>
<other-files/>
<text-files/>
<video-files/>
</action>

При создании пункта особых действий в Thunar (пример создания особых действий читайте здесь) из приведенного выше текста используется только команда, то есть то, что расположено между <command> и </command>. Но если указать приведенную выше команду, то она не сработает и не по причине того, что скрипт неправильный.

Причина заключается в том, что при публикации на форуме текст скрипта подвергся искажениям: ряд символов был автоматически заменён в соответствии с таблицей специальных символов HTML. Поэтому после обратного преобразования команда выглядит так:

z=$(zenity --forms --title="Удалить в указанное время." --text="(Полученное задание: crontab -l)" --separator="." --add-entry="Час, 0-23" --add-entry="Мин, 0-59" --add-calendar="День," --add-list=Удалить --list-values='В корзину|Безвозвратно|Спросить'); if [ -n "$z" ]; then c="$HOME/tmp$(date +%s).cron";crontab -l >"$c" ;echo '## Задание Thunar' >>$c ;h=$(echo $z|awk -F. '{print $1}'); m=$(echo $z|awk -F. '{print $2}'); if [ "$h" -lt "24" -a "$m" -lt "60" ]; then echo -n $m $h $(echo $z|awk -F. '{print $3 " " $4 }') '* '>>$c;case "$(echo $z|awk -F. '{print $6}')" in "Спросить") echo "if /usr/bin/zenity --display=:0 --list --timeout=90 --title='Расписание' --text='Удалить следующие файлы?' --hide-header --column='' %N ;then gvfs-trash -f %F;fi">>$c;; "В корзину") echo "gvfs-trash -f %F">>$c;; "Безвозвратно") echo "gvfs-rm -f %F">>$c;; esac;echo >>$c;crontab $c;rm -v $c;for z in %F;do gvfs-set-attribute "$z" -t stringv metadata::emblems emblem-danger;done;notify-send -i info "Задача добавлена." "Для просмотра используйте: crontab -l";fi;fi

Пользователям Runtu

Вследствие особенностей сборки при использовании указанного выше текста скрипта системное уведомление (оповещение) "Задача добавлена ..." работать не будет. Чтобы системное уведомление отображалось, вместо

notify-send -i info "Задача добавлена." "Для просмотра используйте: crontab -l"

используйте команду (текст можете изменить на свой)

zenity --notification --text "\n\nЗадание на удаление создано.\n\nДля просмотра введите crontab -l\n\n"

или попробовать установить пакет libnotify-binsudo apt install libnotify-bin


При запуске из контекстного меню Thunar отобразится окно запроса, например:


При этом команда будет применима к любым файлам и каталогам, если в условиях появления в контекстном меню Thunar этого задания галочки проставлены во всех полях настройки особого действия.

Задание действительно создаётся, за что следует поблагодарить автора данного скрипта. Однако чтобы его просмотреть, Вам всё равно придётся ознакомиться с некоторыми понятиями во вопросу планировщика заданий cron. Для практического использования рассматриваемого скрипта имеет смысл прочитать п.п. 2 и 4 публикации "Пользовательское задание cron в Linux Mint и Ubuntu".

Примечание. Если Вы будете использовать такой скрипт не на постоянной основе, а время от времени, то можно пойти по простому пути. То есть не вникать в описание пользовательских заданий cron, а просто время от времени удалять пользовательский файл заданий cron до внесения в него очередного задания на удаление по расписанию.

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

sudo rm /var/spool/cron/crontabs/user

В этой команде user будет являться файлом cron пользователя системы user. Если у Вас другой логин, например boss, то вместо user будет boss.

Созданное мной через Thunar пользовательское задание имело такую строку:

55 21 21 03 * gvfs-trash -f '/home/cemea/Article.pdf'


Примечание.

Задание можно назначать на выделенную группу файлов/каталогов. Например, команда для удаления двух файлов имеет вид


  gvfs-trash -f 'путь_к_контенту' 'путь_к_контенту'

При других вариантах удаления используются команды:

безвозвратно – gvfs-rm -f 'путь_к_удаляемому_контенту' ;

спросить – на примере удаления из каталога Mount файла с именем

09. Эдуард Артемьев - Солярис OST [1972] - Track 01 - J. S. Bach's.mp3

if /usr/bin/zenity --display=:0 --list --timeout=90 --title='Расписание' --text='Удалить следующие файлы?' --hide-header --column='' '09. Эдуард Артемьев - Солярис OST [1972] - Track 01 - J. S. Bach'\''s.mp3' ;then gvfs-trash -f '/home/cemea/Mount/09. Эдуард Артемьев - Солярис OST [1972] - Track 01 - J. S. Bach'\''s.mp3';fi


При этом в менеджере файлов Thunar файлу автоматически назначается эмблема


В случае планирования удаления каталогов им также назначается эмблема


Возможно, Вы пожелаете внести некоторые изменения в текст скрипта.

Другая эмблема

Обратитесь к тексту скрипта, найдите в нём значение emblem-danger и вместо него укажите наименование желаемой эмблемы.


Точное наименование эмблем (текст то точки) смотрите в каталоге
 /usr/share/icons/каталог_темы/emblems в любом вложенном каталоге.


Например, в Linux Mint с темой значков Mint-X наименования эмблем можно посмотреть в каталоге  /usr/share/icons/Mint-X/emblems/48

Про собственные эмблемы можно найти материал на этой странице.

Изменение вопроса

Так как скриптом можно запланировать удаление как файлов, так и каталогов, то можно изменить слово "файлы", например, на "выбранное". Найдите в тексте скрипта

   --text='Удалить следующие файлы?' и вместо него укажите:

   --text='Удалить выбранное?'

Важно. Следует отметить, что после отработки заданий по удалению файлов или каталогов строки этих заданий из пользовательского файла cron автоматически не удаляются. Вам их придётся либо удалить вручную (через редактирование своего пользовательского файла cron), либо удалить свой файл пользовательских заданий cron (см. примечание выше). При назначении в Thunar нового задания по удалению контента по расписанию файл пользовательских заданий cron будет создан автоматически.

понедельник, 12 марта 2018 г.

Пользовательское задание cron в Linux Mint и Ubuntu


По мере ознакомления с содержанием найденных по поиску публикаций о cron у меня крепло ощущение, что являюсь ярким представителем "тупых" пользователей подкласса "всё равно не въезжаю". Поэтому предлагаю к ознакомлению свою версию подачи материала или, другими словами, личный опыт создания пользовательских заданий cron, которые работали бы по принципу "Настроил и забыл".

Примечание. Так как создание пользовательского задания cron осуществлялось для Linux Mint и Runtu (Runtu является адаптированной к русскоязычному пользователю Ubuntu с графическим окружением xfce), то далее в тексте будут даваться пояснения для обоих дистрибутивов.


1. Где посмотреть расписание заданий cron?

Так как рассматривается задача запуска именно пользовательских заданий cron, то статьи с упоминаниями о cron.hourly, cron.daily, cron.weelky, cron.mounthly в каталоге etc можете даже не читать. По умолчанию, эти задания являются системными и определены для запуска от суперпользователя root. Если интересно, то можете открыть эти каталоги (только для просмотра не потребуется команда sudo) и ознакомиться с содержанием расположенных там файлов. Расписанием этих заданий является файл /etc/crontab

Ваши пользовательские задания будут расположены в каталоге
 /var/spool/cron/crontabs, но под своим именем просмотреть их будет невозможно:


Чтобы удовлетворить своё любопытство, запустите файловый менеджер с правами суперпользователя, например,

  sudo mc, sudo thunar (sudo nemo или sudo caja).

Так как раньше Вы не создавали заданий, то этот каталог будет пуст.


2. Инструмент для редактирования файла заданий cron

Командой редактирования файла заданий cron является crontab -e

Linux Mint

В Linux Mint Вас может ожидать сюрприз, так как будет запущен редактор nano.


Может быть в этом редакторе и имеются преимущества, но лично меня он совершенно не устраивает. Поэтому воспользуюсь редактором, встроенным в Midnight Commander.

У Вас установлена такая, на мой взгляд, наиполезнейшая вещь? Если нет, то откройте терминал и введите команду sudo apt install mc.

EDITOR=mcedit crontab -e


Так как в дальнейшем вместо crontab -e вводить EDITOR=mcedit crontab -e затруднительно (забывается, понимаете ли), то включите в файловом менеджере отображение скрытых файлов, в файл .bashrc своего домашнего каталога внесите строку export EDITOR=mcedit и сохраните файл. Теперь при дальнейших вводах команды  crontab -e  у Вас будет запускаться  mcedit.


Runtu

В Runtu редактор nano в сборку не включён, а Midnight Commander наоборот – включён в комплект поставки. Поэтому здесь сюрприза не было. При вводе команды crontab -e система выдала запрос на выбор редактора:

Select an editor.  To change later, run 'select-editor'.
  1. /usr/bin/mcedit
  2. /usr/bin/vim.tiny

Choose 1-2 []:

При выборе 1 система запомнила мой выбор и больше вопросов не задавала.


К редактированию файла расписания запускаемых заданий вернёмся немного позже. А пока необходимо определить свои намерения. Так как если Вам по расписанию ничего запускать не требуется, то и дальнейшее чтение этой публикации не имеет практического смысла.


3. Что будет запускаться по расписанию?

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

Примечание. 

На одном из форумов на заданный мной вопрос был получен следующий ответ: "Программа через cron запускается вне окружения рабочего стола, она не может просто так с ним взаимодействовать. И организовать это взаимодействие хоть в принципе и возможно, но довольно сложно – чтобы без глюков". 

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

Следует определиться, если так можно выразиться, с процессом выполнения задания. Задание может быть выполнено или в фоновом режиме без какого-либо отображения на экране (по принципу "не видно и не слышно, но дело своё делает") или сопровождаться выводом на экран монитора. В случае запуска графических приложений, конечно, подходит только второе.

В этой публикации упор сделан на рассмотрении реализации задачи, которую можно описать тремя пунктами.

1. Ежедневный запуск Dropbox в выбранное время.
2. Ожидание определённое время, в течение которого производится синхронизация папок и файлов.
3. Остановка Dropbox.

Сформулированная задача может быть выполнена и в фоновом режиме, и с выводом на экран монитора, поэтому будут описаны оба варианта.

Условно реализацию работы в фоновом режиме назову "Вариант 1", а с выводом на экран монитора – "Вариант 2".

3.1. Вариант 1

Так как в варианте 1 взаимодействия с рабочим столом не предусматривается, то определяю перечень необходимых команд, записанных в файл daily-dropbox моего домашнего каталога.

Примечание. Как было отмечено выше, упомянутый файл можно оформить и как файл daily-dropbox.sh  Для системы разница в именах файла принципиального значения не имеет. Единственным требованием является то, что этот файл должен быть исполняемым. 

#!/bin/bash
dropbox start
sleep 15
rm /home/cemea/.config/autostart/dropbox.desktop
sleep 1200
dropbox stop

dropbox start – запуск dropboxd.

sleep 15 – пауза 15 секунд. Пауза необходима для того, чтобы запускаемый Dropbox "успел" создать ярлык автозапуска (что он в моей системе каждый раз делает). 15 секунд установлены экспериментально, так как при определённой степени загруженности системы Dropbox стартует не моментально.

rm /home/cemea/.config/autostart/dropbox.desktop – данная команда удаляет принудительно создаваемый в xfce ярлык запуска Dropbox при старте системы когда пользователь запускает Dropbox из меню программ (подробности).

sleep 1200 – пауза 1200 секунд, что соответствует 20-ти минутам (20х60). Предполагается, что этого времени будет достаточно, чтобы была осуществлена синхронизация каталога клиента Dropbox с облаком Dropbox.

Вы можете указать своё значение. Так как на ежедневной основе у меня в Dropbox помещаются небольшие объёмы данных, то отводимых на синхронизацию 20-ти минут мне хватает с избытком.

dropbox stop – остановка dropboxd. По этой команде Dropbox прекращает свою деятельность. Поэтому к данным большого объёма будет применяться правило "кто не успел, тот опоздал". Другими словами, их синхронизация будет продолжена в течение последующих сеансов работы Dropbox или завершена при ручном запуске клиента Dropbox.

Для подобных файлов у меня заведён специальный каталог Tools. Поэтому для своего удобства создаю в нём каталог cron и помещаю в него файл daily-dropbox. Далее в свойствах файла (секция "Права") ставлю галочку в поле "Разрешить запуск этого файла в качестве программы".

3.2. Вариант 2

В случае взаимодействия с рабочим столом в рассматриваемом примере кроме отображения самого значка Dropbox будут выводиться сообщения, информирующие о выполнении задания. Данные сообщения будут отображаться в течение 3 секунд и затем автоматически исчезать. Командой вывода таких сообщений является:

zenity --info --text "Текст сообщения." 2>/dev/null --timeout=3

Поэтому в предыдущий текст будут добавлены такие команды. Вместо команды dropbox start будет использоваться dropbox start -i. Для моего графического окружения xfce принципиального значения между dropbox start и dropbox start -i нет, но в меню программ для запуска клиента Dropbox используется именно команда dropbox start -i.

Содержание исполняемого файла dropboxme.sh:

#!/bin/bash
zenity --info --text "Запуск клиента Dropbox." 2>/dev/null --timeout=3
dropbox start -i
sleep 15
rm /home/celesta/.config/autostart/dropbox.desktop
zenity --info --text "Автозапуск Dropbox удалён." 2>/dev/null --timeout=3
sleep 1200
zenity --info --text "Завершение работы Dropbox." 2>/dev/null --timeout=3
dropbox stop


4. Назначение пользовательского задания cron

Ввожу команду  crontab -e

Если посмотреть, что отображается в терминале, то можно увидеть такую запись:

no crontab for cemea - using an empty one

В запустившемся редакторе mcedit в новой строке пишу

15 22 * * * /home/cemea/Tools/cron/daily-dropbox

Что это означает?

Каждая задача формируется следующим образом:

минута  час  день  месяц  день_недели  команда

Соответственно, в диапазонах возможных цифр строка выглядит:

0 ... 59   0 ... 23   1 ... 31   1 ... 12   0 ... 7   команда


Поле "пользователь" присутствует только в таблицах /etc/crontab и др. расположенных в каталоге /etc/cron.d/.

Дополнительные варианты

Дефис (-) между целыми числами обозначает диапазон чисел. Например, 1-4 означает целые числа 1, 2, 3 и 4.

Список значений, разделённых запятыми, обозначает перечень. Например, перечисление 3, 4, 6, 8 означает четыре указанных целых числа.

Косая черта (/) используется для определения шага значений. Если после диапазона указать /<целое_число>. Например, значение минут 0-59/2, определяет, что задание будет запущено каждую вторую минуту.

Если вместо цифры введён символ *, то он соответствует "каждый/ую".

То есть, говоря проще, каждый день недели в 22 часа 15 минут будет запущена задача на синхронизацию Dropbox – /home/cemea/Tools/cron/daily-dropbox.

После ввода строки 15 22 * * * /home/cemea/Tools/cron/daily-dropbox нажимаю клавишу Enter, чтобы курсор перешёл на следующую строку. Если этого не сделать, то при попытке сохранения Вам будет выдано предупреждение:

new crontab file is missing newline before EOF, can't install.
Do you want to retry the same edit? (y/n)

При сохранении Вам будет выдан запрос


Пусть Вас не смущает предложение сохранить задание в каталог  /tmp  да ещё и под каким-то непонятным именем. Жмите "Сохранить".

Если в течение этого сеанса редактирования Вы не планируете вносить какие-либо изменения в свой crontab, то по F10 закрывайте mcedit.

Так как терминал у Вас ещё открыт, то Вы увидите, что в его окне появилось сообщение – crontab: installing new crontab

При назначении задания по варианту 2 строка моего задания имеет вид:

15 22 * * * export DISPLAY=:0 && /home/cemea/Tools/configs/dropboxme.sh

Это важно. Обратите внимание, что DISPLAY должно быть именно заглавными буквами. Если указать export display=:0, то на экране ничего не отобразится. Желающие получить теоретическое обоснование читают ветку форума.

Если поинтересоваться содержанием каталога /var/spool/cron/crontabs, то можно будет увидеть, что в нём появился файл c именем пользователя системы. В моём случае это файл cemea:


В этом файле и будут в дальнейшем находиться все пользовательские задания cron. Этих заданий может быть несколько. Применительно к рассматриваемой задаче внесу 2 задания. Первое будет запускать синхронизацию Dropbox c отображением его значка и всех информационных сообщений, а второе будет запускать синхронизацию Dropbox "тихо", не отвлекая меня от деятельности на благо общества. Например:

15 09 * * * export DISPLAY=:0 && /home/cemea/Tools/configs/dropboxme.sh
30 16 * * * /home/cemea/Tools/cron/daily-dropbox

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

Для просмотра своих заданий используйте команду  crontab -l

Для удаления файла своих заданий используйте команду  crontab -r


5. Экспериментальная проверка

Как говорится, практика – критерий истины, поэтому проверим отработку назначенного задания.

Как было отмечено ранее, если при запуске заданий cron был использован вариант 1, то никакого взаимодействия с графическим окружением производиться не будет, поэтому запускаю диспетчер задач и вижу отработку своего здания cron.

Linux Mint



На рисунках звёздочками красного цвета отмечены выполняющиеся файл задания cron daily-dropbox, Dropbox (повторять длинную строку не буду), а также выполняемая на момент просмотра диспетчера задач команда speep 1200.

Соответственно, если вместо исполняемого файла запущен файл sh, то он и будет отображён в диспетчере задач. Так как выше речь шла про dropboxme.sh, то


При повторном обращении к диспетчеру задач через 20 минут в списке выполняемых заданий перечисленные выше отсутствуют. Это свидетельствует о том, что задание cron было отработано и завершено.

Runtu

В Runtu вместо длинной строки dropbox-dist/... отображается просто dropbox, а вместо sleep 1200 только sleep. При имени исполняемого файла не daily-dropbox, а dropbox.sh будет отображён dropbox.sh


Выполнение заданий по варианту 2 (см. выше) Вы увидите на экране, хотя и через диспетчер задач они также будут отображаться.


6. А что ещё можно запускать?

Применяя инструкцию export DISPLAY=:0 && команда можно запланировать себе запуск желаемых графических приложений.

В частности, в какое-то время запустить браузер Firefox, в адресную строку которого автоматически будет вписан адрес ресурса, например, news.mail.ru  В этом случае содержание исполняемого файла будет следующим:

#!/bin/bash
firefox "http://news.mail.ru"

А в качестве прикола можно поставить себе напоминание:

#!/bin/bash
zenity --info --text "А не испить ли мне кофею?" 2>/dev/null --timeout=60

И вот сижу я, смотрю на экран, а мне вдруг выскакивает:


Поэтому здесь имеется простор для воплощения Ваших фантазий в наборы инструкций операционной системе. Главное – вводить правильные команды.