我希望使用 bash 或 python 中的腳本實現自動化。
假設我有一個來自設備的設定檔。一個簡單的 config.txt 檔案。內容可能是這樣的(實際文件更長並且有更多文字):
> cat config.txt
>
> ASA Version 9.1(5)
> !
> terminal width 511
> hostname confidential
> domain-name confidential
> enable password encrypted
> passwd encrypted
> names
> !
> interface GigabitEthernet0/0
> nameif interconnection
> security-level 50
> ip address 1.1.1.1 255.255.255.240 standby 1.1.1.1
> !
> interface GigabitEthernet0/1
> description Trunk
> no nameif
> no security-level
> no ip address
> !
> interface GigabitEthernet0/1.4
> description confidential
> vlan 4
> nameif vlan004_confidential
> security-level 50
> ip address 1.1.1.1 255.255.255.0
> !
> object network confidential
> host 2.2.2.2
> object network confidential2
> host 3.3.3.3
> object network confidential3
> host 4.4.4.4
>!
>access-list vlan65_access_in extended permit object-group confidential any object-group confidential
>access-list vlan65_access_in remark Allow ICMP OK-20131105
>access-list vlan65_access_in extended permit icmp any object vlan48-confidential
>access-list vlan65_access_in remark Allow NTP OK-20131105
>access-list vlan65_access_in extended permit udp any object-group confidential eq ntp
>access-list warehouse_access_in remark Access to confidential
>access-list warehouse_access_in extended permit object-group confidential any object-group confidential
>access-list warehouse_access_in remark Access to DNS srvrs
>access-list warehouse_access_in extended permit ip any object-group DNS_Servers
>access-list warehouse_access_in remark Allow acces to AD
>!
>no pager
>logging enable
>logging timestamp
>logging standby
>logging list SysLogs message 304001
>logging list connections message 302013-302304
>logging list NewConnection message 302303
>logging list NewConnection message 302015
>logging list NewConnection message 302013
>logging list NewConnection message 303002
>logging list Dropped message 106001-106103
>logging list ConfigChange message 111008
>logging list ConfigChange message 111001
>logging list ConfigChange message 111010
>logging buffer-size 1048576
>logging monitor debugging
>logging buffered warnings
>!
>access-group vlan4_access_in in interface vlan004_confidential1
>access-group vlan65_access_in in interface vlan065_confidential2
>access-group vlan66_access_in in interface vlan066_confidential3
>access-group vlan80_access_in in interface vlan080_confidential4
>!
>service-policy global_policy global
>service-policy test interface interconnection
>service-policy imec_intranet_traffic-policy interface vlan065_confidential5
>service-policy imec_intranet_traffic-policy interface vlan066_confidential6
>service-policy imec_intranet_traffic-policy interface vlan080_confidential7
>service-policy imec_intranet_traffic-policy interface vlan082_confidential8
>service-policy imec_intranet_traffic-policy interface vlan083_confidential9
>!
>: end
我的第二個檔案是一個清單(list.txt)。內容和佈局是這樣的(在記事本++中):
列表.txt
>username full name employid group left comp on
>----------------------------------------------------------------------------------
>test16 confidential1 00014241 zzzz1 19-08-2017
>test38 confidential2 00014223 zzzz2 12-08-2017
>test47 confidential3 00013986 zzzz3 06-07-2017
>test85 confidential4 00013923 zzzz4 16-07-2017
是否可以執行一個腳本,取得 list.txt 檔案中「使用者名稱」和「全名」列中的每個單字,並檢查 config.txt 檔案中是否存在匹配項?最好將腳本的輸出放在第三個檔案中,其中提及在 config.txt 檔案中找到的單字(此處為使用者名稱或全名)以及位置。
假設我想知道 test38 是否位於 config.txt 檔案中的某個位置?我現在可以簡單地 grep,但我的 list.txt 檔案有大約 100 個使用者。我不想 grep 100 次。最重要的是,我將來會得到更多的清單。
答案1
這是一個完成這項工作的 perl 腳本,(據我所知):
#!/usr/bin/perl
use strict;
use warnings;
my $config = 'config.txt'; # give the full path
my $list = 'list.txt'; # give the full path
my $outfile = 'outfile.txt'; # give the full path
# read list file and store in a hash
open my $fhl, '<', $list or die "unable to open '$list': $!";
my %users;
while(my $line = <$fhl>) {
next if $. < 3; # skip first 2 lines (header)
my ($user, $name) = split(/\s+/, $line);
$users{$user} = $name if $user and $name;
}
close $fhl;
open my $fhc, '<', $config or die "unable to open '$config': $!";
open my $out, '>', $outfile or die "unable to open '$outfile': $!";
# read config line by line
while(my $line = <$fhc>) {
# loop on all users
while( my ($u,$n) = each(%users)) {
# print outputfile if user found
print $out "$u:$n found line $.\n" if $line =~ /\b($u|$n)\b/;
}
}
給定範例的輸出文件
test38:confidential2 found line 30
test47:confidential3 found line 32
答案2
根據我個人對你的要求的理解,我使用內建命令while
和命令awk
來解決它。
直接輸出
awk 'NR>2{print $1,$2}' list.txt | while IFS=" " read -r username fullname; do awk -v name="${username}" 'BEGIN{OFS="|"}match($0,/'"${fullname}"'/){gsub(/>/,"",name);print name,NR,$0}' config.txt; done
將輸出寫入文件output.txt
awk 'NR>2{print $1,$2}' list.txt | while IFS=" " read -r username fullname; do awk -v name="${username}" 'BEGIN{OFS="|"}match($0,/'"${fullname}"'/){gsub(/>/,"",name);print name,NR,$0>>"output.txt"}' config.txt; done
輸出格式是
user name|line no.|match content
結果輸出
test16|64|>access-group vlan4_access_in in interface vlan004_confidential1
test38|30|> object network confidential2
test38|65|>access-group vlan65_access_in in interface vlan065_confidential2
test47|32|> object network confidential3
test47|66|>access-group vlan66_access_in in interface vlan066_confidential3
test85|67|>access-group vlan80_access_in in interface vlan080_confidential4