Breaking from a while LoopUse the break statement to exit a while loop when a particular condition realizes. The following script uses a break inside a while loop: #!/bin/bash i=0 while [[ $i -lt 11 ]] do if [[ "$i" == '2' ]] then echo "Number $i!" break fi echo $i ((i++)) done echo "Done!"
and >&2 means send the output to STDERR, So it will print the message as an error on the console. You can understand more about shell redirecting from those references: https://www.gnu.org/savannah-checkouts/gnu/bash/manual/bash.html#Redirections.
break command is used to terminate the execution of for loop, while loop and until loop. It can also take one parameter i.e.[N]. Here n is the number of nested loops to break. The default number is 1.
A bash for loop is a bash programming language statement which allows code to be repeatedly executed. A for loop is classified as an iteration statement i.e. it is the repetition of a process within a bash script. For example, you can run UNIX command or task 5 times or read and process list of files using a for loop.
Chris is correct. The source of the loop breaking was SSH using stdin, however guns is correct in is usage of a looping methodology.
If you are looping through input (a file with a list of hostnames for example), and calling SSH, you need to pass the -n parameter, otherwise your loop based on input will fail.
while read host; do
ssh -n $host "remote command" >> output.txt
done << host_list_file.txt
In the construct
something |
while read x; do
ssh ...
done
the standard input as seen by the while loop is the output of something
.
The default behavior of ssh
is to read standard input. This allows you to do things like
cat id_rsa.pub | ssh new_box "cat - >> ~/.ssh/authorized_keys"
Now, with that being said, when the first value is read, the first ssh command will read the entire input from something
. Then, by the time ssh finishes, there is no output left, and read
stops.
The fix is ssh -n ...
e.g.
cat /etc/hosts | awk '{print $2}' | while read x; do
ssh -n $x "do_something_on_the_machine"
done
Most of the answers are specific to ssh. Other commands also hijack stdin and do not have a -n option. This should address any other commands. This should also work for ssh.
while read x; do
# Make sure command does not hijack stdin
echo "" | command $x
done < /path/to/some/file
I ran into this today -- rsh and/or ssh can break a while read loop due to it using stdin. I put a -n into the ssh line which stops it from trying to use stdin and it fixed the problem.
Don't know if it would help, but a cleaner way of writing that would be
for nu in `ruby -e '(0..20).each { |i| puts i}'`; do
tssh "MYBOXES$nu"
done
I'm also unsure about why it fails, but i like xargs
and seq
:
seq 0 20 | xargs -n1 tssh MYBOXES
As Kaii mentioned, it's really overkill to call ruby or seq (which won't work on BSD or OSX machines) just to output a range of numbers. If you're happy with using bash you can:
for i in {0..20}; do
# command
done
I believe this should work for bash 2.05b and up.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With