Skip to main content

tail — Monitor and Extract the End of Files

Overview

tail prints the end of a file—by default the last 10 lines. It’s a first-choice command for log debugging because errors usually appear at the bottom of logs and because tail can keep watching a file as it grows.

Tool Snapshot
  • Core Function: Output the last part of files (lines or bytes).
  • Primary Benefit: Fast log triage + real-time monitoring.
  • Where to Use: /var/log/nginx/error.log, /var/log/syslog, PHP-FPM logs, WordPress plugin/theme logs.
  • Workflow: tail [OPTION]... [FILE]... (optionally -f / -F for live follow).

System Check

which tail # Expected: /usr/bin/tail
tail --version # Expected: GNU coreutils version output
Rotation awareness

Many logs rotate (e.g., error.logerror.log.1 and a new error.log is created). Use -F when you expect rotation.

Core Syntax

tail [OPTION]... [FILE]...

If FILE is omitted, tail reads from stdin, which is useful in pipelines.

Two important “starting point” forms

  • Last N lines (default): tail -n 10 file
  • Start from line N: tail -n +N file (starts at line N and prints to end)

Options & Flags

OptionWhat it doesWhen you’d use itExample
:-:--:--:--
(none)Last 10 linesQuick glancetail file.log
-n NLast N linesIncrease/decrease outputtail -n 50 error.log
-n +NStart at line N to endSkip headers / resume readingtail -n +200 file.txt
-fFollow appended dataLive debuggingtail -f error.log
-FFollow by name + retrySurvive log rotationtail -F error.log
--retryKeep trying if file missingService logs that appear latertail -f --retry file.log
--pid=PIDStop when process diesTie follow to a processtail -f --pid=1234 error.log
-c NLast N bytesBinary-ish / byte-level checkstail -c 200 file
-qQuiet (no headers)Multiple files output cleanlytail -q a.log b.log
-vAlways print headersMultiple files claritytail -v a.log b.log
--helpHelpReferencetail --help
Large logs

If you follow a very noisy log with tail -f, it can scroll fast and be hard to read. Consider filtering with grep, or use a pager for static views.

Common Patterns

tail /var/log/nginx/error.log
tail -n 50 /var/log/nginx/error.log
tail -n 200 /var/log/syslog

Best Practices

  • Prefer -F for long-running monitoring on production servers (handles rotation):

    tail -F /var/log/nginx/error.log
  • Start with tail -n 50 or -n 200 to get context before going live.

  • Combine with filters for signal:

    tail -F /var/log/nginx/error.log | grep -i "timeout"
  • When investigating a specific incident time window, consider pairing with grep first:

    grep -n "2026-02-17" /var/log/nginx/error.log | tail -n 50
  • For scripts, avoid follow mode unless you manage lifecycle (timeouts / --pid):

    tail -f --pid=1234 /var/log/nginx/error.log
-f vs -F — what’s the difference?
  • tail -f file: follows the current file descriptor. If the file is rotated and replaced, you may keep following the old file.
  • tail -F file: follows the filename and will reopen it if it’s rotated/recreated. This is typically better for server logs.

Troubleshooting

ProblemLikely CauseFix
:--:--:--
No new lines appear in -fService isn’t writing or log path is wrongConfirm path; check service status; try ls -l and permissions
Follow stops after rotationYou used -fUse -F for rotated logs
Permission deniedLog restricted to rootUse sudo tail ...
Output too noisyHigh traffic or verbose logsFilter with grep or increase specificity
Lines are truncated/weirdNon-text/binary contentUse -c to inspect bytes or view with safer tools
Be careful with sensitive logs

WordPress configs and logs may contain secrets (DB host, usernames, tokens). Avoid copying raw output into tickets/chats without redaction.

Cheat Sheet

tail file.log # Last 10 lines
tail -n 50 file.log # Last 50 lines
tail -n +200 file.log # From line 200 to end
tail -f file.log # Follow new lines (may break on rotation)
tail -F file.log # Follow by name (handles rotation)
tail -c 200 file # Last 200 bytes
tail -v -n 20 a.log b.log # Show headers for multiple files
tail -q -n 20 a.log b.log # Quiet headers for multiple files
tail -F file.log | grep error # Follow + filter

Mini Quiz

  1. What does tail show by default?
  2. What’s the difference between tail -f and tail -F?
  3. How do you show the last 200 lines of a file?
  4. How do you start printing from line 500 to the end?
  5. How would you follow Nginx errors and only show “timeout” lines?
Show answers
  1. The last 10 lines of a file.
  2. -f follows the current file; -F follows the filename and reopens after rotation.
  3. tail -n 200 file
  4. tail -n +500 file
  5. tail -F /var/log/nginx/error.log | grep -i "timeout"

Worked Examples

About expected output

Log content varies by server. Outputs below are representative examples.

1) View the last 10 lines of Nginx error log

tail /var/log/nginx/error.log

Expected output (sample):

2026/02/17 10:20:11 [error] 1234#1234: *991 connect() failed (111: Connection refused) while connecting to upstream
2026/02/17 10:21:03 [warn] 1234#1234: *1001 upstream response is buffered to a temporary file
...

Use case: Quick glance at the latest errors.

2) Get more context (last 50 lines)

tail -n 50 /var/log/nginx/error.log

Expected output: (last 50 lines printed) Use case: Understand what led up to the latest error.

3) Follow Nginx error log live

tail -f /var/log/nginx/error.log

Expected output: (prints new lines as they appear) Use case: Live debugging while reproducing an issue in browser.

4) Follow Nginx error log and survive rotation

tail -F /var/log/nginx/error.log

Expected output: (continues following even after log rotation) Use case: Long-running monitoring sessions.

5) Follow and filter only error lines (case-insensitive)

tail -F /var/log/nginx/error.log | grep -i "error"

Expected output (sample):

2026/02/17 10:20:11 [error] 1234#1234: *991 connect() failed (111: Connection refused) while connecting to upstream

Use case: Reduce noise while monitoring.

6) Watch WordPress debug log (if enabled)

tail -n 80 /var/www/html/wp-content/debug.log

Expected output (sample):

[17-Feb-2026 10:33:09 UTC] PHP Warning: Undefined array key "foo" in /var/www/html/wp-content/plugins/example/plugin.php on line 88
[17-Feb-2026 10:34:01 UTC] PHP Fatal error: Uncaught Error: Call to undefined function ...

Use case: Plugin/theme debugging.

7) Follow WordPress debug log live

tail -F /var/www/html/wp-content/debug.log

Expected output: (prints new PHP notices/warnings as they occur) Use case: Reproduce issues and see immediate log output.

8) Show the last 200 lines of syslog

tail -n 200 /var/log/syslog

Expected output: (last 200 syslog lines) Use case: System-level context during incidents.

9) Start from a specific line number

tail -n +500 /var/log/nginx/access.log

Expected output: (prints from line 500 to end) Use case: Resume reading from a known checkpoint.

10) Compare last lines of two logs with headers

tail -v -n 10 /var/log/nginx/access.log /var/log/nginx/error.log

Expected output (sample):

==> /var/log/nginx/access.log <==
192.168.0.10 - - [17/Feb/2026:10:40:01 +0000] "GET / HTTP/1.1" 200 512 "-" "Mozilla/5.0"

==> /var/log/nginx/error.log <==
2026/02/17 10:40:02 [warn] 1234#1234: *1201 upstream response is buffered to a temporary file

Use case: Correlate traffic with errors.

11) Get the last 200 bytes (byte-level view)

tail -c 200 /var/www/html/wp-config.php

Expected output: (last 200 bytes of the file) Use case: Quick check for suspicious appended content.

12) Follow and stop when a process exits (--pid)

tail -f --pid=1234 /var/log/nginx/error.log

Expected output: (follows until PID 1234 exits) Use case: Tied debugging to a short-lived process.

13) Follow a log that may not exist yet (--retry)

tail -f --retry /var/log/myapp/app.log

Expected output: (keeps trying until file appears, then follows) Use case: Services that create logs after startup.

14) Follow and filter for timeouts (common VPS issue)

tail -F /var/log/nginx/error.log | grep -i "timeout"

Expected output (sample):

2026/02/17 11:02:44 [error] 1234#1234: *1401 upstream timed out (110: Connection timed out) while reading response header from upstream

Use case: Detect upstream/PHP-FPM timeout symptoms.

15) Follow PHP-FPM log live (path may vary)

tail -F /var/log/php8.2-fpm.log

Expected output: (new PHP-FPM notices/warnings) Use case: Investigate slow requests, worker issues, pool errors.