Wie liste ich alle Cron-Jobs für alle Benutzer auf?


858

Gibt es einen Befehl oder ein vorhandenes Skript, mit dem ich alle geplanten Cron-Jobs eines * NIX-Systems gleichzeitig anzeigen kann? Ich möchte es alle Benutzer crontabs enthalten, sowie /etc/crontab, und was ist in /etc/cron.d. Es wäre auch schön zu sehen, welche spezifischen Befehle von run-partsin ausgeführt werden /etc/crontab.

Idealerweise möchte ich die Ausgabe in einer schönen Spaltenform und auf sinnvolle Weise sortieren.

Ich könnte diese Einträge dann von mehreren Servern zusammenführen, um den gesamten "Zeitplan der Ereignisse" anzuzeigen.

Ich wollte gerade selbst ein solches Skript schreiben, aber wenn sich schon jemand die Mühe gemacht hat ...


Antworten:


1135

Sie müssten dies als root ausführen, aber:

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

wird jeden Benutzernamen durchlaufen, der die Crontab auflistet. Die Crontabs gehören den jeweiligen Benutzern, sodass Sie die Crontab eines anderen Benutzers nicht sehen können, ohne sie oder root zu sein.


Bearbeiten Sie, wenn Sie wissen möchten, zu welchem ​​Benutzer eine Crontab gehörtecho $user

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

54
Funktioniert nicht, wenn die Benutzer in NIS oder LDAP definiert sind. Sie müssen verwendenfor user in $(getent passwd | cut -f1 -d: ); do echo $user; crontab -u $user -l; done
Hubert Kario

10
Dies wurde aktualisiert, um Kommentare auszuschließen und Nachrichten "Keine Crontab für Benutzer ..." zu unterdrücken:for user in $(cut -f1 -d: /etc/passwd); do crontab -u $user -l 2>/dev/null | grep -v '^#'; done
Jonathan

38
Wäre es nicht einfacher, die Dateien in / var / spool / cron anzusehen?
Graywh

2
Wir uns LDAP und / etc / passwd müssen durch den Befehl getent ersetzt werden:for user in $(getent passwd | awk -F : '{print $1}'); do echo $user; crontab -u $user -l; done
Toby Batch

9
Was ist mit dem cronjobs in /etc/cron.hourly/, /etc/cron.daily/, /etc/cron.weekly/, /etc/cron.monthly/...?
Abdull

309

Am Ende habe ich ein Skript geschrieben (ich versuche mir die Feinheiten des Bash-Skripts beizubringen, deshalb sehen Sie hier so etwas wie Perl nicht). Es ist nicht gerade eine einfache Angelegenheit, aber es macht das meiste, was ich brauche. Es nutzt Kyle Vorschlag für einzelne Benutzer crontabs aufzublicken, sondern befasst sich auch mit /etc/crontab(einschließlich der Start - Skripte von run-partsin /etc/cron.hourly, /etc/cron.dailyusw.) und die Arbeitsplätze im /etc/cron.dVerzeichnis. Es nimmt all diese und führt sie zu einer Anzeige wie der folgenden zusammen:

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

Beachten Sie, dass es den Benutzer anzeigt und mehr oder weniger nach Stunde und Minute sortiert, damit ich den Tagesplan sehen kann.

Bisher habe ich es auf Ubuntu, Debian und Red Hat AS getestet.

#!/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})(.+)$/\1${user} \3/" >>"${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+) +(.*)$/\1\t\2\t\3\t\4\t\5\t\6\t\7/" |
    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}"

38
Nichts, aber es hat nichts gegen die System-Cron-Jobs in / etc / crontab und /etc/cron.d/ getan. Mit diesen umzugehen und alles am Ende zu formatieren, ist das, was mein Skript tut.
Yukondude

10
yukondude - du solltest darüber nachdenken, dies auf github zu setzen, auch nur als Kern.
Kyle Burton

3
Es wurde versucht, das Einfügen zu kopieren und auszuführen, aber es schlägt fehl: showcrons.sh: Zeile 59: Syntaxfehler in der Nähe des unerwarteten Tokens <' showcrons.sh: line 59: erledigt << (cut --fields = 1 --delimiter =: / etc / passwd) '
Fraggle

2
@ KyleBurton Es scheinen mindestens 8 Gists dies bereits zu kopieren, gist.github.com/gists/…
Zitrax

9
Warnung: In diesem Skript fehlen Ereignisse von/etc/anacrontab
ck_

191

Unter Ubuntu oder Debian können Sie crontab von anzeigen, /var/spool/cron/crontabs/und dann befindet sich dort eine Datei für jeden Benutzer. Das gilt natürlich nur für benutzerspezifische Crontab's.

Für Redhat 6/7 und Centos ist die Crontab unter /var/spool/cron/.


7
Dies funktioniert auch unter RedHat (/ var / spool / cron) und ist einfacher als das Schreiben / Ausführen eines Skripts, insbesondere wenn Sie zum Verwalten von Konten etwas wie Ldap verwenden. +1
user49913

6
Dies war für mich viel hilfreicher als jede andere Antwort. Mit dieser Methode können Sie die Crontabs von Benutzern anzeigen, die nicht mehr vorhanden sind, und ALLE Cron-Jobs erhalten, wie vom OP angefordert.
Andrew Ensley

1
Ein weiterer Vorteil dieser Methode: Mein Server verwendet LDAP, sodass die meisten Benutzer nicht angemeldet sind /etc/passwd. IMO sollte dies die akzeptierte Antwort sein und nicht alle Brute-Force-Lösungen.
Mikkel

1
Gut mit Suse Linux hier.
Bret

Thx, dies gilt auch für AWS EC2 instace, diese Info war sehr hilfreich!
Ivan Marjanovic

34

Dies zeigt alle Crontab-Einträge aller Benutzer an.

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

30

Hängt von deiner Linux-Version ab, aber ich benutze:

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

als Wurzel. Sehr einfach und sehr kurz.

Gibt mir Ausgabe wie:

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

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

4
Verwenden Sie tail -n +1 /var/spool/cron/*diese Option, um den gesamten Inhalt der Dateien aufzulisten.
Hans Ginzel

4
... oder sudo sh -c 'tail -n +1 /var/spool/cron/*'wenn du nicht root werden willst. Meine OCD zwang mich zu untersuchen, warum ich diesen Befehl nicht wie geschrieben ausführen konnte. Dies lag daran, dass reguläre Benutzer keinen Zugriff auf / var / spool / cron dir haben und der Glob als wörtliches Sternzeichen interpretiert wurde, das offensichtlich nicht existiert.
Dale Anderson

Alternativ cd /var/spool/cron/cron/ && grep . *wird auch der entsprechende Benutzername vor jedem Cron-Job
gedruckt


14
getent passwd | cut -d: -f1 | perl -e'while(<>){chomp;$l = `crontab -u $_ -l 2>/dev/null`;print "$_\n$l\n" if $l}'

Dadurch wird vermieden, dass Sie direkt mit passwd herumspielen, Benutzer überspringen, die keine Cron-Einträge haben, und für diejenigen, die sie haben, werden der Benutzername sowie deren Crontab ausgedruckt.

Meistens hier, damit ich es später finden kann, falls ich jemals wieder danach suchen muss.


1
Außerdem werden LDAP-Benutzer aufgelistet, die nicht in vorhanden sind /etc/passwd. Die obige Lösung von Matt ist für diese spezielle Situation besser geeignet, aber es ist gut zu wissen, dass der Befehl vorhanden ist.
Mikkel

11

Wenn Sie einen Cluster mit NIS überprüfen, können Sie nur anhand von Matts Antwort / var / spool / cron / tabs feststellen, ob ein Benutzer einen Crontab-Eintrag hat.

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

11

Um eine Liste vom ROOT-Benutzer zu erhalten.

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

10

Dieses Skript hat in CentOS für mich funktioniert, um alle Cron in der Umgebung aufzulisten:

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

2
Genial! Ich habe eine kleine Variation hinzugefügt, um zu sehen, unter welchem ​​Benutzer sich der Cron-Job befindet, und etwas Platz zwischen den Ergebnissen cat /etc/passwd | sed 's/^\([^:]*\):.*$/echo "\ncrontab for \1:"; sudo crontab -u \1 -l 2>\&1/' | grep -v "no crontab for" | sh
eingefügt

9

Ich mag die einfache Einzeiler-Antwort oben:

für Benutzer in $ (cut -f1 -d: / etc / passwd); do crontab -u $ user -l; erledigt

Solaris, das nicht über das Flag -u verfügt und den zu überprüfenden Benutzer nicht druckt, kann wie folgt geändert werden:

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

Sie erhalten eine Liste der Benutzer ohne die von crontab ausgelösten Fehler, wenn ein Konto cron usw. nicht verwenden darf. Beachten Sie, dass sich Rollen in Solaris auch in / etc / passwd befinden können (siehe / etc / user_attr).



Cool. Bis nicht zu verwenden.
Squarism


7

Im Folgenden werden Kommentare, Leerzeilen und Fehler von Benutzern ohne Crontab entfernt. Sie haben nur noch eine übersichtliche Liste der Benutzer und ihrer Jobs.

Beachten Sie die Verwendung von sudoin der 2. Zeile. Wenn Sie bereits root sind, entfernen Sie das.

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

Beispielausgabe:

# ------ 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

Ich benutze dies auf Ubuntu (12 bis 16) und Red Hat (5 bis 7).


5

Hängt von Ihrer Version von cron ab. Mit Vixie cron unter FreeBSD kann ich Folgendes tun:

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

Wenn ich möchte, dass mehr Tabs entfernt werden, kann ich Folgendes tun:

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

Wo das eine wörtliche Registerkarte im sed Ersatzteil ist.

Es kann systemunabhängiger sein, die Benutzer zu durchlaufen /etc/passwdund crontab -l -u $userfür jeden von ihnen zu tun .


4

Vielen Dank für dieses sehr nützliche Skript. Ich hatte einige winzige Probleme beim Ausführen auf alten Systemen (Red Hat Enterprise 3, die unterschiedliche egrep und Tabs in Zeichenfolgen verarbeiten) und anderen Systemen mit nichts in /etc/cron.d/ (das Skript endete dann mit einem Fehler). Hier ist ein Patch, mit dem es in solchen Fällen funktioniert:

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 $1}')
> 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" |

Ich bin mir nicht sicher, ob die Änderungen im ersten egrep eine gute Idee sind, aber dieses Skript wurde problemlos auf RHEL3,4,5 und Debian5 getestet. Hoffe das hilft!


3

Aufbauend auf @Kyle

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

um die Kommentare zu vermeiden, die normalerweise oben in / etc / passwd stehen,

Und auf Macosx

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

3
Solltest du dich nicht grep -v '^#auf eine magische Zahl verlassen 11?
11.

1
Red Hat / CentOS-Distributionen schreiben nicht die hilfreichen Hinweise zu Beginn der Crontab eines Benutzers. Wenn Sie also die ersten 11 Zeilen abschneiden, wird der Inhalt gelöscht. Das Gleiche gilt, wenn ein Ubuntu-Benutzer seine eigene Crontab bearbeitet und alle Handgriffe entfernt hat.
Dale Anderson



3

Sie können für alle Benutzerlisten schreiben:

sudo crontab -u userName -l

,

Sie können auch gehen

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

Diese Datei listet die Zeitpläne auf

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

3

Mit Entschuldigung und Dank an Yukondude.

Ich habe versucht, die Timing-Einstellungen für ein einfaches Lesen zusammenzufassen, obwohl es kein perfekter Job ist, und ich berühre nicht "jeden Freitag" oder "nur montags".

Dies ist Version 10 - jetzt:

  • läuft viel viel schneller
  • verfügt über optionale Fortschrittszeichen, sodass Sie die Geschwindigkeit weiter verbessern können.
  • verwendet eine Trennlinie, um Header und Ausgabe zu trennen.
  • Ausgaben in einem kompakten Format, wenn alle Zeitintervalle zusammengefasst sind.
  • Akzeptiert Jan ... Dec-Deskriptoren für Monate des Jahres
  • Akzeptiert Mon ... Sun-Deskriptoren für Wochentage
  • versucht, das Debian-up von Anacron im Debian-Stil zu handhaben, wenn es fehlt
  • versucht, mit Crontab-Zeilen umzugehen, die eine Datei ausführen, nachdem die Ausführbarkeit mit "[-x ...]" vorab getestet wurde.
  • versucht, mit Crontab-Zeilen umzugehen, die eine Datei ausführen, nachdem die Ausführbarkeit mit "Befehl -v" vorab getestet wurde.
  • ermöglicht die Verwendung von Intervallbereichen und Listen.
  • unterstützt die Verwendung von Run-Parts in benutzerspezifischen / var / spool-Crontab-Dateien.

Ich veröffentliche das Skript jetzt vollständig hier.

https://gist.github.com/myshkin-uk/d667116d3e2d689f23f18f6cd3c71107


2

Da es darum geht, eine Datei ( /etc/passwd) zu durchlaufen und eine Aktion auszuführen, fehlt mir der richtige Ansatz, wie ich eine Datei (Datenstrom, Variable) Zeile für Zeile (und / oder Feld für Feld) lesen kann )? ::

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

Dies liest /etc/passwdZeile für Zeile unter Verwendung :als Feldtrennzeichen. Indem read -r user _wir sagen , $userhalten wir das erste Feld und _den Rest fest (es ist nur eine Junk-Variable, um Felder zu ignorieren).

Auf diese Weise können wir dann crontab -udie Variable aufrufen $user, die wir aus Sicherheitsgründen zitieren (was ist, wenn sie Leerzeichen enthält? In einer solchen Datei ist dies unwahrscheinlich, aber Sie können es nie erfahren).


1

Unter Solaris für einen bestimmten bekannten Benutzernamen:

crontab -l username

Alle anderen * Nix benötigen -uModifikator:

crontab -u username -l

So erhalten Sie alle Jobs eines Benutzers gleichzeitig in Solaris, ähnlich wie in anderen oben genannten Beiträgen:

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

-1

Für mich ist ein Blick auf / var / spool / cron / crontabs der beste Weg


2
Dies wurde vor
Bummi

-2

Dieses Skript gibt die Crontab in eine Datei aus und listet auch alle Benutzer auf, die diejenigen bestätigen, die keinen Crontab-Eintrag haben:

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

//, RobFrost, sind Sie sicher, dass dieses Skript, wie hier geschrieben, konsistent funktioniert?
Nathan Basanese

Siehe Warum Sie keine Zeilen mit "für" lesen . Auch dies wurde viele Male beantwortet, bevor Sie dieses gepostet haben.
Fedorqui 'SO hör auf zu schaden'
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.