![如何在一行中编写以下脚本?](https://linux22.com/image/164360/%E5%A6%82%E4%BD%95%E5%9C%A8%E4%B8%80%E8%A1%8C%E4%B8%AD%E7%BC%96%E5%86%99%E4%BB%A5%E4%B8%8B%E8%84%9A%E6%9C%AC%EF%BC%9F.png)
#Gives a list of servers and their instance
for server instance in `/swb/local/scripts/swdList -p SMARTS -a A5SV_2017.1b -e 1 --type=instance --function=SAM --priority=1 | grep -v sis`
do
echo "===== $server - $instance ====="
#Reason for single line, gotta run this on remote servers
sudo ssh $server "`/swb/local/scripts/amprov /swb/local/scripts/estools/getProperty -s $sam_instance ICS_Notification Active SourceDomainName 2>/dev/null | grep "Partition-" | grep TRUE | awk '{print $1}' | sed 's/NOTIFICATION-Partition_//' | sed 's/_Down//' | sort`; do echo "===== Partition alarm "$alarming_partition" on "$sam_instance" ====="; ampm_instance=`echo $alarming_partition | awk -F\/ '{print $2}'`; for device_in_partition in `/swb/opt/InCharge9/IP/smarts/bin/dmctl -s ${ampm_instance} get Partition:: ${alarming_partition}::ConsistsOf | tr ' ' '\n' | grep '::' | awk -F\: '{print $3}'`; do echo -n $device_in_partition; vzb_qap=`/swb/opt/InCharge9/IP/smarts/bin/dmctl -s ${ampm_instance} get UnitaryComputerSystem::${device_in_partition}::vzb_qap`; echo -n ",vzb_qap="$vzb_qap; device_alarm=`/swb/local/scripts/amprov /swb/local/scripts/estools/getProperty -s $sam_instance ICS_Notification Active SourceDomainName 2>/dev/null | grep TRUE | grep '_Down' | egrep -v '(Interface|BGP)' | grep $device_in_partition | awk '{print $1}'`; echo -n ",UCS_alarm="$device_alarm; echo; done;"
echo
done
PS:非常感谢大家的回复,我的错,我试图通过减少内容来使其看起来不那么复杂,但这就是我所写的。
答案1
我能够抑制自己哭泣的冲动,足够长的时间来自由地应用;
到你的脚本中,以使其成为一行:
Y= [...]; for X in `shell command $Y`; do echo "=== "$X" on "$Y" ==="; Z=`echo $X | awk -F\/ '{print $2}'`; for W in `shell command ${Z} awk -F\: '{print $3}'`; do echo -n $W; V=`shell command ${Z} ${W}`; echo -n ",V="$V; U=`shell command $Y`; echo -n ",T="$U; echo; done; echo; done
另外:它不起作用,至少因为Y= [...]
这不是一个有效的命令,但也可能是其他原因。
答案2
我建议,尽管我完全同意您的帖子下面的评论,但首先写得尽可能短(除了习惯不使用反引号之外,一个字符更一般地为您节省了很多复杂/嵌套命令的麻烦替代案例)。
Y=[...]
for X in $(shell command $Y); do
echo ===\ $X\ on\ $Y\ ===
Z=$(echo $X | cut -d/ -f2)
for W in $(shell command $Z | cut -d: -f3); do
echo $W,V=$(shell command $Z $W),T=$(shell command $Y)
done
echo
done
然后删除所有不需要的标识,同时用分号替换所需的(=有意义的)换行符(+空白以提高可读性)。
Y=[...]; for X in $(shell command $Y); do echo ===\ $X\ on\ $Y\ ===; Z=$(echo $X | cut -d/ -f2); for W in $(shell command $Z | cut -d: -f3); do echo $W,V=$(shell command $Z $W),T=$(shell command $Y); done; echo; done
如果您的目标是使其尽可能短,您可以删除所有不需要的空格:
Y=[...];for X in $(shell command $Y);do echo ===\ $X\ on\ $Y\ ===;Z=$(echo $X|cut -d/ -f2);for W in $(shell command $Z|cut -d: -f3);do echo $W,V=$(shell command $Z $W),T=$(shell command $Y);done;echo;done
或者,如果您想以不同的方式进行操作,您可以尝试:
Y=[...];shell command $Y|xargs -n1 bash -c "echo ===\\ \$1\\ on\\ $Y\\ ===;Z=\$(echo \$1|cut -d/ -f2);shell command \$Z|cut -d: -f3|xargs -n1 bash -c \"echo \\\$1,V=\\\$(shell command \$Z \\\$1),T=\\\$(shell command $Y)\";echo"
或者:
Y=[...];bash -c "for X in \$*;do echo ===\ \$X\ on\ \$*\ ===;bash -c \"for W in \\\$(shell command \\\$*|cut -d: -f3);do echo \\\$W,V=\\\$(shell command \\\$* \\\$W),T=\\\$(shell command $Y)\";echo\$(echo \$X|cut -d/ -f2)" $(shell command $Y)
另外,如果 $(shell 命令) 始终是相同的 shell 命令,您可能需要优化它(放弃 shell 和 wrtie 命令,而不是之前从它创建一个 var,例如:
Y=[...];C='shell command';for X in $($C $Y);do echo ===\ $X\ on\ $Y\ ===;Z=$(echo $X|cut -d/ -f2);for W in $($C $Z|cut -d: -f3);do echo $W,V=$($C $Z $W),T=$($C $Y);done;echo;done
甚至:
Y=[...];C='shell command';E=echo;for X in $($C $Y);do $E ===\ $X\ on\ $Y\ ===;Z=$($E $X|cut -d/ -f2);for W in $($C $Z|cut -d: -f3);do $E $W,V=$($C $Z $W),T=$($C $Y);done;$E;done
尤其是最后一个看起来非常技术性,我想我更喜欢将其作为一行:-D
答案3
使用env_parallel
GNU Parallel。
您的代码确实很难阅读,并且其他人也很难维护。如果将其分成较小的函数并导出到远程服务器,则会更容易。
env_parallel --session
servers() {
/swb/local/scripts/swdList -p SMARTS -a A5SV_2017.1b -e 1 --type=instance --function=SAM --priority=1 |
grep -v sis
}
doit() {
# Run this on every server
}
env_parallel --nonall --slf <(servers) doit