Reputation: 37
I have a task where I need to extract data from an API. I need to specify to only collect data between 7am and 9pm for every day in a given month.
This will be a Bash script that will run at 00:01 on the 1st of each month using cron.
The API will only accept times in Epoch time. The script needs to be flexible enough so I don't have to code in every single day of a year.
I am having problems wrapping my head around this issue. I can get the first day of a month with the epoch time at 7am and the epoch time at 9pm, the API will accept these two epoch values and looks between the 2 times.
I can also get last day of the month with the epoch time at 7am and again at 9pm.
What I cannot figure out are the days between the first and last day of the month for 7am epoch and 9pm epoch.
START_LAST_MONTH=$(date "+%Y-%m-01" -d "-1 Month");
START_DAY_SEVEN_AM_EPOCH_DATE=$(date +%s -d"$START_LAST_MONTH 7am");
START_DAY_NINE_PM_EPOCH_DATE=$(date +%s -d"$START_LAST_MONTH 9pm");
END_LAST_MONTH=$(date "+%Y-%m-%d" -d "$START_LAST_MONTH +1 month -1 day");
END_DAY_SEVEN_AM_EPOCH_DATE=$(date +%s -d"$END_LAST_MONTH 7am");
END_DAY_NINE_PM_EPOCH_DATE=$(date +%s -d"$END_LAST_MONTH 9pm");
I am thinking a way to achieve this is to add a 86400 seconds to the 7am and 9pm START_DAY variables, creating new variables by doing so, then increment upwards a day until the END_DAY 7am and 9pm Epoch time variables are hit. This should be flexible then for each month, since the number of days in a month vary.
But this is beyond my bash scripting skills and I am looking to learn how to achieve this so any help would be appreciated, another angle to look at this from is also fine.
UPDATE:
I now have this in a bash script
#!/bin/sh -x
START_LAST_MONTH=$(date "+%Y-%m-01" -d "-1 Month");
START_DAY_SEVEN_AM_EPOCH_DATE=$(date +%s -d"$START_LAST_MONTH 7am");
START_DAY_NINE_PM_EPOCH_DATE=$(date +%s -d"$START_LAST_MONTH 9pm");
END_LAST_MONTH=$(date "+%Y-%m-%d" -d "$START_LAST_MONTH +1 month -1 day");
END_DAY_SEVEN_AM_EPOCH_DATE=$(date +%s -d"$END_LAST_MONTH 7am");
END_DAY_NINE_PM_EPOCH_DATE=$(date +%s -d"$END_LAST_MONTH 9pm");
until [ $END_DAY_SEVEN_AM_EPOCH_DATE ]
do
let ADD_ONE_DAY=$START_DAY_SEVEN_AM_EPOCH_DATE+86400
echo $ADD_ONE_DAY
done
But its not echoing the ADD_ONE_DAY variable at all. When debugging using -X it gets to here: until [ $END_DAY_SEVEN_AM_EPOCH_DATE ] and doesnt do anything further.
Upvotes: 0
Views: 62
Reputation: 9018
The problem with your updated example code is that in the loop condition you are effectively only checking $END_DAY_SEVEN_AM_EPOCH_DATE
not to be empty - which is just set two lines above, therefore the loop body is never executed.
To make your example work as intended try these modifications:
#!/bin/sh -x
START_LAST_MONTH=$(date "+%Y-%m-01" -d "-1 Month");
START_DAY_SEVEN_AM_EPOCH_DATE=$(date +%s -d"$START_LAST_MONTH 7am");
START_DAY_NINE_PM_EPOCH_DATE=$(date +%s -d"$START_LAST_MONTH 9pm");
END_LAST_MONTH=$(date "+%Y-%m-%d" -d "$START_LAST_MONTH +1 month -1 day");
END_DAY_SEVEN_AM_EPOCH_DATE=$(date +%s -d"$END_LAST_MONTH 7am");
END_DAY_NINE_PM_EPOCH_DATE=$(date +%s -d"$END_LAST_MONTH 9pm");
ADD_ONE_DAY=$START_DAY_SEVEN_AM_EPOCH_DATE
until [ "$ADD_ONE_DAY" -gt "$END_DAY_SEVEN_AM_EPOCH_DATE" ]
do
let ADD_ONE_DAY=$ADD_ONE_DAY+86400
echo $ADD_ONE_DAY
done
$ADD_ONE_DAY
is greater than $END_DAY_SEVEN_AM_EPOCH_DATE
$ADD_ONE_DAY
with before the loop $START_DAY_SEVEN_AM_EPOCH_DATE
$ADD_ONE_DAY
by one day (instead of $START_DAY_SEVEN_AM_EPOCH_DATE
, which results in always the same value, i.e. an endless loop)Another solution in order to loop through all days of a month using the seq
command could be:
#!/bin/bash
START_LAST_MONTH=$(date "+%Y-%m-01" -d "-1 Month")
END_LAST_MONTH=$(date "+%Y-%m-%d" -d "$START_LAST_MONTH +1 month -1 day")
CURRENT_YEAR=$(date +%Y -d "-1 Month")
CURRENT_MONTH=$(date +%m -d "-1 Month")
LAST_DAY_OF_MONTH=$(date +%d -d "$END_LAST_MONTH");
for CURRENT_DAY in $(seq -w 1 "$LAST_DAY_OF_MONTH"); do
CURRENT_DATE="$CURRENT_YEAR-$CURRENT_MONTH-$CURRENT_DAY"
CURRENT_DAY_SEVEN_AM_EPOCH=$(date +%s -d"$CURRENT_DATE 7am")
CURRENT_DAY_NINE_PM_EPOCH=$(date +%s -d"$CURRENT_DATE 9pm")
echo "$CURRENT_DAY_SEVEN_AM_EPOCH - $CURRENT_DAY_NINE_PM_EPOCH"
done
Here seq -w 1 "$LAST_DAY_OF_MONTH"
will generate a sequence from 1 to the last day of the respective month, the -w
outputs the numbers with equal width filling in 0s if necessary, i.e. "01", "02", ...
Upvotes: 2