如何在 linux 中 ping 直到知道主机?

San*_*uys 55 linux bash command-line-interface ping

如何 ping 某个地址,找到后停止 ping。

我想在 bash 脚本中使用它,所以当主机启动时,脚本继续 ping,从主机可用的那一刻起,脚本继续......

Gor*_*son 92

Martynas 回答的进一步简化:

until ping -c1 www.google.com >/dev/null 2>&1; do :; done
Run Code Online (Sandbox Code Playgroud)

请注意,ping 本身用作循环测试;一旦成功,循环就结束。循环体为空,空命令“ :”用于防止语法错误。

更新:我想到了一种让 Control-C 干净地退出 ping 循环的方法。这将在后台运行循环,捕获中断(Control-C)信号,并在发生时终止后台循环:

ping_cancelled=false    # Keep track of whether the loop was cancelled, or succeeded
until ping -c1 "$1" >/dev/null 2>&1; do :; done &    # The "&" backgrounds it
trap "kill $!; ping_cancelled=true" SIGINT
wait $!          # Wait for the loop to exit, one way or another
trap - SIGINT    # Remove the trap, now we're done with it
echo "Done pinging, cancelled=$ping_cancelled"
Run Code Online (Sandbox Code Playgroud)

这有点迂回,但如果您希望循环可取消,它应该可以解决问题。

  • 添加“睡眠”(例如每 5 秒): while !ping -c1 www.google.com &>/dev/null; 睡5;完毕 (6认同)
  • 默认情况下,`ping` 会等待 10 秒,然后才会放弃它的 ping。如果你想把它减少到 1 秒,你可以使用 `-w1`。 (4认同)
  • @JackO'Connor 使用 BSD ping,这是一个大写的 `-W1` (2认同)

Aar*_*ley 32

我知道这个问题很老......并且专门询问关于ping,但我想分享我的解决方案。

我在重新启动主机时使用它来了解何时可以再次通过 SSH 连接到它们。(因为pingsshd启动前会响应几秒钟。)

until nc -vzw 2 $host 22; do sleep 2; done
Run Code Online (Sandbox Code Playgroud)

  • 这正是我要找的,谢谢!您甚至可以使用 CTRL+C 中断呼叫,这对于该线程中的其他一些解决方案而言并非如此。 (2认同)

小智 28

您可以执行循环,发送一个 ping 并根据状态中断循环,例如 (bash):

while true; do ping -c1 www.google.com > /dev/null && break; done
Run Code Online (Sandbox Code Playgroud)

将它放在脚本中的某个位置会阻塞,直到www.google.com可以 ping 通。

  • 这个 `while true` 和 `break` 是更干净的解决方案,IMO。 (2认同)

Jan*_*kel 11

ping 目标主机一次。检查 ping 是否成功(ping 返回值为零)。如果主机不存在,请再次 ping。

以下代码可以保存为文件并使用主机名作为参数调用,或者删除第一行和最后一行并用作现有脚本(waitForHost 主机名)中的函数。

如果 ping 没有产生响应,代码不会评估失败的原因,因此如果主机不存在,则永远循环。我的 BSD 手册页列出了每个返回值的含义,而 linux 则没有,所以我想这可能不可移植,这就是我忽略它的原因。

#!/bin/bash

PING=`which ping`

function waitForHost
{
    if [ -n "$1" ]; 
    then
        waitForHost1 $1;
    else
        echo "waitForHost: Hostname argument expected"
    fi
}

function waitForHost1
{
    reachable=0;
    while [ $reachable -eq 0 ];
    do
    $PING -q -c 1 $1
    if [ "$?" -eq 0 ];
    then
        reachable=1
    fi
    done
    sleep 5
}
waitForHost $1
Run Code Online (Sandbox Code Playgroud)


rad*_*ius 9

UNREACHEABLE=1;
while [ $UNREACHEABLE -ne "0" ]; 
   do ping -q -c 1 HOST &> /dev/null; UNREACHEABLE=$?; sleep 1;
done
Run Code Online (Sandbox Code Playgroud)

您可以删除 sleep 1,它只是为了防止在主机可以访问但 ping 不会以代码 0 退出的情况下出现任何泛洪问题。