I'm trying to make a countdown timer script that takes a number of seconds as $1
, then counts down to zero, showing the current remaining seconds as it goes.
The catch is, I'm doing this on an embedded box that doesn't have seq
or jot
, which are the two tools I know can generate my list of numbers.
Here's the script as I have it working on a normal (non-embedded) system:
#!/bin/sh
for i in $(/usr/bin/jot ${1:-10} ${1:-10} 1); do
printf "\r%s " "$i"
sleep 1
done
echo ""
This works in FreeBSD. If I'm on a Linux box, I can replace the for
line with:
for i in $(/usr/bin/seq ${1:-10} -1 1); do
for the same effect.
But what do I do if I have no jot
OR seq
?
If your shell was bash, you could count down from a fixed number with something like this:
#!/bin/bash
for n in {10..1}; do
printf "\r%s " $n
sleep 1
done
But that won't work for you, because bash won't handle things like {${1:-10}..1}
, and you've specified you want a command line option.
Of course, you've also said you're not using bash, so we'll assume a simpler shell.
If you have awk
, you can use that to count.
#!/bin/sh
for n in $(awk -v m="${1:-10}" 'BEGIN{for(;m;m--){print m}}'); do
printf "\r%s " $n
sleep 1
done
printf "\r \r" # clean up
If you don't have awk, you should be able to do it in pure shell:
#!/bin/sh
n=${1:-10}
while [ $n -gt 0 ]; do
printf "\r%s " $n
sleep 1
n=$((n-1))
done
printf "\r \r" # clean up
I think the pure-shell version is probably simple enough that it should be preferred over the awk solution.
Of course, as Mark Reed pointed out in comments, if your system doesn't include a printf
, then you'll need to perform some ugly echo
magic that will depend on your OS or shell... and if your shell doesn't support $((..))
, you can replace that line with n=$(expr $n - 1)
. If you want to add error handling in case a non-numeric $1
is provided, that wouldn't hurt.