I personally would use
Code:
#!/bin/bash
while read server dummy ; do
[ "${server//[#\/;]/}" = "$server" ] || continue
[ "${#server}" -gt 0 ] || continue
ssh "$server" "$@" </dev/null &>"$server.log" &
done
wait
The command to run is specified as a parameter to the script, and the list of servers as input, i.e.
Code:
./script ls -laF < servers.txt
The
dummy variable makes sure the
server will only contain the first word on each line. You may wish to extend the format later, so requiring the first word to be the server name makes sense.
The first test makes sure the server name does not contain hashes (
#), slashes (
/), or semicolons (
;). Hash and semicolon are often used to indicate a comment line. Slash would make it impossible to create a file based on the server name. None of the three should occur in a server name or address anyway.
The second test makes sure the server name is not empty. Empty lines are common at the end of files, so handling them gracefully is a good idea.
The ampersand (
&) backgrounds each ssh command, and the final
wait waits until all ssh commands have completed. Since the ssh commands are done in parallel, I redirect the input to the ssh commands from /dev/null -- no user input is possible. It would not make sense to allow it anyway, because you could not tell which ssh command you were supplying input to.