Skip to content
DevOps devops linux 5 min read

Viewing File Contents

On a Linux server you spend a huge amount of time just reading files: config files, log files, scripts, and plain text. You usually do not want to open a text editor for that, because you only want to look, not change anything. Ubuntu ships with a handful of small, fast commands built exactly for reading: cat, less, head, and tail. Learning when to reach for each one is one of the most practical Linux skills there is, especially tail -f, which lets you watch a log file update live while you debug a running service.

Why not just open an editor?

When you are administering a server (Ubuntu 22.04 or 24.04 LTS), opening every file in a text editor (a program for changing files, like nano or vim) is slow and risky. You might accidentally edit a production config. The viewing commands below are read-only: they print the file to your terminal and never touch the original. That makes them safe to run on anything, including system files you should not modify by hand.

These commands also work beautifully with pipes (the | symbol, which sends one command’s output into another command). For example, you can filter a huge log down to the lines you care about. We will show a few of those combinations as we go.

cat — print a whole file

cat (short for “concatenate”) dumps the entire contents of a file straight to your screen. It is perfect for short files.

cat /etc/hostname

Output:

web-prod-01

You can print several files at once, and cat -n numbers every line, which is handy when an error message references a line number.

cat -n /etc/timezone

Output:

     1	Etc/UTC

When to use cat: short files you want to see all at once (a 5-line config, a small script). When NOT to: large files. Running cat /var/log/syslog will flood your terminal with thousands of lines that scroll past faster than you can read. For anything big, use less.

less — scroll through big files

less opens a file in a scrollable, searchable viewer without loading the whole thing into memory, so it stays fast even on multi-gigabyte logs. It is the right default for any file you are not sure about.

less /var/log/syslog

This opens an interactive screen. Inside less you control it with the keyboard:

KeyWhat it does
Space / fPage down
bPage up
Arrow keysMove one line at a time
/wordSearch forward for “word”
n / NNext / previous search match
GJump to the end of the file
gJump to the start of the file
qQuit and return to the shell

Tip: less +F /var/log/syslog starts in “follow” mode (like tail -f below) but lets you press Ctrl-C to stop following and scroll back through history, then F to resume. It is the best of both worlds for log spelunking.

When to use less: any large file, or when you need to search inside it. The older more command does something similar but only scrolls forward — less is strictly better (hence the joke “less is more”).

head — the first lines

head prints only the start of a file. By default it shows the first 10 lines. Use -n to ask for a specific number.

head -n 5 /etc/passwd

Output:

root:x:0:0:root:/root:/bin/bash
daemon:x:1:1:daemon:/usr/sbin:/usr/sbin/nologin
bin:x:2:2:bin:/bin:/usr/sbin/nologin
sys:x:3:3:sys:/dev:/usr/sbin/nologin
sync:x:4:65534:sync:/bin:/bin/sync

When to use head: checking a file’s header (like a CSV column row), or peeking at the top of a file without printing the whole thing.

tail — the last lines

tail is the mirror image of head: it prints the end of a file, the last 10 lines by default. This is what you want for logs, because the newest events are always written at the bottom.

tail -n 20 /var/log/auth.log

Output:

2026-06-15T09:12:44.103Z web-prod-01 sshd[2041]: Accepted publickey for deploy from 203.0.113.9 port 50122 ssh2
2026-06-15T09:12:44.110Z web-prod-01 sshd[2041]: pam_unix(sshd:session): session opened for user deploy(uid=1000)
2026-06-15T09:13:02.555Z web-prod-01 sudo:   deploy : TTY=pts/0 ; PWD=/home/deploy ; USER=root ; COMMAND=/usr/bin/systemctl restart nginx

tail -f — watch a log live

The single most useful flag in this whole page is -f (“follow”). tail -f prints the end of the file and then keeps the command running, printing new lines the instant they are written. When you restart a service and want to see what happens in real time, this is the tool.

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

Output:

2026/06/15 09:20:01 [error] 1502#1502: *88 connect() failed (111: Connection refused) while connecting to upstream, client: 198.51.100.4, server: example.com, request: "GET /api/health HTTP/1.1", upstream: "http://127.0.0.1:3000/"

Leave it open in one terminal, then trigger the bug (reload the page, hit the API) in another, and watch the error appear live. Press Ctrl-C to stop following.

You can follow several logs at once and even filter as they stream:

sudo tail -f /var/log/nginx/access.log | grep " 500 "

This shows only requests that returned a 500 (server error) status as they happen.

Gotcha: some Ubuntu services (anything using systemd) write logs to the journal, not to a plain file, so tail -f on /var/log may show nothing. For those, use journalctl -u nginx -f, which is the systemd equivalent of tail -f for a single service.

Quick comparison

CommandShowsBest forStays open?
catWhole fileShort files, pipingNo
lessScrollable viewLarge files, searchingYes (interactive)
headFirst N linesFile headers, top peekNo
tailLast N linesRecent log entriesNo
tail -fLast lines + live updatesDebugging running servicesYes (follows)

Best Practices

  • Default to less when you are unsure of a file’s size — it never floods your terminal.
  • Keep a tail -f of the relevant log open in a spare terminal whenever you restart or deploy a service, so you catch errors the moment they appear.
  • Use journalctl -u <service> -f instead of tail -f for systemd-managed services like nginx, ssh, or postgresql.
  • Combine these tools with grep via pipes (tail -f app.log | grep ERROR) to cut noise down to only what matters.
  • Use sudo for protected logs in /var/log (most auth and service logs need it), but never use sudo with an editor just to read — viewing is enough.
  • Prefer head -n and tail -n over cat for big files so you only pull the slice you need.
Last updated June 15, 2026
Was this helpful?