In this code I find a list all of the running java
processes and give the below function a name to look for, it will do its best. But since I find my approach a little too ugly, could some POSIX shell script writer have a look and possibly give me some simplification recommendations?
#!/bin/sh
# here is an ugly constant vuze java process name
readonly vuze_java_process_name='org.gudy.azureus2.ui.swt.Main'
is_java_program_running()
# expected arguments:
# 1ドル = java program name
{
# there will always be at least one java process:
# jdk.jcmd/sun.tools.jps.Jps, which is actually
# the program giving us the list of java processes
java_process_list=$( jps -l | awk '{print 2ドル}' )
# this behaves strangely if there is zero processes (needs verification)
# but since there is always at least one, no problem here
java_process_list_count=$(( $( printf '%s\n' "${java_process_list}" | wc -l ) ))
# set the result value as if we did not find it
result=false
# POSIX-ly simulate FOR loop
i=1; while [ "${i}" -le "${java_process_list_count}" ]
do
# here we take one line from the list on $i position
java_process_entry=$( echo "${java_process_list}" | sed --posix --quiet "${i}{p;q}" )
# compare the given process entry with given java program name
if [ "${java_process_entry}" = "${1}" ]
then
# set the result value
result=true
# end this loop
break
fi
# increase iterator
i=$(( i + 1 ))
done
# depending on if we found vuze process running,
# return positive or negative result value
if [ "${result}" = true ]
then
return 0
else
return 1
fi
}
###
### EXAMPLE on Vuze
###
# keep Vuze alive forever, check in 5 seconds interval
while true
do
sleep 5s
if ! is_java_program_running "${vuze_java_process_name}"
then
my_date_time=$(date +%Y-%m-%d_%H:%M:%S)
printf '%s %s\n' "${my_date_time}" "(re-)starting Vuze"
( /home/vlastimil/Downloads/vuze/vuze > /dev/null 2>&1 & )
fi
done
2 Answers 2
Instead of simulating a for (( expr1 ; expr2 ; expr3 ))
loop, use a POSIX
for java_process_entry in $java_process_list
Notice that now you don't need to compute the number of lines, neither invoke sed
.
There is noting wrong with early return. return 0
as soon as the desired process is found.
There is no need to store the entire list in a variable, neither invoke awk
. Process the jps
output sequentially.
All that said, consider
is_java_program_running()
{
jps -l | while read pid java_process_entry; do
if [ $java_process_entry = "${1}" ]; then return 0; fi
done
return 1
}
(On top of what @vnp already wrote.)
When these lines are the last in a function:
if [ "${result}" = true ] then return 0 else return 1 fi
Then you can write simply:
[ "${result}" = true ]
Because the exit code of a function is the exit code of its last executed statement.
-
\$\begingroup\$ In fact, given that the only other possible value of
$result
isfalse
, we can just expand and execute it. \$\endgroup\$Toby Speight– Toby Speight2019年02月25日 19:06:06 +00:00Commented Feb 25, 2019 at 19:06