Related Entries

Unix's revenge
Corn on unix
Find and replace locks
*Nixing linkfest 2002.10.04
Unixifying Windows

« Remove duplicate jars
» Bangalore Coonoor on Royal Enfield

Bash infinite loop script

A template script if you need to weakly emulate the Cron like behavior

There are times when cron won’t do for automated jobs. Classic example is when you need to start a script, enter some data and then get it into cron. Now, in most cases this can be handled by having env variables or config files. However, what if some one needs to enter a secret value? You don’t want that stored in the filesystem anywhere. For situations like these, you can get inspiration from the following script.

#!/bin/bash
#####################################################################
#                                                                   #
#  Daily cron like job template. 
#  At times you may not be able to use regular unix cron. Common    #
#  case being you need to manually enter some data when the job     #
#  is started. For example, typing in a password.                   #
#                                                                   #
#  So this has an infinite loop and time comparison to process when #
#  comparison matches.                                              #
#                                                                   #
#  It is not very accurate in finegrained time comparison. Best to  #
#  use this for jobs that run once in a day. Nor is it powerful     #
#  like cron time expressions.                                      #
#                                                                   #
#  Startup normally and enter whatever you need to enter.           #
#  Then do CTRL-Z, bg, disown -h to move it to background and exit  #
#  shell                                                            #
#                                                                   #
#####################################################################

# define an array of times to fire. In this example, it is at minutes 32,34,36,38 every  hour
read -ra TARGET_TIMES <<< "32 34 36 38"
# adjust date command format to match the times you put out above
DATE_CMD="date +%M"
# adjust sleep time. make sure it is large enough to avoid triggering multiple
# times in a slot; small enough to avoid skipping a slot. eg, if you’ve time target
# at minutes, and sleep is 10 seconds, if the worker finishes within 10 seconds,
# it will start again before minute is out. If it is longer than 60 seconds, the
# monitor may skip the minute totally after 3-4 iterations.
SLEEP_TIME=30 #in seconds

# -----------  nothing to change below this ----
read -p "Enter value one : " VAL_1
read -s -p "Enter secret : " VAL_2

# this is the guy that gets called when the time comes
# note that if this takes a long time, your results may vary
doWork() {
  echo; echo
  tm=$1
  shift
  echo "Running at [$tm]: $@"
  # add your code to do stuff here
}

echo  $VAL_1 $VAL_2
while : ;do
  dt=`$DATE_CMD`
  for t in "${TARGET_TIMES[@]}"; do
    if [ $dt == $t ]; then
      doWork $t $VAL_1 $VAL_2
    fi
  done
  sleep $SLEEP_TIME
done

Please don’t treat this as fully secure way of doing things. One can do a memory dump and still get the value of the variables. However, it is a bit better than having no security at all.

If you are thinking of using some variation of this to securely connect to your database without having to keep db password in the filesystem, don’t! Write a java program instead and use jasypt to do it properly :)