Skip to content

Instantly share code, notes, and snippets.

@pyrtsa
Last active February 12, 2023 05:12
Show Gist options
  • Star 3 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save pyrtsa/7e8ae9fa99c8f6e57654 to your computer and use it in GitHub Desktop.
Save pyrtsa/7e8ae9fa99c8f6e57654 to your computer and use it in GitHub Desktop.
Make Bash report the start times all commands, and total durations of long-running ones.
export _ps1_timer
function _ps1_timer_start {
# echo START
_ps1_timer=${_ps1_timer:-`gdate +%s%N 2> /dev/null || date +%s%N`};
}
function _ps1_timer_stop {
# echo STOP
if [ -z "$_ps1_timer" ]; then
return
fi
local nanoseconds=$((`gdate +%s%N 2> /dev/null || date +%s%N` - ${_ps1_timer:-0}))
_ps1_timer=
local milliseconds=$((nanoseconds / 1000000))
local seconds=$((milliseconds / 1000))
local minutes=$((seconds / 60))
local hours=$((minutes / 60))
local milli=$((milliseconds % 1000))
local hecto=$((milli / 10))
local deci=$((hecto / 10))
local second=$((seconds % 60))
local minute=$((minutes % 60))
local elapsed
if [ $milliseconds -lt 200 ]; then elapsed=
elif [ $seconds -lt 1 ]; then elapsed=$(printf "%d ms" $milliseconds)
elif [ $seconds -lt 10 ]; then elapsed=$(printf "%d.%02d s" $seconds $hecto)
elif [ $seconds -lt 100 ]; then elapsed=$(printf "%d.%d s" $seconds $deci)
elif [ $hours -lt 1 ]; then elapsed=$(printf "%d min %02d s" $minutes $second)
else elapsed=$(printf "%d h %02d min %02d s" $hours $minute $second)
fi
if [[ -n "$elapsed" ]]; then
echo $'\e[90m'"($elapsed)"$'\e[0m'
fi
}
export _ps1_timer_enabled=
function _pre_command {
if [ -z "$_at_prompt" ]; then
return
fi
unset _at_prompt
if [ -n "$_ps1_timer_enabled" ]; then
local timestamp=`date +'%H:%M:%S'`
echo $'\e[90m'"$timestamp"$'\e[0m'
_ps1_timer_start
fi
}
_first_prompt=1
function _post_command {
_at_prompt=1
if [ -n "$_first_prompt" ]; then
unset _first_prompt
return
fi
_ps1_timer_stop
}
PROMPT_COMMAND="$PROMPT_COMMAND"$'\n''_z --add "$(pwd '$_Z_RESOLVE_SYMLINKS' 2>/dev/null)" 2>/dev/null;'$'\n''_post_command;'
function prompt-time {
case $1 in
y|yes|on)
_ps1_timer_enabled=1
trap '_pre_command' DEBUG
;;
n|no|off)
_ps1_timer_enabled=
trap - DEBUG
;;
*) echo 'usage: prompt-time (y|yes|on|n|no|off)' ;;
esac
}

Prints current time whenever you start executing a shell command, and the elapsed time in the end if the execution took more than 0.2 s.

Example:

pyrtsa ~ $ sleep 0.1 && echo 'Done waiting.'
10:43:34
Done waiting.
pyrtsa ~ $ sleep 1 && echo 'Done waiting.'
10:43:37
Done waiting.
(1.06 s)
pyrtsa ~ $

Usage: Add the following to your .bash_profile or .bashrc:

source ~/.prompt-time
prompt-time on

(On macOS, requires gdate, i.e. brew install coreutils.)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment