bash getopts没有传递电子邮件或IP地址

时间:2013-04-21 07:31:54

标签: bash getopts

我一直在敲打这个。想看看我做错了什么,这可能就是我的全部内容。我正在ping一个IP,然后当它下降或上升时,它会发送一个通知。我的问题是关于getops。我正在使用它来尝试解析电子邮件地址和IP。这些都没有被解析。如何使用getopts解析我的两个变量我需要允许我的脚本正常运行。提前谢谢你:)

#!/bin/bash
# Variable(s)
# --------
EMAIL_DOWN_SENT="0";
EMAIL_UP_SENT="0";
PING_FAILED="0";
PING_UP_AGAIN="0";

# FUNctions
# ---------
# 
# Echo a string value that is passed
echo_text() {
   echo -e >&2 "$@";
}

echo_help() {
echo_text "Usage: $(basename "$0") [-e] [EMAIL][-h] [-i] [IP]\n\nScript to ping ip address to see if it's up and send an alert on status changes.\n
        -e Enter email: user@domain.tld
        -h This help screen
        -i IP to ping";
   exit;
}

# Main body
# ---------
#
# Get command line options
# ------------------------
while getopts ":e:hi:" OPTIONS 
do
  case $OPTIONS in
     e) EMAIL=$OPTARGS ;;
  h|\?) echo_help ;;
     i) IP= $OPTARGS | grep -E '[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}'; if [ "$?" != "0" ]; then echo_text "Please enter a valid IP"; exit 1; fi; ;;
     *) echo_text "$OPTARGS is invalid, try again";
        exit 1 ;;
  esac
  shift $((OPTIND-1))
done
echo_text "Your email is: $EMAIL";
echo_text "Your ip to ping is: $IP";

# Ping me
# -------
trap "echo You hit ctrl-c, now exiting..; exit" SIGINT
while :
do
   ping -i 2 -c 2 $IP > /dev/null
   if [ $? -ne 0 ]; then
      let PING_DOWN+=1
      echo_text "Down! Abandon all hope who enter here...";
      PING_FAILED="1";
      # If greater than 3 cycles send an email...
      if [[ $PING_DOWN -ge 3 && $EMAIL_DOWN_SENT -eq 0 ]]; then
         echo "$IP Down!"|mutt -s "Ping Failed!" $EMAIL;
         EMAIL_DOWN_SENT="1";
      fi
   else
      let PING_UP+=1
      echo_text "Up! Ahoy! Host alive!";
      # If greater than 3 cycles send an email...
      if [[ $PING_UP -ge 3 && $EMAIL_UP_SENT -eq 0 && $PING_FAILED -eq 1 ]]; then
         echo "$IP up!"|mutt -s "Ping succeeded!" $EMAIL;
         EMAIL_UP_SENT="1";
         PING_UP_AGAIN="1";
      fi
      # Reset checks
      if [ $PING_UP_AGAIN -eq 1 ]; then
         PING_FAILED="0";
         PING_UP="0";
         PING_DOWN="0";
         EMAIL_UP_SENT="0";
         EMAIL_DOWN_SENT="0";
      fi
   fi
done

if [ ! `echo "$OPTARG" | grep -qE '[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}'` ]; then
    echo_text "Please enter a valid IP"
    exit 1
fi
IP="$OPTARG"

3 个答案:

答案 0 :(得分:1)

您的脚本中有两个主要问题:

首先,它是$OPTARG,而不是$OPTARGS

其次,

IP= $OPTARGS | grep -E '[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}';

你做不到。将整个段落改为

if ! echo "$OPTARG" | grep -qE '[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}'; then
    echo_text "Please enter a valid IP"
    exit 1
fi
IP="$OPTARG"

值得注意的是,除非您使用古老的bash,否则您的shell应该有一个=~运算符(请参阅here),您可以替换外部grep与...:

  

使用它时,运算符右侧的字符串被视为扩展正则表达式并相应地匹配(如在regex3中))。如果字符串与模式匹配,则返回值为0,否则返回1。

答案 1 :(得分:1)

除了AdrianFrühwirth指出的问题,你还需要在循环之后将shift命令移动到。你编写它的方式是删除脚本的参数,而getopts仍在解析它们,这将完全混淆事物。

while getopts ":e:hi:" OPTIONS 
do
    ...
done
shift $((OPTIND-1))  # This must be after the "done"

答案 2 :(得分:-1)

尝试用“”包围$ OPTARGS:

e)EMAIL =“$ OPTARGS”;;