Automated submissions from bash shell script

Here is a bash script I have written which automates submissions to daily tournaments from home machines, without using Compute or web hooks or any other complications. If you want to learn to write similar scripts yourself, you may like to buy my e-book Bash for Fun

Edit:

  1. Now an updated version that executes Tuesdays till Saturdays inclusive (can be changed).

  2. Simplified version that uses sleep instead of rewriting crontab.

It is assumed that your script does all else that is necessary: that is check for new validations and live data, download them when necessary, do the processing and send the predictions to the server.

#!/bin/bash
# Sets up cron checks for new numerai rounds TUE-FRI, from 13:01 UTC.
# Local timezone is taken care of, as long as it is not sub-hourly.
# Activate only once, verify with crontab -l, deactivate with crontab -r
# Make sure that your computer and internet connection are on at the target time

# days of the week to be checking for new tournaments - no spaces!
FIRSTDAY=Tue
LASTDAY=Sat
# hours in UTC to be checking from
HRS=13
# at MINS minutes intervals after the initial attempt at $HRS:01
MINS=5
# name of bash script here that downloads live data, generates predictions and uploads them
PREDICT=numbatch
# full path/name of fully installed numerapi CLI (python) script
NAPI=/home/l/.local/bin/numerapi
# name of log file here 
LOG=cronlog

############ no need to change anything below ###################

# physical path/name of this script
SCRIPT=$(realpath $0)
# PREDICT script must be in the same directory as this script: $PD
PD=$(dirname $SCRIPT)
# crontab expects by default local time, so convert from UTC
LHRS=`date -d "$HRS UTC" +%H`
DAYS=`date -d "$HRS next $FIRSTDAY UTC" +%w`-`date -d "$HRS next $LASTDAY UTC" +%w`

# no argument given means first time manual startup to initiate crontab
# thereafter this script is invoked by cron with dummy argument 'r' to do actual processing
[ $1 ] || {
    printf "1 $LHRS * * $DAYS $SCRIPT r >> $PD/$LOG\n" | crontab - && { 
        printf "$0: `date` crontab initiated:\n`crontab -l`\n" | tee -a $PD/$LOG
        exit 0
    } || {
        printf "$0: `date` crontab initiation failed!\n" | tee -a $PD/$LOG
        exit 2
    }
}

# Invoked by cron at the specified time 13:01 UTC
while [ "$NAPI check-new-round --hours 1" != '1' ]; do 
    printf "$0: `date -u`: tournament has not yet started\n" 
    sleep "$MINS"m #sleep till tournament opens
done
# new tournament has started within the last hour, so download, predict, upload 
printf "$0: `date -u`: new tournament has started!\n" 
printf "$0: running $PD/$PREDICT\n" 
$PD/$PREDICT >> $PD/$LOG 
printf "$0: All done for today!\n" 
exit 0
5 Likes

Here is a new version that should also cope with lots of errors that numerapi sometimes throws up, outside users’ control:

#!/bin/bash
# Sets up cron checks for new numerai rounds TUE-FRI, from 13:01 UTC.
# Local timezone is taken care of.
# Activate only once, verify with crontab -l, deactivate with crontab -r
# Make sure that your computer and internet connection are on at the target time

########### Change these values to suit (no spaces around =) #######################

FIRSTDAY=Tue
LASTDAY=Sat
HRS=13 # hours in UTC to be checking from
MINS=1 # after minutes of initial delay
DOZE=5 # sleep intervals in minutes after unsuccessful attempts
PREDICT=numbatch # bash script in this directory that does all the dowloading, processing and uploading
NAPI=/home/l/.local/bin/numerapi # absolute path/name of fully installed numerapi CLI (python) script 
LOG=cronlog # main log file
ERRLOG=errlog # logfile for numerapi errors

############ No need to change anything below here ###################

SCRIPT=`realpath $0`
PD=$(dirname $SCRIPT) # absolute path directory to this SCRIPT and PREDICT 
# crontab expects by default local time, so convert to it from UTC
LMINS=`date -d "$HRS:$MINS UTC" +%M`
LHRS=`date -d "$HRS:$MINS UTC" +%H`
LDAYS=`date -d "$HRS:$MINS next $FIRSTDAY UTC" +%w`-`date -d "$HRS:$MINS next $LASTDAY UTC" +%w`

# manual invocation with no argument just initiates the crontab and quits
[ $1 ] || {
    printf "$LMINS $LHRS * * $LDAYS $SCRIPT r\n" | crontab - && { 
        printf "$0: `date` crontab initiated:\n`crontab -l`\n" | tee -a $PD/$LOG
        exit 0
    } || {
        printf "$0: `date` crontab initiation failed!\n" | tee -a $PD/$LOG
        exit 2
    }
}

# Invoked by cron at the specified time (13:01) UTC
while :; do
    NRES=`$NAPI check-new-round --hours 1` 2>$PD/$ERRLOG
    # numerapi status is valid and the new tournament has started
    [ $? ] && [  "$NRES" == '1' ] && { 
        printf "$0: `date -u`: new tournament has started!\n" | tee -a $PD/$LOG
        printf "$0: running $PD/$PREDICT\n" | tee -a $PD/$LOG
        $PD/$PREDICT | tee -a $PD/$LOG  # download, predict, upload 
        printf "$0: All done for today!\n" | tee -a $PD/$LOG
        exit 0
    }
    printf "$0: `date -u`: tournament has not yet started, sleeping for $DOZE minutes\n" | tee -a $PD/$LOG
    sleep "$DOZE"m  
done