Last active
March 17, 2018 16:58
-
-
Save jcausey-astate/9a37f2a2f91f693aaa1e7d473d88c2b6 to your computer and use it in GitHub Desktop.
Watches a running process, executing a specified command when it finishes (Bash).
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
script="$(basename ${0})" | |
read -r -d '' USAGE <<-EOF | |
Watches a specified process (by pid or name) and runs | |
a specified command after it exits. | |
If watching by name, the command executes when no process | |
by that name is running. | |
Usage: | |
${script} [-a|-A] [-t seconds] pid cmd | |
${script} [-a|-A] [-t seconds] -n name cmd | |
${script} -h | |
pid the process id of the process to monitor | |
cmd a command to run when the monitored process exits | |
-a uses \`ps -a\` when searching for processes | |
-A uses \`ps -A\` when searching for processes | |
-h print this usage message and exit | |
-n name monitor for presence of any running process named | |
\`name\`, not by pid | |
-t seconds set delay between polling attempts to \`seconds\` (default 5) | |
EOF | |
by_name=0 | |
delay=5 | |
dash_a="" | |
# process command arguments | |
while [[ "${1:0:1}" == "-" ]] ; do | |
if [[ "${1}" == "-a" ]] || [[ "${1}" == "-A" ]] ; then | |
dash_a="${1}" | |
shift | |
elif [[ "${1}" == "-n" ]] || [[ "${1}" == "--name" ]] ; then | |
shift | |
by_name=1 | |
name=${1} | |
pid=${1} | |
shift | |
elif [[ "${1}" == "-t" ]] || [[ "${1}" == "--time" ]] ; then | |
shift | |
delay=${1} | |
shift | |
elif [[ "${1}" == "-h" ]] || [[ "${1}" == "--help" ]] ; then | |
shift | |
echo | |
echo "${USAGE}" | |
echo | |
exit 0 | |
fi | |
done | |
if [[ -z ${name} ]] ; then | |
name="${1}" | |
pid="${1}" | |
shift | |
fi | |
cmd="$@" | |
# Do some sanity checking | |
if [[ -z ${pid} ]] || [[ -z ${cmd} ]] ; then | |
echo | |
echo "Error: Not enough arguments given." | |
echo | |
echo "${USAGE}" | |
echo | |
exit 1 | |
fi | |
isint_re='^[0-9]+$' | |
if [[ ${by_name} -eq 0 ]] && ! [[ ${pid} =~ ${isint_re} ]] ; then | |
echo | |
echo "Error: PID must be an integer. (Saw '${pid}'.)" | |
echo | |
echo "${USAGE}" | |
echo | |
exit 2 | |
fi | |
if ! [[ ${delay} =~ ${isint_re} ]] ; then | |
echo | |
echo "Error: Delay must be an integer. (Saw '${delay}'.)" | |
echo | |
echo "${USAGE}" | |
echo | |
exit 3 | |
fi | |
# Now we can do the work | |
echo "Waiting on ${pid}, then running: ${cmd}" | |
first_check=0 | |
while true; do | |
if [[ $by_name -ne 0 ]] ; then | |
pid=$(ps ${dash_a} | grep -m1 -e "[0-9]\s*${name}" | awk '{print $1}') | |
fi | |
kill -0 $pid 2>/dev/null | |
if [[ $? -ne 0 ]] ; then | |
if [[ ${first_check} -ne 0 ]] ; then | |
$cmd | |
exit $? | |
else | |
echo | |
echo "Error: The process '${name}' does not appear to be running!" | |
echo " Maybe you need the -a or -A option?" | |
echo | |
echo "${USAGE}" | |
echo | |
exit 4 | |
fi | |
fi | |
sleep ${delay} | |
first_check=1 | |
done | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment