patternbashMinor
Send an email if a URL is down twice only
Viewed 0 times
twiceemaildownsendonlyurl
Problem
We want to check if a URL is down or not. But sometimes, the environment is down for maintenance for 3-4 hours and we don't want to keep sending emails during that time.
I have written a shell script for performing a URL check and running it every 30 mins using a cronjob.
The actual requirements are:
The script works. Could you please review and suggest if there is a nicer way of writing the script? I'm learning shell script but don't know all the available options.
``
if [ "$E1" != "" ] || [ $HTTPCode -ge 500 ]
then
status="DOWN"
echo "Step 1"
echo "${ENV}""_DOWN"
if [ -f "${ENV}""_DOWN" ];
then
echo "step 2"
echo "Please check if $ENV in Maintanance window.The check for $url has failed twice.Next The next failure email will be sent if preceding test was SUCCESSFUL" | /bin/mail -s "Is $ENV in Maintanance Window ?" $MAddr
I have written a shell script for performing a URL check and running it every 30 mins using a cronjob.
The actual requirements are:
- Check if the URL is up. If it is down, send an email.
- Cronjob will execute the script again. If Step 1 sent an email, then send an email again asking if the environment is under maintenance.
- Cronjob will execute the script again. If it is still down, don't do anything.
- Keep checking the URL, and if it is responding, don't do anything. But if it goes down again, follow step 1-3.
The script works. Could you please review and suggest if there is a nicer way of writing the script? I'm learning shell script but don't know all the available options.
``
#!/bin/bash
#Checking urls from urls.txt
MAddr="jsing002@internalsvcs.pte.com"
TIME=date +%d-%m-%Y_%H.%M.%S
SCRIPT_LOC=/user/inf/ete4/eteabp4/eid_scripts/jsing002
for url in awk '{print $1}' $SCRIPT_LOC/urls.txt
do
/usr/bin/wget -t 0 --spider --no-check-certificate $url > wget.output 2>&1
HTTPCode=(/usr/bin/wget -t 0 --spider --no-check-certificate $url) 2>&1 | grep HTTP| tail -1|cut -c 41-43
ENV=(grep $url $SCRIPT_LOC/urls.txt | awk '{print $2}')
echo $HTTPCode
E1=/bin/grep -ise 'refused' -ise 'failed' wget.output`if [ "$E1" != "" ] || [ $HTTPCode -ge 500 ]
then
status="DOWN"
echo "Step 1"
echo "${ENV}""_DOWN"
if [ -f "${ENV}""_DOWN" ];
then
echo "step 2"
echo "Please check if $ENV in Maintanance window.The check for $url has failed twice.Next The next failure email will be sent if preceding test was SUCCESSFUL" | /bin/mail -s "Is $ENV in Maintanance Window ?" $MAddr
Solution
- Quoting: Be in the habit of always double-quoting your variables when you use them, e.g.
"$url"instead of$url. Otherwise, nasty vulnerabilities could happen if a variable's value contains spaces or shell metacharacters. URLs, especially, often contain special characters such as&and?.
-
Structure: When processing input with multiple columns, one row at a time, the idiom to use is…
while read url env ; do
# Do stuff here
done < "$SCRIPT_LOC/urls.txt"If the columns are delimited by something other than whitespace…
while IFS=: read user pwhash uid gid gecos homedir shell ; do
# Do stuff here
done < /etc/passwd-
Status of
wget: You run wget twice for each URL. Instead of trying to get the HTTP status code, consider using just the exit status of wget to indicate success or failure.if wget -q -t 0 --spider --no-check-certificate "$url" ; then
# Handle success
else
# Handle failure
fiI've used the
--quiet flag here. Also, I think that an infinite timeout (-t 0) is a bad idea.- HTTP status interpretation: HTTP status codes other than 200 (e.g. 2xx or 3xx) could also indicate some kind of success.
- Filesystem littering: You litter the current directory with temporary files
wget.outputand"${ENV}_DOWN"and"${ENV}_DOWN_2". Perhaps you could append all the state to a single log file.
SCRIPT_LOCcould probably be computed using$(dirname $0).
Code Snippets
while read url env ; do
# Do stuff here
done < "$SCRIPT_LOC/urls.txt"while IFS=: read user pwhash uid gid gecos homedir shell ; do
# Do stuff here
done < /etc/passwdif wget -q -t 0 --spider --no-check-certificate "$url" ; then
# Handle success
else
# Handle failure
fiContext
StackExchange Code Review Q#33742, answer score: 2
Revisions (0)
No revisions yet.