【发布时间】:2019-02-04 14:23:52
【问题描述】:
过去我收到了一些有用的回复,希望大家能帮助我。我遇到了一些我无法确定的奇怪行为。我正在处理 Cisco 交换机的配置文件,并希望生成列出 VLAN IP 地址的输出,格式如下:
Vlan1:172.31.200.1 255.255.255.0
Vlan10:172.40.220.1 255.255.255.0
“Vlan”将被捕获在一个变量中,IP/掩码是使用“sed”提取的,它在大多数情况下都有效。有时它会拒绝填充“vlan”变量,尽管它看起来对其他配置很有效。
如果只有一个 VLAN,它只会处理那个 VLAN,如果有多个 VLAN,它会处理额外的 VLAN。如果用户选择 (-v) 它在列表中包括 VLAN1,则配置了多个 VLAN(否则它会忽略 VLAN1)。
此输入文件出现损坏(文件名 1.cfg):
!
interface Vlan1
ip address 172.29.96.100 255.255.255.0
!
ip default-gateway 172.29.96.1
ip http server
no ip http secure-server
!
这个输入文件可以正常工作(文件名 2.cfg):
!
interface Vlan1
ip address 172.31.200.111 255.255.255.0
no ip route-cache
!
ip default-gateway 172.31.200.1
ip http server
ip http secure-server
我得到的输出是这样的:
注意第一个没有包含“Vlan1”引用?
这是我的脚本:
#!/bin/bash
if [ -f getlan.log ];
then
rm getlan.log
fi
TempFile=getlan.log
verbose=0
while [[ $# -gt 0 ]]
do
key="$1"
case $key in
-v)
verbose=1
shift
;;
#*)
#exit
#shift
#;;
esac
done
#Start Processing all files
files=$( ls net )
for i in $files; do
#########################################################
# Collect Configured VLAN Interfaces and IP Information #
#########################################################
echo "-------- Configured VLAN Interfaces --------" >> ~/$TempFile
echo "" >> ~/$TempFile
if [ `grep "^interface Vlan" ~/net/$i | awk '{ print $2 }' | wc -l` -gt 1 ];
then
for g in `grep "^interface Vlan" ~/net/$i | awk '{ print $2 }'`;
do
if [ $g == "Vlan1" ];
then
if [ $verbose -gt 0 ];
then
echo "$g": `sed -n '/^interface '$g'/,/!/p' ~/net/$i | head -n 5 | grep -i "ip address" | awk '{ print $3, $4 }'` >> ~/$TempFile
fi
else
echo "$g": `sed -n '/^interface '$g'/,/^!/p' ~/net/$i | grep -i "ip address" | awk '{ print $3, $4 }'` >> ~/$TempFile
fi
done
echo "" >> ~/$TempFile
else
vlanid=`grep "^interface Vlan" ~/net/$i | awk '{ print $2 }'`
echo $vlanid: `sed -n '/^interface 'Vlan'/,/^!/p' ~/net/$i | grep -i "address" | awk '{ print $3, $4 }'` >> ~/$TempFile
echo "" >> ~/$TempFile
fi
done
如果这更一致,那就太好了。谢谢!
【问题讨论】:
-
请在您的问题中添加示例输入和该示例输入所需的输出。
-
示例包括两者...所需的输出是让行包括 Vlan(Vlan1、Vlan10 等),后跟 IP 和掩码。第二个例子是正确的。在第一种情况下,它只显示 IP/掩码。我的输入文件也显示在上面的原始描述中。
-
一般情况下
grep ... | awk '{foo}'可以换成awk '/.../ { foo }'。我通常也倾向于摆脱所有sed/head/awk/等。支持使用 BashFAQ #1while read循环来解析文件的杂项,这将更加高效和运行时间,并且附带的复杂性更少(移动部件更少)。 -
考虑通过shellcheck.net 运行您的代码并修复它找到的内容。 bash 中的引用规则可能与您对其他语言的期望相反——例如,在
[ "$g" = Vlan1 ]中,它是需要引用的变量的扩展,以便您的代码在读取空字符串或其他异常文件时能够可靠地运行内容,不是常量字符串。
标签: bash variables sed scripting