Bash Shell脚本,用于监视具有IP的文件

x33g5p2x  于 2022-11-16  发布在  Shell
关注(0)|答案(2)|浏览(206)

我 希望 建立 一 个 脚本 , 我 可以 监控 一 个 文件 的 IP 与 ping 命令 时 , 向上 或 向下 。
我 发现 了 两 个 很 好 的 方法 在 stackoverflow 和 我 试图 结合 他们 , 但 无论 我 做 什么 它 不 工作 。 我 正在 阅读 man shell 学习 的 未来 以及 , 但 我 认为 我 错过 了 一些 东西 , 不能 使 它 工作 。
脚本 一 :
I cannot seem to find the script i found on stackoverflow but found the same under this resource: (Bash and Ping) section in: https://jmanteau.fr/posts/the-facets-of-ping/#check-if-many-hosts-are-alive
这个 令 人 惊奇 的 脚本 可以 非常 快 地 并行 ping 多 个 主机

#!/bin/bash

argc=$#
if [ $# -lt 1 ]
then
   echo "Usage: $0 <ip-list-file>"
   exit 1
fi

hosts=$1

function customping 
{
    DATE=$(date '+%d/%m/%Y %H:%M:%S')
    ping -c 1 -W 1 $1 >/dev/null 2>&1 && echo "$DATE Node $1 is UP" || echo -e "\033[1;31m $DATE Node $1 is DOWN \033[0m"
# ping -c 1 -W 1 $1 >/dev/null 2>&1 && echo "$DATE Node $1 is UP" || echo "$DATE Node $1 is DOWN"
# sleep 0.01s
}

T="$(date +%s%N)"

DEFAULT_NO_OF_PROC=8
noofproc=$DEFAULT_NO_OF_PROC

if [ -n "$2" ] #user-set no. of process instead of default
then
  noofproc=$2
  echo "Max processes: $noofproc"
fi

export -f customping && cat $hosts | xargs -n 1 -P $noofproc -I{} bash -c 'customping {}' \;

中 的 每 一 个
脚本 二 :
https://stackoverflow.com/a/4708831/19313640 的 最 大 值
这个 惊人 的 脚本 循环 通过 IP 和 显示 如果 关闭 或 启动 ( 监视 )

function check_health {

set 192.168.10.1 192.168.10.2 192.168.10.3 192.168.10.4 192.168.10.5 192.168.10.6 192.168.10.7 192.168.10.8 192.168.10.9 192.168.10.10 192.168.10.11 192.168.10.12 192.168.10.13

trap exit 2

for ipnumber in "$@"; do
  DATE=$(date '+%d/%m/%Y %H:%M:%S')
  ping -c 1 -t 1 $ipnumber > /dev/null
  [ $? -eq 0 ] && echo -e "|\033[1;36m $DATE \033[0m" "|\033[1;32m Node |"$ipnumber "| UP \033[0m" | column -t -s "|"
done

while true; do
  i=1
  for ipnumber in "$@"; do
    statusname=up$i
    laststatus=${!statusname:-0}
    ping -c 1 -t 1 $ipnumber > /dev/null
    ok=$?
    eval $statusname=$ok
    if [ ${!statusname} -ne $laststatus ]; then
      # echo $DATE Status changed for $ipnumber
      DATE=$(date '+%d/%m/%Y %H:%M:%S')
      if [ $ok -eq 0 ]; then
        echo -e "|\033[1;36m $DATE \033[0m" "|\033[1;32m Node |"$ipnumber "| UP \033[0m" | column -t -s "|"
      else
        echo -e "|\033[1;36m $DATE \033[0m" "|\033[1;31m Node |"$ipnumber "| DOWN \033[0m" | column -t -s "|"
      fi
    fi
    i=$(($i + 1))
  done
 # sleep 1
done

}

格式
因此 , 我 的 问题 是 如何 将 这 两 个 脚本 放在 一起 , 并 使 其 完全 并行 作为 第 一 个 脚本 , 并 通过 读取 文件 而 不是 在 第 二 个 脚本 中 " 设置 " , 但 也 与 第 二 个 脚本 的 监视 功能 。
编辑 : 如果 它 是 复杂 的 , 使 这个 工作 至少 我 怎么 才能 使 第 二 个 脚本 读取 一 个 文件 作为 参数 作为 第 一 个 脚本 呢 ?
我 希望 我 是 彻底 的 , 并 给 出 了 足够 的 信息 , 我 正在 努力 做 什么 。

  • 谢谢 - 谢谢
    • 更新 日期 : * *

你 好 再次 , 我 已经 设法 使 它 在 一 个 混乱 的 代码 工作 。

#!/bin/bash

trap exit 2

argc=$#
if [ $# -lt 1 ]
then
   echo "Usage: $0 <ip-list-file>"
   exit 1
fi

hosts=$1

function check_live {

  trap exit 2

  DATE=$(date '+%d/%m/%Y %H:%M:%S')
    ping -c 1 -t 1 $1 > /dev/null
    [ $? -eq 0 ] && echo -e "|\033[1;36m  $DATE \033[0m" "|\033[1;32m Node |"$1 "| UP \033[0m" | column -t -s "|"
    # sleep 1
}

function check_health {

  trap exit 2

#  DATE=$(date '+%d/%m/%Y %H:%M:%S')
#    ping -c 1 -t 1 $1 > /dev/null
#    [ $? -eq 0 ] && echo -e "|\033[1;36m  $DATE \033[0m" "|\033[1;32m Node |"$1 "| UP \033[0m" | column -t -s "|"
#    sleep 3

  while true; do
  # while read line; do 
  # i="$i $line"
    i=1
    for ipnumber in "$@"; do
      statusname=up$i
      laststatus=${!statusname:-0}
      ping -c 1 -t 1 $ipnumber > /dev/null
      ok=$?
      eval $statusname=$ok
      if [ ${!statusname} -ne $laststatus ]; then
        # echo $DATE Status changed for $ipnumber
        DATE=$(date '+%d/%m/%Y %H:%M:%S')
        if [ $ok -eq 0 ]; then
          echo -e "|\033[1;36m  $DATE \033[0m" "|\033[1;32m Node |"$ipnumber "| UP \033[0m" | column -t -s "|"
        else
          echo -e "|\033[1;36m  $DATE \033[0m" "|\033[1;31m Node |"$ipnumber "| DOWN \033[0m" | column -t -s "|"
        fi
      fi
      i=$(($i + 1))
    done
   # sleep 1
  done
}

function duck_art {

textred=$(tput setaf 1)
textcyan=$(tput setaf 12)
textyellow=$(tput setaf 11)
textpurple=$(tput setaf 4)
textpink=$(tput setaf 5)
textwhite=$(tput setaf 7)
textgray=$(tput setaf 8)
textgreen=$(tput setaf 10)

echo -e ${textpink} ================================================================
cat <<EOM
${textyellow}
EOM
cat << "EOF"
                  __                         __
              ___( o)>       DuckLab       <(o )___
              \ <_. )        Monitor        ( ._> /
               `---'                         `---' 
EOF
echo -e ${textpink} ================================================================
echo -e ${textyellow} "                    Press <CTRL+C> to exit.                   "
echo -e ${textpink} ================================================================
echo -e "\033[1;36m  $internal_ip \033[0m" "     ${textpink}|     " "\033[1;36m $my_name \033[0m" "     ${textpink}|     " "\033[1;36m $external_ip \033[0m"
echo -e ${textpink} ================================================================
}

external_ip=$(curl -s ifconfig.me)

internal_ip=$(ifconfig | grep -Eo 'inet (addr:)?([0-9]*\.){3}[0-9]*' | grep -Eo '([0-9]*\.){3}[0-9]*' | grep -v '127.0.0.1')

my_name=$(hostname)


function multi_process_live {
T="$(date +%s%N)"

DEFAULT_NO_OF_PROC=8
noofproc=$DEFAULT_NO_OF_PROC

if [ -n "$2" ] #user-set no. of process instead of default
  then
    noofproc=$2
    echo "Max processes: $noofproc"
  fi

export -f check_live && cat $hosts | xargs -n 1 -P $noofproc -I{} bash -c 'check_live  {}' \; 2>/dev/null 
}


function multi_process_health {
T="$(date +%s%N)"

DEFAULT_NO_OF_PROC=8
noofproc=$DEFAULT_NO_OF_PROC

if [ -n "$2" ] #user-set no. of process instead of default
  then
    noofproc=$2
    echo "Max processes: $noofproc"
  fi

export -f check_health && cat $hosts | xargs -n 1 -P $noofproc -I{} bash -c 'check_health  {}' \; 2>/dev/null 
}


# ================================ End of fucntions ================================

# ================================ Start of Script =================================

clear
duck_art
multi_process_live
multi_process_health

# ================================ End of Script ===================================

格式
第 一 个 函数 检查 是否 有 活动 的 主机 。 第 二 个 函数 循环 显示 初始 输出 , 但 没有 正确 地 循环 文件 的 每 一 行 来 监视 哪些 主机 是 UP 或 DOWN 并 打印 输出 。 它 只 对 第 二 行 做 了 这 一 点 , 我 认为 它 没有 正确 地 读取 文件 的 每 一 行 。
任何 想法 , 改进 和 建议 , 使 这项 工作 和 学习 是 高度 重视 。

  • 谢谢 - 谢谢
yws3nbqq

yws3nbqq1#

请注意,原始脚本的神奇之处在于使用xargs -P $noofproc来并行运行检查。
如果不知道主机列表是什么样子的,很难猜出第一行出现了什么问题。我最好的猜测是,第一次输入的ping退出代码不是零,它没有退出任何东西。
我发现您最近的check_health函数有一些问题。

  • 如您所述,while true循环
  • for ipnumber in "$*",这没有意义,因为你一次只调用一个条目。
  • 由此产生的问题是,对check_health的每个调用都将以i=1开始,因此即使while true不存在,这些调用中的每个调用也将设置相同的statusnameup1),最终将被使用。

以下是我的建议(希望您不介意我删除了脚本中不重要的部分):

#!/bin/bash

trap exit 2

argc=$#
if [ $# -lt 1 ]; then
    echo "Usage: $0 <ip-list-file>"
    exit 1
fi

hosts=$1

function check_live {
    trap exit 2

    DATE=$(date '+%d/%m/%Y %H:%M:%S')
    ping -c 1 -t 1 $1 > /dev/null
    [ $? -eq 0 ] && echo -e "|\033[1;36m  $DATE \033[0m" "|\033[1;32m Node |"$1 "| UP \033[0m" | column -t -s "|"
}

function check_health {
    trap exit 2

    i=$1
    ipnumber=$2
    statusname=up$1
    laststatus=${!statusname:-0}
    ping -c 1 -t 1 $ipnumber > /dev/null
    ok=$?
    eval $statusname=$ok
    if [ ${!statusname} -ne $laststatus ]; then
        DATE=$(date '+%d/%m/%Y %H:%M:%S')
        if [ $ok -eq 0 ]; then
            echo -e "|\033[1;36m  $DATE \033[0m" "|\033[1;32m Node |"$ipnumber "| UP \033[0m" | column -t -s "|"
        else
            echo -e "|\033[1;36m  $DATE \033[0m" "|\033[1;31m Node |"$ipnumber "| DOWN \033[0m" | column -t -s "|"
        fi
    fi
}

function multi_process_live {
    T="$(date +%s%N)"

    DEFAULT_NO_OF_PROC=8
    noofproc=$DEFAULT_NO_OF_PROC

    if [ -n "$2" ]; then
        #user-set no. of process instead of default
        noofproc=$2
        echo "Max processes: $noofproc"
    fi

    export -f check_live
    cat $hosts | xargs -n 1 -P $noofproc -I{} bash -c 'check_live  {}' \; 2>/dev/null
}

function multi_process_health {
    T="$(date +%s%N)"

    DEFAULT_NO_OF_PROC=8
    noofproc=$DEFAULT_NO_OF_PROC

    if [ -n "$2" ]; then
        #user-set no. of process instead of default
        noofproc=$2
        echo "Max processes: $noofproc"
    fi

    export -f check_health
    awk '{print FNR " " $1}' < $hosts | xargs -n2 -P $noofproc -I{} bash -c 'check_health  {}' \; 2>/dev/null
}

multi_process_live
while true; do
    multi_process_health
    sleep 1
done

它运行初始实时检查,然后运行multi_process_health函数。
关键在于两件事。第一,使用awk '{print FNR " " $1}'将主机列表:

127.0.0.1
10.0.0.1
192.168.0.1

变成这样:
其次,使用xargs -n2,这样每次调用check_health时,都会将序列号作为第一个参数,将实际主机作为第二个参数。

brvekthn

brvekthn2#

如果屏幕上显示的主机数量合适,请尝试以下操作:

healthcheck() {
    ipnumber=$1
    last="-1"
    while true; do
        date=$(date -Is)
        ping -c 1 -t 20 $ipnumber > /dev/null 2>/dev/null
        latest=$?
        if [ $last -ne $latest ] ; then
            # status changed                                                                                                                        
            if [ $latest -eq 0 ] ; then
                echo -e "|\033[1;36m  $date \033[0m" "|\033[1;32m Node |"$ipnumber "| UP \033[0m" | column -t -s "|"
            else
                echo -e "|\033[1;36m  $date \033[0m" "|\033[1;31m Node |"$ipnumber "| DOWN \033[0m" | column -t -s "|"
            fi
        fi
        last=$latest
        sleep 1
    done
}
export -f healthcheck

cat hostlist | parallel-20220622 -j0 --ll healthcheck

如果您没有parallel-20220622,则可能已足够:

cat hostlist | parallel -j0 --lb healthcheck

相关问题