起因


進入網路工程師這個領域快1年了,遇到了幾次需要大量並且重複的動作,接著發現有些東西是可以寫一些腳本來自動執行,所以就開始找相關資料來編寫了。

使用環境

基本上還是基於linux的執行,linux內請安裝expect。


apt-get install expect -y

mac os 預設內建就有請查看/usr/bin/expect
目前我是使用在windows10內開啟ubuntu bash的方式,真的頗開心windows把這東西加進來。

文件介紹

這邊要介紹一些執行的文件

-device-list.txt 連線的設備ip清單
-cisco.sh 主要執行,並且呼叫expect執行
-configure-cisco.exp 所有執行expect的設定
-file_process.sh 文件整理
-results.log 執行完後的資料

文件編寫

1.首先我們先建立一份需要連線的設備清單,並取名為device-list.txt。

2.建立cisco.sh的文件,並在裡面加入以下內容


##!/bin/bash
# input the telnet username,password and enable passwords/輸入telnet連線時需要的帳號密碼
 echo -n "Enter the telnet username : "
 read -s -e user
 echo -ne '\n'
 echo -n "Enter the password : "
 read -s -e password
 echo -ne '\n'
 echo -n "Enter the Enable password : "
 read -s -e enable
 echo -ne '\n'
# Feed the expect script a device list & the collected passwords/向expect腳本提供以上輸入的資料
for device in `cat device-list.txt`; do
 ./configure-cisco.exp $device $user $password $enable ;
 done

3.建立configure-cisco.exp文件,並加入以下內容


#!/usr/bin/expect -f

# Set variables/設定變量
 set timeout 3
 set hostname [lindex $argv 0]
 set username [lindex $argv 1]
 set password [lindex $argv 2]
 set enablepassword [lindex $argv 3]

# Log results/儲存log檔
 log_file -a  results.log

# Announce which device we are working on and at what time/宣布我們正在處理哪個設備以及在什麼時候
 send_user "\n"
 send_user ">>>>>  Working on $hostname @ [exec date] <<<<<\n"
 send_user "\n"

# telnet /telnet連線
 spawn telnet $hostname

 expect "Username:" {
   send "$username\n"
   expect "Password:"
   send "$password\n"

   expect ">" {
     send "en\n"
     expect "Password:"
     send "$enablepassword\n"
     expect "*#"
   }

   # Enter your commands here. Examples listed below/在此輸入您的命令。 下面列出的例子
    #send "conf t\n"
    #expect "(config)#"
    #send "int vlan1 \n"
    #expect "(config-if)#"
    #send "ip address 192.168.1.1 255.255.255.0 \n"
    #expect "(config-if)#"
    #send "no shunt\n"
    #expect "(config-if)#"
    #send "exit"
    #expect "(config)#"

   #備份資料設定並存檔(cisco設備存檔)

   send "terminal length 0 \n"
   expect "#"
   send "show version \n"
   expect "#"
   send "show clock \n"
   expect "#"
   send "show inventory \n"
   expect "#"
   send "show ntp status \n"
   expect "#"
   send "show run \n"
   expect "#"
   send "show vlan \n"
   expect "#"
   send "show vtp status \n"
   expect "#"
   send "show spann acti \n"
   expect "#"
   send "show interface status \n"
   expect "#"
   send "show interface \n"
   expect "#"
   send "show interface description \n"
   expect "#"
   send "show interface trunk \n"
   expect "#"
   send "show port-security address \n"
   expect "#"
   send "show etherchannel summary \n"
   expect "#"
   send "show ip interface brief \n"
   expect "#"
   send "show ip access-list \n"
   expect "#"
   send "show ip route \n"
   expect "#"
   send "show standby brief \n"
   expect "#"
   send "show cdp neighbors \n"
   expect "#"
   send "show cdp neighbors de \n"
   expect "#"
   send "show standby brief \n"
   expect "#"
   send "show monitor \n"
   expect "#"
   send "show logging \n"
   expect "#"
   send "terminal length 24 \n"
   expect "#"
   send "write \n"
   expect "#"
   send "exit\n"
   expect ":~\$"
   # Announce which device we are end of work/宣布結束在這個設備的工作
    send_user "\n"
    send_user ">>>>>  end of work $hostname  <<<<<\n"
    send_user "\n"
   exit
 }

4.建立file_process.sh,並加入以下內容


#!/bin/bash
#建立log資料夾與底下的日期資料夾
mkdir -p log/`date +%Y-%m-%d`
filename='device-list.txt'
#讀取device-list.txt,建立以ip為名稱的txt,並儲存到log/2018-xx-xx的日期資料夾內。
READFILE=$filename
while read line; do
     sed -n '/>>>>>  Working on '$line' /,/>>>>>  end of work '$line'  <<<< log/`date +%Y-%m-%d`/$line.txt
done < $READFILE

### 5.更改成ssh
telnet是比較少使用的連線方式,比較常見的是ssh,以下提供ssh的方式,一樣是寫在configure-cisco.exp內。


#!/usr/bin/expect -f

# Set variables
 set hostname [lindex $argv 0]
 set username [lindex $argv 1]
 set password [lindex $argv 2]
 set enablepassword [lindex $argv 3]

# Log results
 #log_file -a ~/expect/results.log
 log_file -a results.log

# Announce which device we are working on and at what time
 send_user "\n"
 send_user ">>>>>  Working on $hostname @ [exec date] <<<<<\n"
 send_user "\n"

# Don't check keys
 spawn ssh -o StrictHostKeyChecking=no $username\@$hostname

# Allow this script to handle ssh connection issues
 expect {
 timeout { send_user "\nTimeout Exceeded - Check Host\n"; exit 1 }
 eof { send_user "\nSSH Connection To $hostname Failed\n"; exit 1 }
 "*#" {}
 "*assword:" {
 send "$password\n"
 }
 }

# If we're not already in enable mode, get us there
 expect {
 default { send_user "\nEnable Mode Failed - Check Password\n"; exit 1 }
 "*#" {}
 "*>" {
 send "enable\n"
 expect "*assword"
 send "$enablepassword\n"
 expect "*#"
 }
 }

# Let's go to configure mode
 #send "conf t\n"
 #expect "(config)#"
 send "terminal length 0 \n"
 expect "#"
 send "show version \n"
 expect "#"
 send "show run \n"
 expect "#"
 send "terminal length 24 \n"
 expect "#"

# Enter your commands here. Examples listed below
 #send "tacacs-server host 10.0.0.5\n"
 #expect "(config)#"
 #send "tacacs-server directed-request\n"
 #expect "(config)#"
 #send "tacacs-server key 7 0000000000000\n"
 #expect "(config)#"
 #send "ntp server 10.0.0.9\n"
 #expect "(config)#"
 #send "ip domain-name yourdomain.com\n"
 #expect "(config)#"

 send "end\n"
 expect "#"
 send "write \n"
 expect "#"
 send "exit\n"
 expect ":~\$"
 # Announce which device we are end of work
 send_user "\n"
 send_user ">>>>>  end of work $hostname  <<<<<\n"
 send_user "\n"
 exit

6.總結

每次遇上大量相同的更動,或者需要紀錄設定檔時,這份script大概可以幫上大忙吧。

資料來源:https://paulgporter.net/2012/12/08/30/
http://corecoding.com/cisco-expect-script_c32.html

Facebook 功能: