If you know what are background processes, you can directly proceed to see Setting the prompt.
Whenever we execute a time taking command, we don't see the prompt till the time command finishes. For example, when we execute
sleep 5s, shell will do nothing for 5 seconds but wait for the command (
sleep) to finish. After 5 seconds, we will see the prompt again.
Many times, commands are not worthy to wait till they finish their processing. For example, when you are compiling a project and it takes about a minute to complete. You can run the build in background by using
& at the end of command and you will be notified when background job is completed.
chinmay@CC-T480:~$ sleep 5 &  3683711 chinmay@CC-T480:~$ # After 5 seconds when we press Enter + Done sleep 5 chinmay@CC-T480:~$
Here what we did was put
sleep 5 task in background and we got the background process ID that is
3683711. After 5 or more seconds when we enter a new command just press Enter, we see that the background job
sleep 5 is completed by seeing
Done sleep 5.
When building a project we can send the build process in background and while waiting for it to complete, we can do some other task. If we are using
make to build a project and it takes about a minute to complete, we can use
make >/dev/null 2>&1 & to build in background and not display any info/error logs while also making the shell prompt usable to give other commands.
We can also stop a process by hitting
Ctrl-Z and this will also send the task in background. But in this case, task will not run in background but will be stopped until resumed by command
fg in same terminal. We can see the background tasks by command
03:26:34 $ sleep 10 ^Z + Stopped sleep 10 03:26:36 $ jobs + Stopped sleep 10 03:26:38 $ fg sleep 10 03:26:45 $ jobs 03:26:47 $
Another common use of sending task to background is while using
vim or other terminal based editor. When we need to run some commands in terminal, we can just hit
ctrl-z in normal mode and
vim will be stopped. This way we can have our terminal prompt for running commands. When done with terminal, we can switch back to
Bash prompt can be set by setting the environment variable
PS1. We will update this variable to get number of background jobs in our prompt.
If we see manual page for
bash, we can see that it says we can use
\j to show number of jobs
\j the number of jobs currently managed by the shell
But most of the times we have 0 jobs running in background and displaying a 0 every time is not so tidy approach.
We can use a simple bash command to print the jobs in the prompt if they are more than 0.
[ \j -gt 0 ] && echo \j
\j is the number of background jobs. What we are doing is checking if it's greater than 0, if yes, then print (
echo) in the prompt else not.
A simple shell prompt including the current directory and number of background processes can be like
chinmay@CC-T480:~/Downloads$ PS1="\w\$([ \j -gt 0 ] && echo [\j]) $ " ~/Downloads $ sleep 10 ^Z + Stopped sleep 10 ~/Downloads $ sleep 15 ^Z + Stopped sleep 15 ~/Downloads $ vi + Stopped vi ~/Downloads $ jobs  Stopped sleep 10 - Stopped sleep 15 + Stopped vi ~/Downloads $ fg 2 sleep 15 ~/Downloads $ fg 1 sleep 10 ~/Downloads $ fg vi ~/Downloads $
Here the number of background processes will be listed inside square brackets.
Checkout designing a minimal bash prompt.