1. Introduction

When running a shell within a Linux terminal, we see a prompt before typing in commands. The prompt usually consists of useful pieces of information such as the current username, host system name, and the full path to our current working directory. For example, we can have a prompt such as kd@localhost:~/mail-to-telegram/venv/bin.

Sometimes, this full path to the current working directory can make the prompt very long. Consequently, we may want to shorten it by showing just a shortened version of it.

In this tutorial, we’ll look at some ways to shorten the shell prompt to include just the name of the current working directory.

2. Modifying the PS1 Variable

One way to change the shell prompt is to modify the PS1 variable. The PS1 variable stores the format for the shell prompt.

Let’s start by seeing what its value currently is:

kd@localhost:~/mail-to-telegram/venv/bin$ echo $PS1
\[\e]0;\u@\h: \w\a\]${debian_chroot:+($debian_chroot)}\[\033[01;32m\]\u@\h\[\033[00m\]:\[\033[01;34m\]\w\[\033[00m\]\$

From the output, we see that the prompt value contains some Bash functions, plain-text characters, formatting such as ANSI color codes, and also some escape sequences such as \u, \h, and \w.

Let’s see what some of these mean:

  • \u: username of the current shell user
  • \h: hostname of the machine
  • \w: full path to the current working directory
  • \W: name of the current working directory
  • \[ and \]: characters within these such as \033 won’t be printed; they’ll instead be used to format the text by changing font color, background color, and others

Of the above, we’re specifically looking to modify \w, which stands for the full path of the current working directory. For instance, we can replace this with its uppercase counterpart \W to display just the current working directory. We can do so by setting the PS1 variable to a new value using the export command:

kd@localhost:~/mail-to-telegram/venv/bin$ export PS1="\[\e]0;\u@\h: \W\a\]${debian_chroot:+($debian_chroot)}\[\033[01;32m\]\u@\h\[\033[00m\]:\[\033[01;34m\]\W\[\033[00m\]\$"
kd@localhost:bin$

From the output above, we see that the prompt changes immediately after we set the new value for the PS1 variable. Notably, we see this change only in our current session.

To make the change permanent for subsequent shell sessions, we can modify the PS1 assignment in the ~/.bashrc file. In particular, we replace \w with \W depending on the color settings:

if [ "$color_prompt" = yes ]; then
    PS1='${debian_chroot:+($debian_chroot)}\[\033[01;32m\]\u@\h\[\033[00m\]:\[\033[01;34m\]\w\[\033[00m\]\$ '
else
    PS1='${debian_chroot:+($debian_chroot)}\u@\h:\w\$ '
fi

Once we replace \w with \W, the new prompt appears for subsequent shell sessions.

3. Using the PROMPT_DIRTRIM Variable

Starting from Bash version 4, we can use the PROMPT_DIRTRIM variable to shorten the directory path in the prompt.

Setting the PROMPT_DIRTRIM variable’s value to 1 shows only the current directory name, 2 shows the current directory with one above it, 3 shows two levels up, and so on.

Naturally, we can set the value to 0 to show the full path. Let’s see some examples below:

kd@localhost:~/mail-to-telegram/venv/bin$ export PROMPT_DIRTRIM=1
kd@localhost:~/.../bin$ export PROMPT_DIRTRIM=2
kd@localhost:~/.../venv/bin$ export PROMPT_DIRTRIM=3
kd@localhost:~/mail-to-telegram/venv/bin$ export PROMPT_DIRTRIM=0
kd@localhost:~/mail-to-telegram/venv/bin$

In the output, we see that every time we set a new value for the PROMPT_DIRTRIM variable, the effect of the value is reflected in the subsequent prompt.

Again, to make this change permanent, we can set the value of this variable in our ~/.bashrc file:

# Sets PROMPT_DIRTRIM for every shell login
PROMPT_DIRTRIM=1

After adding the above lines in our ~/.bashrc file, the prompt directory is trimmed to show just the directory name on all subsequent shell logins.

4. Zsh Shell Prompt

Of course, prompts are a universal concept in different environments and shells. Moreover, many shells offer their specific default prompt formatting and control mechanisms.

For example, the common Zsh shell provides the PROMPT or PS1 variable for prompt customization.

In it, prompt escape sequences start with a % instead of a *\* backslash. Let’s see some examples:

  • login information such as %M machine name, %m hostname, and %n user name
  • shell state like %# root check, %? last status check, and %j number of jobs
  • date and time like %D date (yy-mm-dd), %T (HH:MM:SS), and %D{string} custom timestamp
  • visual effects like %B (%b) bold, %U (%u) underline, and %S (%s) standout

Let’s see a particular example with prompt paths.

4. Zsh Prompt Current Working Directory

When it comes to the current working directory, there are three escape sequences:

  • %d, %/: current working directory
  • %~: similar to %d and %/, but replaces $HOME and other tilde expansions

Importantly, if an integer follows the percent sign of any of the above, it decides the number of components in the path. Specifically, 0 means the whole path, positive integers restrict the path to that number of trailing components, while negative integers show only leading components.

5.1. Truncate by Number of Paths

Let’s see some examples:

baeldung@host:~/dir/subdir$ echo "$PROMPT"
%n@%m:%~%#
baeldung@host:~/dir/subdir$ echo "$PS1"
%n@%m:%~%#
baeldung@host:~/dir/subdir$ export PROMPT='%n@%m:%d%# '
baeldung@host:/home/baeldung/dir/subdir$ export PROMPT='%n@%m:%1d%# '
baeldung@host:subdir$ export PROMPT='%n@%m:%2d%# '
baeldung@host:dir/subdir$ export PROMPT='%n@%m:%-2d%# '
baeldung@host:/home/baeldung$

Here, we first see that PROMPT and PS1 both have the same value. After that, we test different values of PROMPT by varying %~, %d%1d%2d, and %-2d.

5.2. Indicate Path Truncation

Since the latter might get confusing, a good way to show missing parts of the path is an ellipsis:

baeldung@host:/home/baeldung/dir/subdir/anotherdir$ export PROMPT='%n@%m:%(4~|.../%3~|%~)%# '
baeldung@host:.../dir/subdir/anotherdir$

Here, we employ a feature of the Zsh prompt: conditional substrings. Specifically, %() is similar to an if statement that surrounds different alternatives for that part of the prompt. Here, the condition is whether we have at least 4 components in the current path.

In case 4~ we have 4 or more components, we use …/%3~ for the path. Otherwise, we use %~ and show the full path.

Alternatively, we can employ a different way of limiting:

baeldung@host:.../subdir/anotherdir/moredir$ export PROMPT='%n@%m:%(5~|%-1~/…/%3~|%4~)%# '
baeldung@host:~/…/subdir/anotherdir/moredir$

The main difference here is the condition and the number of leading components we show.

5.3. Truncate by Length

Sometimes, limiting the number of path elements may not be enough when separate elements are too long.

In such cases, we can use the %< truncation operation:

baeldung@host:/home/baeldung/loooooooooooooooooooooong$ export PROMPT='%n@%m:%24<...<%~%<<%#
baeldung@host:...ooooong$

Thus, we limit the total prompt length to 24 characters. If that’s exceeded, the difference comes out of the < left side of the current working directory path. Here, the shell replaces it with an ellipsis.

6. Conclusion

In this article, we looked at different ways to shorten the shell prompt by shortening the path of the current working directory the prompt includes.

While modifying the PS1 variable in Bash offers more options to customize the prompt, using the version 4 PROMPT_DIRTRIM variable is a quick and elegant way of shortening the current working directory path without fundamental changes to the main prompt variables.

On the other hand, Zsh has different mechanisms for PROMPT current working directory manipulation.