Skip to content
DevOps devops linux 5 min read

Command History & Shortcuts

When you administer a Linux server, you spend most of your day typing commands into a shell (the program that reads your typed commands and runs them; on Ubuntu the default shell is Bash, short for “Bourne Again SHell”). The difference between a slow engineer and a fast one is rarely talent — it is muscle memory for a handful of small tricks. This page covers command history, the !! shortcut, reverse search with Ctrl+R, tab completion, and the editing keyboard shortcuts every Bash user should know. None of these are hard, and together they save you hours every week.

Command history

Bash remembers the commands you type. That list is your history. Run the history command to see it:

history

Output:

  496  cd /etc/nginx/sites-available
  497  sudo nano default
  498  sudo nginx -t
  499  sudo systemctl reload nginx
  500  history

Each line has a number you can reuse. The history is kept in memory during your session and written to a file called ~/.bash_history when you log out (the ~ means your home directory, e.g. /home/ubuntu).

To re-run a command by its number, type ! followed by the number:

!498

That re-runs sudo nginx -t. To run the most recent command that started with some text, use ! plus that text:

!sudo

This re-runs the last command beginning with sudo. Be careful — it runs immediately. To preview it first, add :p (print) so Bash shows the command without executing it:

!sudo:p

Searching history with grep

Your history can hold thousands of entries. To find a specific old command, pipe history into grep (a tool that filters lines matching a pattern):

history | grep systemctl

Output:

  461  sudo systemctl restart postgresql
  499  sudo systemctl reload nginx
  503  sudo systemctl status ufw

Repeating the last command with !!

!! (two exclamation marks) means “the entire previous command”. Its most common use is when you forget sudo (the command that runs something as the administrator). Instead of retyping the whole line:

apt update

Output:

Reading package lists... Done
E: Could not open lock file /var/lib/apt/lists/lock - open (13: Permission denied)

Just prefix !! with sudo:

sudo !!

Bash expands !! to apt update, so it runs sudo apt update. You can also reuse just the last argument of the previous command with !$. This is handy when you create a file and then act on it:

sudo nano /etc/nginx/sites-available/myapp
sudo ln -s !$ /etc/nginx/sites-enabled/

Here !$ becomes /etc/nginx/sites-available/myapp.

Gotcha: !! and !sudo run instantly with no confirmation. Never blindly chain history expansion into destructive commands like rm or sudo. When in doubt, add :p to print first, or press the Up arrow to load the command into your prompt so you can read it before hitting Enter.

Reverse search with Ctrl+R

Pressing the Up arrow walks back through history one line at a time, which is slow if the command was 30 entries ago. Ctrl+R (hold Ctrl, press R) opens an interactive reverse search: you type part of a command and Bash finds the most recent match as you type.

  1. Press Ctrl+R. The prompt changes to (reverse-i-search).
  2. Start typing, e.g. nginx.
  3. Bash shows the latest match. Press Ctrl+R again to step to older matches.
  4. Press Enter to run it, or the Right arrow (or Tab) to edit it first.
  5. Press Ctrl+G to cancel and keep your prompt empty.
(reverse-i-search)`nginx': sudo systemctl reload nginx

Ctrl+R is the single biggest time-saver in this list. Once it is muscle memory, you will rarely retype a long command again.

Tab completion

Press Tab and Bash tries to finish what you are typing — file names, directory names, and command names. Type a few letters and press Tab:

cd /etc/ng

Press Tab and it completes to /etc/nginx/. If more than one option matches, press Tab twice to list them all:

systemctl res

Output:

reset-failed  restart  resume

On Ubuntu 22.04/24.04, the bash-completion package adds smart completion for many tools — for example systemctl <Tab> lists subcommands and even service names. It is installed by default, but if completion seems limited, install it and reopen your terminal:

sudo apt install bash-completion

When to use it: always. Tab completion is also a safety net — if a path does not complete, you typed it wrong, catching typos before they cause errors.

Keyboard shortcuts

Bash uses Emacs-style key bindings by default for editing the current line. These work whether the line is empty or half-typed.

ShortcutWhat it doesWhen to use
Ctrl+CCancel the current command / kill the running programStop a hung command or abandon a half-typed line
Ctrl+AJump to the start of the lineAdd sudo before a long command
Ctrl+EJump to the end of the lineContinue editing after fixing the start
Ctrl+LClear the screen (same as clear)Tidy a cluttered terminal without losing history
Ctrl+UDelete from cursor to start of lineWipe a wrong command and start over
Ctrl+KDelete from cursor to end of lineTrim a trailing mistake
Ctrl+WDelete the word before the cursorFix one wrong argument
Ctrl+DSend EOF / log out of the shellExit a session or close cat input
Alt+B / Alt+FMove back / forward one wordNavigate a long line quickly

A few notes that trip people up:

  • Ctrl+C does not copy text in most Linux terminals — it cancels. To copy, use Ctrl+Shift+C and paste with Ctrl+Shift+V.
  • Ctrl+L only scrolls the old output out of view; it does not erase your history.
  • Ctrl+D on an empty prompt logs you out, which can be a surprise over SSH (Secure Shell, the protocol you use to log into remote servers).

Best Practices

  • Reach for Ctrl+R before the Up arrow — searching beats scrolling for anything more than a few commands back.
  • Use sudo !! to re-run the last command with admin rights instead of retyping it.
  • Add :p to any history expansion (!!:p, !500:p) when you want to preview before running.
  • Lean on Tab constantly; double-Tab to list options and catch path typos early.
  • Increase how much history Bash keeps by adding HISTSIZE=10000 and HISTFILESIZE=20000 to ~/.bashrc, then run source ~/.bashrc.
  • Keep secrets out of history: prefix a sensitive command with a space (with the default HISTCONTROL=ignorespace) so it is never saved.
Last updated June 15, 2026
Was this helpful?