Der Befehl tail zeigt das Ende einer Datei an — voreingestellt die letzten zehn Zeilen. Sein eigentlicher Wert liegt aber im Live-Modus mit -f: Damit verfolgst du Logs in Echtzeit, während sie geschrieben werden. Ergänzt um -F für Logrotation und das oft missverstandene +N für „ab Zeile N” ist tail eines der nützlichsten Werkzeuge im Server- und Debugging-Alltag.
Was tail macht
Ohne Optionen liefert tail die letzten zehn Zeilen einer Datei zurück und beendet sich. Das macht ihn zum natürlichen Gegenstück zu head und zum schnellen Werkzeug, um zu sehen, was zuletzt in eine Datei geschrieben wurde — etwa die jüngsten Einträge in einer Logdatei oder die neuesten Zeilen einer CSV.
tail /var/log/syslogDas eigentliche Killer-Feature ist aber -f (für „follow”): Damit bleibt tail nach der Ausgabe am Dateiende stehen und gibt jede neue Zeile aus, sobald sie angehängt wird. Genau dieser Modus macht tail zum Standardwerkzeug für Live-Log-Beobachtung auf Servern.
Optionen
| Option | Wirkung |
|---|---|
-n N | Zeigt die letzten N Zeilen (Default: 10) |
-n +N | Zeigt ab Zeile N bis zum Ende (umgekehrtes Verhalten) |
-c N | Zeigt die letzten N Bytes statt Zeilen |
-f | Folgt der Datei live, gibt neue Zeilen aus, sobald sie geschrieben werden |
-F | Wie -f, aber robust gegen Logrotation (= --follow=name --retry) |
--retry | Versucht erneut zu öffnen, wenn die Datei (noch) nicht existiert |
-q, --quiet | Unterdrückt Header bei mehreren Dateien |
-v, --verbose | Zeigt Header immer an, auch bei einer einzelnen Datei |
--pid=PID | Beendet tail -f automatisch, wenn der Prozess PID endet |
-s SEC | Wartezeit zwischen Polls bei -f (z. B. -s 5) |
---disable-inotify | Erzwingt Polling statt inotify (z. B. auf NFS-Mounts) |
+N ist invertiert
Hier liegt eine der häufigsten Stolperfallen: tail -n 10 zeigt die letzten zehn Zeilen — tail -n +10 dagegen zeigt ab Zeile zehn bis zum Ende der Datei. Das Plus dreht die Bedeutung also komplett um.
tail -n +2 daten.csv1,Alice,42
2,Bob,37
3,Carla,29Das ist der klassische Trick, um die erste Zeile (typischerweise eine CSV-Header-Zeile) wegzuwerfen und nur die Datenzeilen weiterzuverarbeiten — etwa in einer Pipe an awk, cut oder sort.
-f Live-Follow
Mit -f bleibt tail nach der Ausgabe der letzten Zeilen aktiv und gibt jede neu angehängte Zeile sofort aus. Das ist die Standardmethode, um eine Logdatei live zu beobachten, während ein Dienst läuft.
tail -f /var/log/syslogBeendet wird der Modus mit Ctrl+C. Auf modernen Linux-Systemen verwendet tail -f intern inotify, um vom Kernel benachrichtigt zu werden, sobald die Datei wächst — das ist effizient und reagiert ohne Verzögerung. Auf Netzwerk-Dateisystemen wie NFS funktioniert inotify nicht zuverlässig; dort fällt tail automatisch auf Polling zurück (oder du erzwingst es mit ---disable-inotify).
-F für rotierte Logs
tail -f folgt einem File-Deskriptor, nicht einem Dateinamen. Wenn ein Logrotation-Tool wie logrotate die Datei umbenennt (access.log → access.log.1) und eine neue, leere Datei am alten Pfad anlegt, schreibt der Dienst weiter in die alte (umbenannte) Datei. tail -f bleibt an dieser umbenannten Datei hängen — und du siehst nichts mehr, was in die neue Datei geschrieben wird.
Die Lösung ist -F (großes F):
tail -F /var/log/nginx/access.log-F ist eine Kurzform für --follow=name --retry. Damit folgt tail dem Dateinamen statt dem File-Deskriptor und öffnet die Datei erneut, sobald sie nach einer Rotation am alten Pfad wieder existiert. Auf Servern, auf denen Logrotation aktiv ist, ist -F praktisch immer die richtige Wahl.
Mehrere Dateien gleichzeitig
tail akzeptiert beliebig viele Dateien als Argumente und setzt vor jedem Block einen Header mit dem Dateinamen. Im -f-Modus erscheint der Header immer dann, wenn tail die Quelle wechselt — also wenn eine andere Datei als zuletzt eine neue Zeile bekommt.
tail -f /var/log/nginx/access.log /var/log/nginx/error.log==> /var/log/nginx/access.log <==
192.0.2.10 - - [04/May/2026:14:02:11 +0000] "GET / HTTP/1.1" 200 1024
==> /var/log/nginx/error.log <==
2026/05/04 14:02:13 [error] 1234#0: *1 open() failedDas ist nützlich für eine schnelle Doppelsicht — etwa Access- und Error-Log gleichzeitig. Wer dauerhaft mehrere Logs in mehreren Panes nebeneinander beobachten will, ist allerdings mit multitail oder tmux plus mehreren tail -F-Aufrufen besser bedient.
Praxis-Patterns
Live-Logs verfolgen — der Klassiker auf jedem Server:
tail -F /var/log/nginx/access.log-F (großes F) folgt dem Dateinamen statt dem File-Deskriptor und überlebt damit eine Logrotation, ohne dass du den Befehl neu starten musst. Auf Produktiv-Servern ist das praktisch immer die richtige Wahl.
Letzte Zeilen filtern — die letzten 100 Zeilen einer Logdatei nach Fehlern durchsuchen:
tail -n 100 /var/log/syslog | grep ERRORtail schneidet zuerst auf ein überschaubares Fenster zu, grep filtert anschließend — so bleibt der Aufruf billig, auch wenn die Logdatei mehrere Gigabyte groß ist.
CSV-Header überspringen — alle Zeilen ab Zeile 2 weitergeben:
tail -n +2 daten.csv | sort -t, -k3 -n-n +2 startet ab Zeile 2 und lässt damit die Header-Zeile weg, sodass sort nicht über die Spaltenüberschriften stolpert. Ohne diesen Schritt würde der String-Header je nach Sortierung mitten im Datensatz landen.
Live-Filter — tail -f mit grep kombinieren, um nur bestimmte Einträge live zu sehen:
tail -F /var/log/nginx/access.log | grep --line-buffered " 500 "Der --line-buffered-Schalter bei grep ist hier wichtig: Ohne ihn puffert grep blockweise und du siehst die gefilterten Zeilen erst stark verzögert.
Bis Prozessende folgen — tail automatisch beenden, wenn ein anderer Prozess endet:
tail -f --pid=$$ logfile.log$$ ist die PID der aktuellen Shell — sobald die Shell endet, beendet sich auch das tail. Praktisch in Skripten oder temporären Sessions, damit kein verwaistes tail-Prozess hängenbleibt.
Häufige Stolperfallen
tail -f bricht bei Logrotation ab — nimm tail -F.
Wenn logrotate oder ein vergleichbares Tool die Logdatei umbenennt und am alten Pfad eine neue anlegt, folgt tail -f stur dem alten File-Deskriptor und sieht keine neuen Einträge mehr. tail -F (großes F) folgt stattdessen dem Dateinamen und öffnet die Datei nach einer Rotation automatisch neu. Auf Produktiv-Servern mit aktiver Logrotation ist -F praktisch immer die richtige Wahl — und kostet nichts.
tail -n +N ist invertiertes Verhalten.
Das Plus in -n +N dreht die Bedeutung um: tail -n 10 zeigt die letzten 10 Zeilen, tail -n +10 dagegen zeigt ab Zeile 10 bis zum Ende der Datei. Das überrascht selbst erfahrene Linux-Nutzer regelmäßig. Der typische Anwendungsfall ist tail -n +2 datei.csv, um die erste Zeile (CSV-Header) zu überspringen, bevor die Daten in eine Pipe gehen.
tail -f | grep puffert blockweise — line-buffered fehlt oft.
In einer Pipe wie tail -f log | grep ERROR wechselt grep automatisch in den blockgepufferten Modus und gibt erst alle paar Kilobyte etwas aus. Bei langsam wachsenden Logs sieht man die gefilterten Treffer dann mit großer Verzögerung — oder gar nicht, bis der Buffer voll ist. Abhilfe: grep —line-buffered erzwingt zeilenweise Ausgabe. Bei awk hilft analog fflush(), bei sed die Option -u (unbuffered).
inotify funktioniert nicht auf NFS und einigen FUSE-Mounts.
tail -f nutzt auf modernen Linux-Systemen inotify, um vom Kernel sofort über Datei-Änderungen informiert zu werden — sehr effizient und reaktionsschnell. Auf NFS-Mounts oder einigen FUSE-Dateisystemen funktioniert inotify aber nicht zuverlässig, weil Änderungen auf einem anderen Host stattfinden. tail fällt zwar in vielen Fällen auf Polling zurück, aber nicht immer transparent. Mit ---disable-inotify erzwingst du explizit Polling, optional in Verbindung mit -s SEC.
Mehrere -f-Dateien werden schnell unübersichtlich.
tail -f file1 file2 file3 ist verlockend, aber im Live-Betrieb verwirrend: Die Header-Zeilen erscheinen zwischen den Log-Einträgen verstreut, und bei drei oder mehr aktiven Logs verliert man den Überblick, welche Zeile aus welcher Datei kommt. Für ernstes Mehr-Datei-Monitoring sind Werkzeuge wie multitail (mit eigenen Panes pro Datei) oder ein tmux-Setup mit mehreren tail -F-Sessions die deutlich angenehmere Lösung.
tail beendet sich frühzeitig durch SIGPIPE.
Wenn der Empfänger einer Pipe (etwa head oder ein anderes Programm dahinter) seine Eingabe schließt, bekommt tail beim nächsten Schreibversuch ein SIGPIPE-Signal und beendet sich — auch im -f-Modus. Das ist kein Bug, sondern Unix-Standardverhalten, kann aber überraschen, wenn man eine lange Live-Pipeline aufbaut und der hintere Teil unerwartet endet. Mit trap ” PIPE in einem Shell-Skript oder einem expliziten Schreib-in-Datei-Schritt lässt sich das Verhalten beeinflussen.
Weiterführende Ressourcen
Externe Quellen
- tail(1) – Linux manual page (man7.org) — offizielle Dokumentation aller tail-Optionen
- GNU Coreutils Manual: tail invocation — ausführliche Beschreibung im GNU-Handbuch, inklusive
-fund-F - Arch Wiki: System log — Übersicht über Logdateien, Logrotation und Werkzeuge zur Auswertung
- multitail – mehrere Logs in Panes — Alternative für komplexere Mehr-Datei-Beobachtung
Verwandte Artikel
- head – Erste Zeilen einer Datei anzeigen — das Gegenstück zu tail
- cat – Dateien ausgeben und verbinden — vollständige Ausgabe statt nur des Endes
- cut – Spalten aus Text extrahieren — gezielte Spaltenauswahl in Pipelines mit tail
- Streams und Pipes — wie tail in Pipelines mit grep, awk und Co. zusammenspielt
- Manpages – Hilfe auf der Kommandozeile — so liest du
man tailund verwandte Hilfeseiten