Linux在awk中批量执行ssh命令操作

来自三线的随记

在管理多节点的时候难免会有不方便 / 不想使用 ansible 但是又想批量执行命令的情况

然后想使用 awk 结合 ssh 去执行的时候会发现实际上只有第一个节点执行了相应的操作

如下所示

[root@node-1 ~]# cat nodes.txt
172.16.44.44
172.16.44.45
[root@node-1 ~]# cat nodes.txt |awk '{print "ssh -p12722 -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null "$1 " hostname"}'
ssh -p12722 -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null 172.16.44.44 hostname
ssh -p12722 -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null 172.16.44.45 hostname
[root@node-1 ~]# cat nodes.txt |awk '{print "ssh -p12722 -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null "$1 " hostname"}'|sh
Warning: Permanently added '[172.16.44.44]:12722' (ECDSA) to the list of known hosts.
compute-1
[root@node-1 ~]#


还有这种类似的误报 Permission denied

[root@node-1 ~]# cat nodes.txt |awk '{print "ssh -p12722 -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null "$1 }'|sh
Pseudo-terminal will not be allocated because stdin is not a terminal.
Warning: Permanently added '[172.16.44.44]:12722' (ECDSA) to the list of known hosts.
Pseudo-terminal will not be allocated because stdin is not a terminal.
Warning: Permanently added '[172.16.44.45]:12722' (ECDSA) to the list of known hosts.
Permission denied, please try again.
Permission denied, please try again.
Permission denied (publickey,gssapi-keyex,gssapi-with-mic,password).


这种情况下都是只需要给ssh加个-n 参数即可

     -n      Redirects stdin from /dev/null (actually, prevents reading from stdin).  This must be used when ssh is run in the background.  A common trick is to use this to run X11 programs on a remote machine.  For example, ssh -n shadows.cs.hut.fi emacs & will start an emacs on shadows.cs.hut.fi, and the X11 connection will be automatically forwarded over an encrypted channel.  The ssh program will be put in the background.  (This does not work if ssh needs to ask for a password or passphrase; see also the -f option.)

注意其中也提到了This does not work if ssh needs to ask for a password or passphrase, 如果remote节点没有做免密认证的话,这时候就应该使用 -f 参数

     -f      Requests ssh to go to background just before command execution.  This is useful if ssh is going to ask for passwords or passphrases, but the user wants it in the background.  This implies -n.  The recommended way to start X11 programs at a remote site is with something like ssh -f host xterm.

             If the ExitOnForwardFailure configuration option is set to “yes”, then a client started with -f will wait for all remote port forwards to be successfully established before placing itself in the background.

但是实测下来 -n 的回显效果相对于 -f 更为人性化

实际效果如下(warning msg已被重定向减少无用信息):

[root@node-1 ~]# cat nodes.txt |awk '{print "2>/dev/null ssh -p12722 -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null -f "$1 " hostname"}'|sh
compute-1
[root@node-1 ~]# compute-2
[root@node-1 ~]# cat nodes.txt |awk '{print "2>/dev/null ssh -p12722 -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null -n "$1 " hostname"}'|sh
compute-1
compute-2
[root@node-1 ~]#