组合多个awk输出以在一行上打印

时间:2017-11-01 06:13:34

标签: awk zsh

我有两个不同的函数,每个函数都有自己的AWK来搜索多个目录中的特定文件并输出我需要的信息。这两个函数都打印FILENAME和我需要的特定字段,并且可以自行工作。我想将它们组合在一起以获得更强大的输出。

我不是程序员。我在阅读awk的同时写了这些文章。

功能1

cver () {
X=""
case $1 in
("-b") X="bb";;
("-c") X="cpe";;
("-e") X="etech";;
("-k") X="core";;
("-o") X="ohgov";;
("-h"|help) echo "'cver' allows us to see the software version 
running on all Company Juniper devices.\n'cver' is especially helpful 
in determining which devices require a software upgrade.\n\nOptions 
are -b for bb, -c for cpe, -e for etech, -k for core, and -o for 
ohgov.\n\nUse grep to find specific information. Ex: cver -c | grep 
name";;
(*) echo "Unrecognized or incomplete command.\nUse -h for help.";;
  esac
[ $X ] && awk -vSRCH="$3" '/JUNOS/ && /boot/ && $5 ~ "^[[]" SRCH  
{sub ("/show.version", "", FILENAME); sub (".*/", "", FILENAME); 
print $5 " " FILENAME}' ~/svn/nw_config_data/*${X}.domain.net/show.version | sort
}

输入/输出示例:

% cver -k   <---input
[11.4R10.3] device.core.domain.net <---ouput

功能2

cmod () {
X=""
case $1 in
("-b") X="bb";;
("-c") X="cpe";;
("-e") X="etech";;
("-k") X="core";;
("-o") X="ohgov";;
esac
awk '/Model/ {sub ("/show.version", "", FILENAME);
sub (".*/", "", FILENAME); print FILENAME " " $2}' 
~/svn/nw_config_data/*${X}.domain.net/show.version | sort
}

输入/输出示例:

% cmod -k <---input
device.core.domain.net mx480 <---output

这些脚本正在进行的是〜/ svn / nw_config_data /目录,并存储了我们部署的每个设备的目录。在每个设备目录中,都有配置文件以及一些show命令。我担心的文件是show.version文件和几行信息。对于&#34; cver&#34;我想要JUNOS Base OS启动信息。对于&#34; cmod&#34;我想要Model的信息。 &#34; X&#34;然后将获取不同的设备选项,如-b =&#34; bb&#34; (device.bb.domain.net)

以下是show.version文件的示例。

Hostname: device-r0
Model: ex3300-24t
JUNOS Base OS boot [12.3R7.7]
JUNOS Base OS Software Suite [12.3R7.7]
JUNOS Kernel Software Suite [12.3R7.7]
JUNOS Crypto Software Suite [12.3R7.7]
JUNOS Online Documentation [12.3R7.7]
JUNOS Enterprise Software Suite [12.3R7.7]
JUNOS Packet Forwarding Engine Enterprise Software Suite [12.3R7.7]
JUNOS Routing Software Suite [12.3R7.7]
JUNOS Web Management [12.3R7.7]
JUNOS FIPS mode utilities [12.3R7.7]

我试着在最近几天搜索任何类似的例子并且做得很短。我看到一个答案说管道awk,但它只打印第二个awk信息。

然后我尝试了&amp;&amp; awk而不是管道它,它让我更接近,但打印第一个awk然后打印第二个awk在单独的行上,我希望它们合并。

&安培;&安培;例如:

cver () {
X=""
case $1 in
("-b") X="bb";;
("-c") X="cpe";;
("-e") X="etech";;
("-k") X="core";;
("-o") X="ohgov";;
("-h"|help) echo "'cver' allows us to see the software version 
running on all Company Juniper devices.\n'cver' is especially helpful 
in determining which devices require a software upgrade.\n\nOptions 
are -b for bb, -c for cpe, -e for etech, -k for core, and -o for 
ohgov.\n\nUse grep to find specific information. Ex: cver -c | grep 
name";;
(*) echo "Unrecognized or incomplete command.\nUse -h for help.";;
  esac
[ $X ] && awk -vSRCH="$3" '/JUNOS/ && /boot/ && $5 ~ "^[[]" SRCH 
{sub ("/show.version", "", FILENAME); sub (".*/", "", FILENAME); 
print $5 " " FILENAME}' ~/svn/nw_config_data/*${X}.domain.net/show.version 
| sort && awk '/Model/ {sub ("/show.version", "", FILENAME); 
sub (".*/", "", FILENAME); print $2}' 
~/svn/nw_config_data/*${X}.domain.net/show.version | sort

输入/输出示例:

% cver -k <---input
[11.4R10.3] device.core.domain.net <---output
mx480 <---output

我希望输入/输出为:

% cver -k <---input
device.core.domain.net mx480 [11.4R10.3] <---output

我认为命令的打印部分看起来像

print FILENAME " " $2 " " $5

我还试过添加/ Model /&amp;&amp;我的第一个功能是2美元,但它并没有给我任何输出,而我现在就输了。

示例:

cver () {
X=""
case $1 in
("-b") X="bb";;
("-c") X="cpe";;
("-e") X="etech";;
("-k") X="core";;
("-o") X="ohgov";;
("-h"|help) echo "'cver' allows us to see the software version 
running on all Company Juniper devices.\n'cver' is especially helpful 
in determining which devices require a software upgrade.\n\nOptions 
are -b for bb, -c for cpe, -e for etech, -k for core, and -o for 
ohgov.\n\nUse grep to find specific information. Ex: cver -c | grep 
name";;
(*) echo "Unrecognized or incomplete command.\nUse -h for help.";;
  esac
[ $X ] && awk -vSRCH="$3" '/JUNOS/ && /boot/ && $5 && /Model/ && $2 ~ "^[[]" SRCH  
{sub ("/show.version", "", FILENAME); sub (".*/", "", FILENAME); 
print FILENAME " " $2 " " $5}' ~/svn/nw_config_data/*${X}.domain.net/show.version | sort

2 个答案:

答案 0 :(得分:1)

您的awk代码非常复杂;我已经在这里大大缩短了你希望(和其他人)更容易理解的内容!

/PATTERN/{STATEMENT}匹配时,EXPRESSION行评估PATTERN。因此,使用该标准分配给变量是一件非常简单的事情。然后在END块中打印我们收集的信息(而不是弄乱文件名,只需使用-v标志直接传递所需信息即可设置变量。)

#!/bin/zsh

cver () {
    svn="$HOME/svn/nw_config_data"
    case "$1" in
        ("-b")
            host="bb.domain.net"
            ;;
        ("-c")
            host="cpe.domain.net"
            ;;
        ("-e")
            host="etech.domain.net"
            ;;
        ("-k")
            host="core.domain.net"
            ;;
        ("-o")
            host="ohgov.domain.net"
            ;;
        ("-h"|help)
            echo "'cver' allows us to see the software version running on all Company Juniper devices.\n'cver' is especially helpful in determining which devices require a software upgrade.\n\nOptions are -b for bb, -c for cpe, -e for etech, -k for core, and -o for ohgov.\n\nUse grep to find specific information. Ex: cver -c | grep name\n"
            exit 0
            ;;
        (*)
            echo "Unrecognized or incomplete command.\nUse -h for help.\n"
            exit 2
            ;;
    esac
    awk -v "h=$host" '/^JUNOS Base OS boot/{v=$5} /^Model/{m=$2} END{printf("%s %s %s\n",h,m,v)}' "$svn/$host/show.version"
}

答案 1 :(得分:0)

我刚刚向同事提到这个脚本,发现他有一些编程经验。他决定对miken32提供的内容进行一次尝试,并提出了一个完全符合我要求的工作脚本。

现在,我们计划在不久的将来扩展此脚本以准确地提取更多信息,因为瞻博网络没有跨软件版本标准化他们的show.version信息,以及提取信息我们需要我们在现场部署的少数思科设备,因为这个脚本是基于Juniper的。

我们添加了一个&#34; -a&#34;拉取所有主机的选项。 dirs部分允许我们查看所有选择的主机(-b,-c,-e等),并在for循环中弹出它以防止填充重复信息。我稍后会在旧cver中添加帮助和(*)选项。

我原来的cver脚本的目的只是为了提取我们所有设备的软件版本,以便我们可以开始规划维护窗口以升级Juniper软件。然后我决定看到模型也很好,所以我编写了cmod脚本来获取模型。我们需要这些信息,因为某些型号在软件升级过程中存在错误(mx80),需要在加载软件之前进行抢先重启。

此脚本非常适合在ISP工作的任何人,甚至是部署了大量路由器和交换机的企业环境。现在,您可以快速获取这些设备上的信息,而无需登录每个设备并手动运行命令来获取此信息。

现在,新的和改进的cver!

#!/usr/local/bin/zsh
svn="$HOME/svn/nw_config_data/"
 case "$1" in
   ("-a")
   hosts=""
   ;;
   ("-b")
   hosts=".bb.domain.net"
   ;;
   ("-c")
   hosts=".cpe.domain.net"
   ;;
   ("-e")
   hosts=".etech.domain.net"
   ;;
   ("-k")
   hosts=".core.domain.net"
   ;;
   ("-o")
   hosts=".ohgov.domain.net"
   ;;
 esac

dirs=($(ls -d $svn*$hosts*))
for hostdir in $dirs
do
host=$(echo $hostdir | grep -Eo "(\w|\.|-)*$")

awk -v h=$host '/^JUNOS Base OS boot/{v=$5} /^Junos:/{v="["$2"]"} /^Model/{m=$2} END{if(m!="number"){printf("%s %s %s\n",h,m,v)}}' "$hostdir/show.version"
done