问题
Could anyone of you explain why the following bash while loop ends execution after the first iteration when ssh
is executed in it's body, please?
Input file:
$ cat hosts
192.168.223.21 miner01
192.168.223.23 miner03
- While without ssh - two iterations:
$ while IFS=' ' read -r IP HOST; do echo "ip=$IP hostname=$HOST"; done < hosts
ip=192.168.223.21 hostname=miner01
ip=192.168.223.23 hostname=miner03
$
- While with ssh in body - one iteration:
$ while IFS=' ' read -r IP HOST; do echo "ip=$IP hostname=$HOST"; ssh $HOST hostname ; done < hosts
ip=192.168.223.21 hostname=miner01
miner01
$
I also executed it with set -x
but I can't see the reason for such behavior:
$ while IFS=" " read -r IP HOST; do echo "ip=$IP hostname=$HOST"; ssh $HOST hostname; done < hosts
while IFS=" " read -r IP HOST; do echo "ip=$IP hostname=$HOST"; ssh $HOST hostname; done < hosts
+ IFS=' '
+ read -r IP HOST
+ echo 'ip=192.168.223.21 hostname=miner01'
ip=192.168.223.21 hostname=miner01
+ ssh miner01 hostname
miner01
+ IFS=' '
+ read -r IP HOST
$
Bash version:
$ bash --version
bash --version
GNU bash, version 5.0.3(1)-release (x86_64-pc-linux-gnu)
Copyright (C) 2019 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
回答1:
ssh
also consumes standard input. Try to replace ssh $HOST hostname
with cat
or nl
, to understand conceptually why it does not work. After the command consumes the input, while
ends since there is nothing else to read.
Since you do not need ssh
to consume stdin, redirect it. This works:
while IFS=" " read -r IP HOST; do
echo "ip=$IP hostname=$HOST"
ssh $HOST hostname < /dev/null
done < hosts
来源:https://stackoverflow.com/questions/58449272/bash-while-loop-ends-execution-when-ssh-is-in-loop-body