Как вывести список всех заданий cron для всех пользователей?



есть ли команда или существующий скрипт, который позволит мне просматривать все запланированные задания cron системы *NIX сразу? Я бы хотел, чтобы он включал все пользовательские crontabs, а также /etc/crontab, что в /etc/cron.d. Также было бы неплохо увидеть конкретные команды, выполняемые run-parts на /etc/crontab.



В идеале, я бы хотел, чтобы вывод в хорошей форме столбца и упорядочен каким-то значимым образом.



затем я мог бы объединить эти списки с нескольких серверов для просмотра общий " график мероприятий."



Я собирался написать такой скрипт сам, но если кто-то уже беда...

1422   22  

22 ответов:

вы должны были бы запустить это как root, но:

for user in $(cut -f1 -d: /etc/passwd); do crontab -u $user -l; done

будет цикл над каждым именем пользователя, перечисляя их crontab. Crontabs принадлежат соответствующим пользователям, поэтому вы не сможете увидеть crontab другого пользователя без них или root.


Edit если вы хотите узнать, какому пользователю принадлежит crontab, используйте echo $user

for user in $(cut -f1 -d: /etc/passwd); do echo $user; crontab -u $user -l; done

Я закончил писать сценарий (я пытаюсь научить себя тонкостям сценариев bash, поэтому вы не видите здесь что-то вроде Perl). Это не совсем простое дело, но оно делает большую часть того, что мне нужно. Он использует предложение Кайла для поиска кронтабов отдельных пользователей, но также имеет дело с /etc/crontab (включая скрипты, запущенные run-parts на /etc/cron.hourly,/etc/cron.daily и т. д.) и рабочие места в . Он берет все это и сливает их в дисплей что-то например:

mi     h    d  m  w  user      command
09,39  *    *  *  *  root      [ -d /var/lib/php5 ] && find /var/lib/php5/ -type f -cmin +$(/usr/lib/php5/maxlifetime) -print0 | xargs -r -0 rm
47     */8  *  *  *  root      rsync -axE --delete --ignore-errors / /mirror/ >/dev/null
17     1    *  *  *  root      /etc/cron.daily/apt
17     1    *  *  *  root      /etc/cron.daily/aptitude
17     1    *  *  *  root      /etc/cron.daily/find
17     1    *  *  *  root      /etc/cron.daily/logrotate
17     1    *  *  *  root      /etc/cron.daily/man-db
17     1    *  *  *  root      /etc/cron.daily/ntp
17     1    *  *  *  root      /etc/cron.daily/standard
17     1    *  *  *  root      /etc/cron.daily/sysklogd
27     2    *  *  7  root      /etc/cron.weekly/man-db
27     2    *  *  7  root      /etc/cron.weekly/sysklogd
13     3    *  *  *  archiver  /usr/local/bin/offsite-backup 2>&1
32     3    1  *  *  root      /etc/cron.monthly/standard
36     4    *  *  *  yukon     /home/yukon/bin/do-daily-stuff
5      5    *  *  *  archiver  /usr/local/bin/update-logs >/dev/null

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

до сих пор я тестировал его на Ubuntu, Debian и Red Hat AS.

#!/bin/bash

# System-wide crontab file and cron job directory. Change these for your system.
CRONTAB='/etc/crontab'
CRONDIR='/etc/cron.d'

# Single tab character. Annoyingly necessary.
tab=$(echo -en "\t")

# Given a stream of crontab lines, exclude non-cron job lines, replace
# whitespace characters with a single space, and remove any spaces from the
# beginning of each line.
function clean_cron_lines() {
    while read line ; do
        echo "${line}" |
            egrep --invert-match '^($|\s*#|\s*[[:alnum:]_]+=)' |
            sed --regexp-extended "s/\s+/ /g" |
            sed --regexp-extended "s/^ //"
    done;
}

# Given a stream of cleaned crontab lines, echo any that don't include the
# run-parts command, and for those that do, show each job file in the run-parts
# directory as if it were scheduled explicitly.
function lookup_run_parts() {
    while read line ; do
        match=$(echo "${line}" | egrep -o 'run-parts (-{1,2}\S+ )*\S+')

        if [[ -z "${match}" ]] ; then
            echo "${line}"
        else
            cron_fields=$(echo "${line}" | cut -f1-6 -d' ')
            cron_job_dir=$(echo  "${match}" | awk '{print $NF}')

            if [[ -d "${cron_job_dir}" ]] ; then
                for cron_job_file in "${cron_job_dir}"/* ; do  # */ <not a comment>
                    [[ -f "${cron_job_file}" ]] && echo "${cron_fields} ${cron_job_file}"
                done
            fi
        fi
    done;
}

# Temporary file for crontab lines.
temp=$(mktemp) || exit 1

# Add all of the jobs from the system-wide crontab file.
cat "${CRONTAB}" | clean_cron_lines | lookup_run_parts >"${temp}" 

# Add all of the jobs from the system-wide cron directory.
cat "${CRONDIR}"/* | clean_cron_lines >>"${temp}"  # */ <not a comment>

# Add each user's crontab (if it exists). Insert the user's name between the
# five time fields and the command.
while read user ; do
    crontab -l -u "${user}" 2>/dev/null |
        clean_cron_lines |
        sed --regexp-extended "s/^((\S+ +){5})(.+)$/${user} /" >>"${temp}"
done < <(cut --fields=1 --delimiter=: /etc/passwd)

# Output the collected crontab lines. Replace the single spaces between the
# fields with tab characters, sort the lines by hour and minute, insert the
# header line, and format the results as a table.
cat "${temp}" |
    sed --regexp-extended "s/^(\S+) +(\S+) +(\S+) +(\S+) +(\S+) +(\S+) +(.*)$/\t\t\t\t\t\t/" |
    sort --numeric-sort --field-separator="${tab}" --key=2,1 |
    sed "1i\mi\th\td\tm\tw\tuser\tcommand" |
    column -s"${tab}" -t

rm --force "${temp}"

в Ubuntu или debian вы можете просмотреть crontab по /var/spool/cron/crontabs/ и выберите файл для каждого пользователя там. Это, конечно, только для конкретных пользователей crontab.

это покажет все записи crontab от всех пользователей.

sed 's/^\([^:]*\):.*$/crontab -u  -l 2>\&1/' /etc/passwd | grep -v "no crontab for" | sh

зависит от вашей версии Linux, но я использую:

tail -n 1000 /var/spool/cron/*

как root. Очень просто и очень коротко.

дает мне выходной, как:

==> /var/spool/cron/root <==
15 2 * * * /bla

==> /var/spool/cron/my_user <==
*/10 1 * * * /path/to/script

небольшое уточнение ответа Кайла Бертона с улучшенным форматированием вывода:

#!/bin/bash
for user in $(cut -f1 -d: /etc/passwd)
do echo $user && crontab -u $user -l
echo " "
done
getent passwd | cut -d: -f1 | perl -e'while(<>){chomp;$l = `crontab -u $_ -l 2>/dev/null`;print "$_\n$l\n" if $l}'

Это позволяет избежать возиться с passwd напрямую, пропускает пользователей, у которых нет записей cron, и для тех, у кого они есть, он выводит имя пользователя, а также их crontab.

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

Если вы проверяете кластер с помощью NIS, единственный способ увидеть, есть ли у пользователя запись crontab ist в соответствии с ответом Мэтта /var/spool/cron/tabs.

grep -v "#" -R  /var/spool/cron/tabs

Мне нравится простой однострочный ответ выше:

для пользователя в $(cut-f1-d: /etc/passwd); do crontab-u $user-l; done

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

for user in $(cut -f1 -d: /etc/passwd); do echo User:$user; crontab -l $user 2>&1 | grep -v crontab; done

вы получите список пользователей без ошибок, вызванных crontab, когда учетная запись не может использовать cron и т. д. Имейте в виду, что в Solaris роли могут быть также в /etc/passwd (см. / etc / user_attr).

этот скрипт работал для меня в CentOS, чтобы перечислить все кроны в среде:

sudo cat /etc/passwd | sed 's/^\([^:]*\):.*$/sudo crontab -u  -l 2>\&1/' | grep -v "no crontab for" | sh
for user in $(cut -f1 -d: /etc/passwd); 
do 
    echo $user; crontab -u $user -l; 
done

зависит от вашей версии cron. Используя Vixie cron на FreeBSD, я могу сделать что-то вроде этого:

(cd /var/cron/tabs && grep -vH ^# *) 

если я хочу, чтобы он был более разделен табуляцией, я мог бы сделать что-то вроде этого:

(cd /var/cron/tabs && grep -vH ^# * | sed "s/:/      /")

где это буквальная вкладка в части замены sed.

это может быть более независимым от системы, чтобы петля через пользователей в /etc/passwd и crontab -l -u $user для каждого из них.

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

обратите внимание на использование sudo во 2-й строке. Если вы уже корень, удалите это.

for USER in $(cut -f1 -d: /etc/passwd); do \
USERTAB="$(sudo crontab -u "$USER" -l 2>&1)";  \
FILTERED="$(echo "$USERTAB"| grep -vE '^#|^$|no crontab for|cannot use this program')";  \
if ! test -z "$FILTERED"; then  \
echo "# ------ $(tput bold)$USER$(tput sgr0) ------";  \
echo "$FILTERED";  \
echo "";  \
fi;  \
done

пример:

# ------ root ------
0 */6 * * * /usr/local/bin/disk-space-notify.sh
45 3 * * * /opt/mysql-backups/mysql-backups.sh
5 7 * * * /usr/local/bin/certbot-auto renew --quiet --no-self-upgrade

# ------ sammy ------
55 * * * * wget -O - -q -t 1 https://www.example.com/cron.php > /dev/null

Я использую это на Ubuntu (12 до 16) и Red Hat (5 до 7).

Спасибо за этот очень полезный скрипт. У меня были небольшие проблемы с запуском его на старых системах (Red Hat Enterprise 3, которые обрабатывают по-разному egrep и вкладки в строках) и других системах без ничего в /etc/cron.d / (скрипт тогда закончился с ошибкой). Так вот патч, чтобы заставить его работать в таких случаях :

2a3,4
> #See:  http://stackoverflow.com/questions/134906/how-do-i-list-all-cron-jobs-for-all-users
>
27c29,30
<         match=$(echo "${line}" | egrep -o 'run-parts (-{1,2}\S+ )*\S+')
---
>         #match=$(echo "${line}" | egrep -o 'run-parts (-{1,2}\S+ )*\S+')
>         match=$(echo "${line}" | egrep -o 'run-parts.*')
51c54,57
< cat "${CRONDIR}"/* | clean_cron_lines >>"${temp}"  # */ <not a comment>
---
> sys_cron_num=$(ls /etc/cron.d | wc -l | awk '{print }')
> if [ "$sys_cron_num" != 0 ]; then
>       cat "${CRONDIR}"/* | clean_cron_lines >>"${temp}"  # */ <not a comment>
> fi
67c73
<     sed "1i\mi\th\td\tm\tw\tuser\tcommand" |
---
>     sed "1i\mi${tab}h${tab}d${tab}m${tab}w${tab}user${tab}command" |

Я не совсем уверен, что изменения в первом egrep являются хорошей идеей, но хорошо,этот скрипт был протестирован на RHEL3,4, 5 и Debian5 без каких-либо проблем. Надеюсь, что это помогает!

здание на вершине @Kyle

for user in $(tail -n +11 /etc/passwd | cut -f1 -d:); do echo $user; crontab -u $user -l; done

чтобы избежать комментариев обычно в верхней части /etc / passwd,

и на macosx

for user in $(dscl . -list /users | cut -f1 -d:); do echo $user; crontab -u $user -l; done    

Я думаю, что лучше один лайнер будет ниже. Например, если у вас есть пользователи в NIS или LDAP, они не будут находиться в /etc/passwd. Это даст вам crontabs каждого пользователя, который вошел в систему.

for I in `lastlog | grep -v Never | cut -f1 -d' '`; do echo $I ; crontab -l -u $I ; done

вы можете написать для всего списка пользователей:

sudo crontab -u userName -l

,

вы также можете перейти к

cd /etc/cron.daily/
ls -l
cat filename

в этом файле будут перечислены расписания

cd /etc/cron.d/
ls -l
cat filename

так как речь идет о цикле через файл (/etc/passwd) и выполняя действие, я упускаю правильный подход на как я могу прочитать файл (поток данных, переменная) строка за строкой (и/или поле за полем)?:

while IFS=":" read -r user _
do
   echo "crontab for user ${user}:"
   crontab -u "$user" -l
done < /etc/passwd

это /etc/passwd построчно с помощью : в качестве разделителя полей. Говоря read -r user _, мы $user провести первое поле и _ остальное (это просто мусорная переменная, чтобы игнорировать поля).

таким образом, мы можем звоните crontab -u использование переменной $user, который мы цитируем для безопасности (что делать, если он содержит пробелы? Вряд ли в таком файле, но вы никогда не сможете узнать).

чтобы получить список от пользователя ROOT.

for user in $(cut -f1 -d: /etc/passwd); do echo $user; sudo crontab -u $user -l; done

на Solaris, для конкретного известного имени пользователя:

crontab -l username

все остальные * Nix понадобится -u модификатор:

crontab -u username -l

чтобы получить все задания пользователя сразу на Solaris, как и другие сообщения выше:

for user in $(cut -f1 -d: /etc/passwd); do crontab -l $user 2>/dev/null; done

для меня смотреть на /var / spool/cron/crontabs-это лучший способ

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

for user in $(cut -f1 -d: /etc/passwd); do 
  echo $user >> crontab.bak
  echo "" >> crontab.bak
  crontab -u $user -l >> crontab.bak 2>> > crontab.bak
done

Comments

    Ничего не найдено.