1

I've got a bunch of CronJobs, and they work fine, except for one. I've looked through a lot of forums and websites, and tried a combination of things but alas nothing has worked.

Rephrasing the question is:

Q: The bashscript works without any problems from the terminal. But with the CronJob it does not work at all.

The last thing I have done for debugging is the following:

1) Checked if the Cron Daemon is running (ps ax | grep) =is working

2) Made an extra chron job to (retest) send out an email to me every minute (* * * * * echo "hello" | mail -s "subject" [email protected]) =worked fine

3) I've ran my bash script through the terminal as a standalone =worked fine

4) I've checked grep CRON /var/log/syslog for any errors =looks good/no errors

5) Checked for permissions etc. = no problems with permissions

6) The file path to the bash script for the cron job looks fine

#!/bin/bash

#When adding any additional machines make sure there are two files
#within the directory. MACHINE_NAMEMACHINE_NUMBER_initial_time.txt
#and MACHINE_NAMEMACHINE_NUMBER_old_ignition_value.txt

#./engine_switch_check.txt MACHINE_NAME MACHINE_NUMBER

echo `date +%T` >> test.txt

./engine_switch_check.txt MXE 065
./engine_switch_check.txt TMX5BP 001
./engine_switch_check.txt MX3 122
./engine_switch_check.txt TMX 098

and the engine_switch_check.txt :

#!/bin/bash

mc_id="$1"        #-->eg: TMX
mc_no="$2"        #-->eg: 098
echo "$mc_id $mc_no"

#echo "1--$mc_id$mc_no-DATAFILE.txt"
mc_fname=$mc_id$mc_no'_old_ignition_value.txt'
echo $mc_fname


#old_ignition_value=$(sed -n '1p' $mc_fname)
#echo "2--$old_ignition_value"
#old_ignition_value=$(sed -n '1p' $mc_id$mc_no'DATAFILE.txt')
#echo "3--$old_ignition_value"
new_ignition_value=`get values from the terminal`
old_ignition_value=$(sed -n '1p' $mc_id$mc_no'_old_ignition_value.txt')


echo "Program name: $0"
echo "New Ignition Value: $new_ignition_value"
echo "Old Ignition Value: $old_ignition_value"
echo;echo;echo

#difference_btwn_new_old_ign_values=$(awk '{print $1-$2}' <<< "$new_ignition_value $old_ignition_value")

difference_btwn_new_old_ign_values=$(($new_ignition_value - $old_ignition_value))
#difference_btwn_new_old_ign_values= expr new_ignition_value - old_ignition_value

echo "$new_ignition_value"
echo "$old_ignition_value"
echo "$difference_btwn_new_old_ign_values"

if [ "$difference_btwn_new_old_ign_values" -lt "1" ]
then
    > $mc_id$mc_no'_initial_time.txt'
    initial_time=`date +"%s"`    
    echo $initial_time >> $mc_id$mc_no'_initial_time.txt'
fi

if [ "$difference_btwn_new_old_ign_values" -ge "5" ]
then
    final_time=`date +"%s"`
    initial_time=$(sed -n '1p' $mc_id$mc_no'_initial_time.txt')
    echo;echo;echo "initial time: $initial_time"
    echo "final time: $final_time"
  #initial_time=0000
    time_difference_in_sec=$(( $final_time - $initial_time ))

    echo "time difference in sec: $time_difference_in_sec"

    time_difference_in_min=$(( $time_difference_in_sec / 60 ))


    if [ "$time_difference_in_sec" -le "3600" ]
    then
      email_subject="$mc_id $mc_no switched on $difference_btwn_new_old_ign_values times within $time_difference_in_min minutes"

            `echo -e "Hi there,\n\n$mc_id $mc_no has been switched on $difference_btwn_new_old_ign_values times within the last $time_difference_in_min minutes\n\nCheers," | mail -s "$email_subject" $email_list`

      echo "EMAIL SENT"

: <<'psuedo'

      > $mc_id$mc_no'_old_ignition_value.txt'
      echo $new_ignition_value >> $mc_id$mc_no'_old_ignition_value.txt'

psuedo
    fi  

    if [ "$time_difference_in_sec" -gt "3600" ]
    then

            > $mc_id$mc_no'_initial_time.txt'
            initial_time=`date +"%s"`    
            echo $initial_time >> $mc_id$mc_no'_initial_time.txt'


    fi
fi

I've cut out the details regarding the email, but that line works fine.

I honestly don't know what else I can do. The only difference with this bash file is that it calls another 'executable txt' file from within it. And both of these files work great from the terminal by themselves.

Update (18/02/2015): I have further tried the CronTab by writing another (simpler) script to email out a timestamp, also recorded the timestamp into a .txt file - which worked without any problems. I rewrote it because I was thinking maybe the CronTab was not working like it should.

For anyone who is having a similiar problem these are some options you should consider: Other things I did during troubleshooting (not in order)

  • Created an echo out to a text file to see if the program was being run
  • Avoided using sudo crontab -e everyone recommends staying away from sudo crontab -e
  • Checked the directory path within the crontab
  • Read/reread various forums, read/reread my program over and over again (get someone else who understands programming to do it, as fresh eyes can see what you might miss)
  • Added PATH and SHELL in to crontab
  • Added different CronJobs (mentioned update 18/02/15)
  • Changed relative path to full path within all the programs This made it work with the crontab
6
  • 3
    Now if only you provided the actual script :} for us to look at... it may require an actual TTY for in-/output, for example. Is it using fully qualified paths?
    – tink
    Commented Feb 17, 2015 at 2:19
  • @tink I've added the script.
    – 3kstc
    Commented Feb 17, 2015 at 4:35
  • Are you sure this script is working without any errors? I see issues with the if conditions.
    – Sreeraj
    Commented Feb 17, 2015 at 5:14
  • 3
    The "bash script for the cron job" references the script ./engine_switch_check.txt, but what directory is .? You could try adding the debugging line to output pwd into a file and see whether the "bash script for the cron job" is executing where you think it is.
    – Sparhawk
    Commented Feb 17, 2015 at 6:05
  • Please show the crontab entry that should run this.
    – wurtel
    Commented Feb 17, 2015 at 7:51

3 Answers 3

1

I think you need to set the path variable in the script

For example

PATH='/usr/local/bin:/bin:/usr/bin:/usr/local/sbin:/usr/sbin'
5
  • A bit of an amateurish question - would this be inside my script which calls the engine_switch_check.txt? And how would I figure out the PATH variable?
    – 3kstc
    Commented Feb 17, 2015 at 4:57
  • @3kstc run echo $PATH from a normal terminal. You can place it inside the script or at the top of the crontab, before the cron entries begin. An example: unix.stackexchange.com/questions/158473/…
    – muru
    Commented Feb 18, 2015 at 0:35
  • @muru - I'm unfamiliar with PATH. So I have a few Q's . I've run echo $PATH and I got this: /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games. Q Where do I place this line, and do I call it. Is there anything else I need to write up within the crontab? Do I have to reconfigure my crontab's directory i.e. * * * * * /home/ed/enginecheck/engine.txt?
    – 3kstc
    Commented Feb 18, 2015 at 1:10
  • Place PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/lo‌​cal/games at the top of of your crontab (the question I linked to in the previous comment has an example). As to the other question, first check out Sparhawk's comment on your question.
    – muru
    Commented Feb 18, 2015 at 1:14
  • @muru I'm guessing it would be wise to also add SHELL=/bin/bash as all my codes in CronTab are written in BashScript (extensions are TXT though - this shouldn't be a problem right?) Q Once I place the PATH and SHELL on top of my crontab, what will I be doing :/ Sorry for such trivial questions, but I really want to learn.
    – 3kstc
    Commented Feb 18, 2015 at 1:26
1

Setting $PATH, as others have suggested, is always a good practice in scripts that may be called from outside of your interactive environment.

When you are calling the scripts from your shell, you probably cd to the containing directory first. You'll also need to do that here.

cron may run your script with a working directory of / or /var, for example, so you need to use full paths to programs outside of $PATH, or change to the proper working directory. In this case you will want to change working directories because the script writes to disk and it appears you want the output file to reside in the same directory as the script.

You can change directories in the crontab entry:

* * * * * cd /home/ed/enginecheck && ./engine.txt

Or in the script itself (before any other commands):

cd /home/ed/enginecheck

echo `date +%T` >> test.txt
...
1

The solution that worked for me is I changed all of the paths within my two programs from relative paths ie: (./name_of_file.txt) to full paths (ie: /home/ed/directory/some_more_directory/name_of_file.txt)

Was it just this, or a combination of the other things I did, I don't know - but changing the paths from relative to full path did it.

1
  • 1
    cron jobs always start up in your HOME directory. Yes, if you don't specify an absolute pathname, you have to use a relative pathname that is relative to your HOME directory. Your relative pathnames were not relative to your HOME directory. Commented Nov 23, 2015 at 6:29

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .