DevOps/Programmability2018.03.30 13:46
 

안녕하세요.

이번 포스팅은 현재 제가 운영진으로 활동 중인 [네트워크 전문가 따라잡기] 커뮤니티의 

'제 24회 네트워크 전문가 따라잡기 "N.EX.T" (정기기술세미나)' 에서 진행한 세션의 발표 자료입니다. 

발표 자료는 첨부하였으며, 슬라이드를 바로 보실 수 있게 사진으로도 첨부합니다.

다만, 첨부 가능한 사진이 한계가 있어서 슬라이드는 2개의 포스팅으로 나눠서 합니다. (2번째 포스팅입니다.)

[첫번째 포스팅]

 

 

Posted by 네떡지기
DevOps/Programmability2018.03.30 13:43

안녕하세요.

이번 포스팅은 현재 제가 운영진으로 활동 중인 [네트워크 전문가 따라잡기] 커뮤니티의 

'제 24회 네트워크 전문가 따라잡기 "N.EX.T" (정기기술세미나)' 에서 진행한 세션의 발표 자료입니다. 

Session2.네트워크엔지니어를위한Python101.pdf

발표 자료는 첨부하였으며, 슬라이드를 바로 보실 수 있게 사진으로도 첨부합니다.

다만, 첨부 가능한 사진이 한계가 있어서 슬라이드는 2개의 포스팅으로 나눠서 합니다.

[두번째 포스팅]

 

Posted by 네떡지기
DevOps/Programmability2018.03.30 13:30

안녕하세요.

이번 포스팅은 현재 제가 운영진으로 활동 중인 [네트워크 전문가 따라잡기] 커뮤니티의 

'제 24회 네트워크 전문가 따라잡기 "N.EX.T" (정기기술세미나)' 에서 제가 진행한 세션과 관련된 내용입니다.

이번 행사에서는  [예제로 보는 '네트워크 엔지니어를 위한 Python 101'] 이라는 주제로 세션을 하였고

세션 시간에 사용된 간단한 예제에 대해서 코드를 공유합니다.

코드에 대한 내용은 세션 시간에 다루었기 때문에 자세한 설명은 생략합니다.

그리고 본 예제에 사용된 코드는 완성형 코드는 아닙니다.

우선 대표적인 예가 예외처리가 전혀 없습니다. (기본 라이브러리에서 제공되는 부분 제외)

아래의 코드들은 처음 접근을 어렵게 생각하시는 분들을 위해서 최대한 쉽게 접근할 수 있을 정도로 짧게 짧게 만들었으며

이후에 아래의 코드들을 조금씩 변형해가면서 본인만의 코드를 만들어보면 좋을 것 같습니다.

 

예제 1) 장비 접속 및 기본 명령어 수행 및 실행

from netmiko import ConnectHandler

arista= {
    'device_type': 'arista_eos',
    'ip':   'device',
    'username': 'admin',
    'password': 'admin',
    'port' : 2222,          # 기본 값이 22포트를 사용할 경우에는 사용하지 않아도 무방


net_connect = ConnectHandler(**arista)

output = net_connect.send_command('show int desc')
print(output)

 ○ 세션 시에 IP를 숨기기 위해서 'device'라는 이름으로 사용을 하였으며, 실제로는 해당 위치에 IP가 들어가면 됩니다

   단,IP 값은 문자열이기 때문에 ' ' 혹은 " "를 사용해야 합니다.

   문자열이기 때문에 도메인 값으로 대체해도 무방합니다

 

예제 2-1) 장비 접속 및 기본 명령어 수행 및 실행

from netmiko import ConnectHandler
import device

print("Connecting....")
nwnode = ConnectHandler(**device.ARI)
shver = nwnode.send_command("show ver")
print(shver)

예제 2-2) 장비 접속 및 기본 명령어 수행 및 실행  (device.py)

ariuser='admin'
aripwd='admin'
dv='arista_eos'

ARI={'device_type':dv,'verbose':False,'username':ariuser,'password':aripwd,'ip':'device','port':2222} 

 ○ 장비 인벤토리 정보를 기능을 수행할 코드와 별도로 분리한 예제입니다.

    예제 1과 동일하지만, 단순히 인벤토리를 분리한 내용입니다

    인벤토리 정보는 py코드를 사용할 수도 있지만, 별도의 파일로 관리해서 관리도 가능할 수 있습니다.

 

예제 3-1) 장비 인터페이스 상태 출력  

shstatus ='''
Port    Name               Status       Vlan       Duplex Speed Type
Fa1/0   ZIGI-SVR0          notconnect   1            auto    auto 10/100BaseTX
Fa1/1   ZIGI-SVR1          notconnect   1            auto    auto 10/100BaseTX
Fa1/2   ZIGI-SVR2          notconnect   1            auto    auto 10/100BaseTX
Fa1/3   ZIGI-SVR3          connected   1            auto    auto 10/100BaseTX
Fa1/4   ZIGI-SVR4          notconnect   1            auto    auto 10/100BaseTX
Fa1/5   ZIGI-SVR5          notconnect   1            auto    auto 10/100BaseTX
Fa1/6   ZIGI-SVR6          connected   1            auto    auto 10/100BaseTX
Fa1/7   ZIGI-SVR7          notconnect   1            auto    auto 10/100BaseTX
Fa1/8   ZIGI-SVR8          notconnect   1            auto    auto 10/100BaseTX
Fa1/9   ZIGI-SVR9          notconnect   1            auto    auto 10/100BaseTX
Fa1/10  ZIGI-SVR10         connected   1            auto    auto 10/100BaseTX
Fa1/11  ZIGI-SVR11         notconnect   1            auto    auto 10/100BaseTX
Fa1/12  ZIGI-SVR12         notconnect   1            auto    auto 10/100BaseTX
Fa1/13  ZIGI-SVR13         notconnect   1            auto    auto 10/100BaseTX
Fa1/14  ZIGI-SVR14         notconnect   1            auto    auto 10/100BaseTX
Fa1/15  ZIGI-SVR15         notconnect   1            auto    auto 10/100BaseTX

'''

status = shstatus.split('\n')

for op in status:
    print(op)
 

○ 장비 인터페이스 정보를 출력하는 예제입니다.  

   이번 예제는 실제 장비를 접속한 것이 아니라, 장비에 접속하여 인터페이스 정보 가져온 내용을 출력하는 부분입니다.

   장비 정보를 가져오게 되면, 하나의 길 문자열로 되어 있는 데 이를 가공하는 방법에 대한 예제이며

   이 예제에서는 결과 값을 각 Line 단위로 쪼개는 함수(split)를 사용하여 정보 Line 단위로 저장하고

   저장된 값을 하나씩 가져와서 출력합니다.

 

예제 3-2) 장비 인터페이스 상태 출력 

shstatus ='''
Port    Name               Status       Vlan       Duplex Speed Type
Fa1/0   ZIGI-SVR0          notconnect   1            auto    auto 10/100BaseTX
Fa1/1   ZIGI-SVR1          notconnect   1            auto    auto 10/100BaseTX
Fa1/2   ZIGI-SVR2          notconnect   1            auto    auto 10/100BaseTX
Fa1/3   ZIGI-SVR3          connected   1            auto    auto 10/100BaseTX
Fa1/4   ZIGI-SVR4          notconnect   1            auto    auto 10/100BaseTX
Fa1/5   ZIGI-SVR5          notconnect   1            auto    auto 10/100BaseTX
Fa1/6   ZIGI-SVR6          connected   1            auto    auto 10/100BaseTX
Fa1/7   ZIGI-SVR7          notconnect   1            auto    auto 10/100BaseTX
Fa1/8   ZIGI-SVR8          notconnect   1            auto    auto 10/100BaseTX
Fa1/9   ZIGI-SVR9          notconnect   1            auto    auto 10/100BaseTX
Fa1/10  ZIGI-SVR10         connected   1            auto    auto 10/100BaseTX
Fa1/11  ZIGI-SVR11         notconnect   1            auto    auto 10/100BaseTX
Fa1/12  ZIGI-SVR12         notconnect   1            auto    auto 10/100BaseTX
Fa1/13  ZIGI-SVR13         notconnect   1            auto    auto 10/100BaseTX
Fa1/14  ZIGI-SVR14         notconnect   1            auto    auto 10/100BaseTX
Fa1/15  ZIGI-SVR15         notconnect   1            auto    auto 10/100BaseTX

'''

status = shstatus.split('\n')

for op in status:
    if(op.find('connected') > 0):
        print(op.split()[0]) 

○ 장비 인터페이스 정보를 출력하는 예제의 변형입니다.

    각 Line별로 가져온 값에서 현재 연결된 인터페이스 정보만을 출력하기 위해서 'connected'라는 값을 찾아서

    'connected'된 인터페이스만을 출력합니다.

 

 

 

예제 4-1) 장비 Uptime 출력 

shverinc = "zigi-r1 uptime is 2 hours, 27 minutes"
uptime = shverinc.split(" uptime is ")
print(uptime)

 

예제 4-2) 장비 Uptime 출력 

shverinc = "zigi-r1 uptime is 2 hours, 27 minutes"

uptime = shverinc.split(" uptime is ")
print("Device Host : {0}\t\tUptime : {1}".format(uptime[0],uptime[1]))

 ○ 장비 Uptime을 출력하는 예제입니다.

    출력된 값은 기본적으로 가져온 값을 어느 정도 수준까지 가공해서 사용할 것인지에 대한 부분입니다.

 

예제 5) 장비 Mac-address 정보 출력

shmac = '''VDX# show mac-address-table
VlanId   Mac-address       Type     State        Ports
41       0000.0000.fe00    Dynamic  Active       Te 1/5/1
41       0000.0000.fe01    Dynamic  Remote       Te 2/5/1
41       001c.7f63.950f    Dynamic  Active       Te 1/5/1
41       02e0.52b2.f50d    System   Active       XX 1/X/X
41       c4f5.7c18.3962    System   Remote       XX 2/X/X
43       0000.0000.fe00    Dynamic  Active       Po 3
43       0000.0000.fe01    Dynamic  Active       Po 4
43       001c.7f63.7efc    Dynamic  Active       Po 4
43       001c.7f69.7b76    Dynamic  Active       Po 3
43       02e0.52c3.940e    System   Active       XX 1/X/X
43       c4f5.7c18.3962    System   Remote       XX 2/X/X
701      0050.5686.049e    Dynamic  Remote       Te 15/0/14
701      0050.5686.09d9    Dynamic  Remote       Te 15/0/19
701      0050.5686.123f    Dynamic  Remote       Te 15/0/4
701      0050.5686.1384    Dynamic  Remote       Te 15/0/15
701      0050.5686.1647    Dynamic  Remote       Te 15/0/18
701      0050.5686.44ff    Dynamic  Remote       Te 15/0/6
701      0050.5686.4614    Dynamic  Remote       Te 15/0/9
701      0050.5686.6265    Dynamic  Remote       Te 15/0/8
701      0050.5686.7078    Dynamic  Remote       Te 15/0/3'''

mactables = shmac.split('\n')
macinfos = []
for mactb in mactables:
    if((mactb.lower().find(' te'))>0):
        macinfos.append(mactb)

for macinfo in macinfos:
    macinfo=macinfo.split()
    print("MAC : {0} \t Interface : Te {1}".format(macinfo[1],macinfo[5]))

○ 장비의 Local Mac Address 정보를 출력하는 내용입니다.

   

 

예제 6) 파일 입출력해보기 

zigifile = open("zigi.txt",'w')
zigifile.write("zigispace.net")
zigifile.close()

zigifile2 = open('zigi.txt','r')
zigi = zigifile2.read()
zigifile2.close()
print (zigi)

○ 초간단 파일 입출력 예제입니다.

예제 7) 장비 정보 가져온 후, 파일로 만들기

from netmiko import ConnectHandler
import device

print("Connecting....")
nwnode = ConnectHandler(**device.ARI)
shver = nwnode.send_command("show ver")

zigifile = open('zigi.txt','w')
zigifile.write(shver)
zigifile.close() 

○ 장비의 정보를 가져와서, 해당 값을 파일로 만드는 예제입니다.

Posted by 네떡지기
프로그래밍/Python2014.08.24 17:15

 

Last Updated 2014.08.26


Python for Networker의 이번 포스팅은 Cisco dCloud 의  Nexus 9000 : NX-OS Programmability v1에 있는 Python Script 예제 중의 하나를 다뤄봅니다.

 

이 Python Script는 Nexus에서 현재 원하는 정보를 Text 형태의 첨부파일로 만들어서, 메일로 전송을 하는 예제 Script 입니다.

 

다음과 같이 bootflash://script 디렉토리에서 예제 Script를 실행합니다.

 

 

dcloud-n9k#  python ./n9k_serviceability.py 수신메일주소

 

 

 

 

Script를 실행하게 되면, 어떤 종류의 정보를 수집할 것인지에 대해서 물어보게 됩니다.

 

여기서 원하는 정보의 종류를 선택하면, Nexus에서 해당 정보를 수집하여, 수신하고자 하는 Email 주소로 발송을 하게 됩니다.

 

실제 메일이 제대로 발송이 되었는지 확인을 해보면, 아래와 같이 제 메일 계정으로  메일이 수신되었음을 확인할 수 있습니다.

 

Cisco dCloud의 Nexus 9000에서의 예제 Script이기는 하지만,

어차피 기존 포스팅에서도 다뤘듯이 Nexus에서만 가능한 부분은 아닙니다.

 

그럼 유사한 기능을 기존 포스팅에서 언급했던, Arista vEOS에서 유사한 Script로 만들어서 테스트 해보겠습니다.

 

Arista VM을 실행하여, vEOS에서 mail.py 이라는 예제 Script를 만들었습니다.

 

그리고 아래와 같이 해당 Script를 실행해봅니다.

 

 

이 예제에서는 특정 정보를 가공해서 메일을 발송할 수 있다는 점에 대해서 보여주는 것이기 때문에

복잡하게 구현하지는 않았고, 단순하게 현재 vEOS의 version 정보를 확인하여, 첨부파일로 전송을 하는 역할을 합니다.

 

위와 같이 해당 Script를 실행하게 되면, vEOS의 version 정보를 Text 형태의 첨부 파일로 가공을 하게 되고, 메일을 보내게 됩니다.

(참고로 Arista VM에서 bash shell mode에서 python script를 실행 중인 모습입니다.)

 

자 이제, 메일이 잘 도착했는지 메일함을 확인해보겠습니다.

(위의 예제에서는 별도로 뒤에 수신자 email 주소를 쓰지 않았지만 Nexus에서와 마찬가지로 실행 시 수신하고자 하는 email주소를 쓰게 되면,  해당 email로 전송도 물론 가능합니다.)

 

 

 메일함을 보면,  정상적으로 메일이 잘 수신된 것을 확인할 수 있습니다.

 첨부파일을 열어보게 되면, show version으로 확인된 정보를 볼 수 있습니다.

 

 이번 포스팅에서는 별도의 기술적인 내용은 배제하였습니다.

 

  다만, Python을 이용하여 어떤 것들이 가능한지에 대해서 Cisco dCloud에서의 보여주는 예제를 확인해보고

 또한 그러한 예제들이 단순히 특정 벤더에서만 실행되는 것이 아니라 Python을 지원하는 어떤 장비에서도 유연하게 사용할 수 있다는 것을

 확인해보는 것이 이번 포스팅에서 말하고자 하는 부분입니다.

 

  물론 Script 상에 들어가는 각 벤더에서 제공하는 모듈들은 유사한 기능을 하는 각 벤더의 모듈을 가져다 쓰기는 해야겠지만,

 기본적인 프로그램 상의 로직이나 코드는 모두 재활용이 가능합니다. 

 

  또한 기존에 있는 코드에서 추가적인 기능들을 얼마든지 필요에 의해서 추가도 가능하게 될 것입니다. 

 

 그럼 다음 포스팅에서 다시 찾아뵙겠습니다.

 

 


Nexus 5000에서도 테스팅 추가 완료하였습니다.

 

아래와 같이 Nexus 5000에서 mail.py 이라는 Script를 만들었습니다.

기본적인 코드는 위에서 사용했던 코드와 거의 유사하며, 실제 장비에 Cli 모드의 명령하는 부분과 결과값을 가공하는 부분만

다르게 되어 있습니다. Script의 내용은 기존과 마찬가지로 show version으로 나오는 결과값을 메일로 발송하도록 되어 있습니다.

 

 

위와 같이 정상적으로 코드가 실행된 것을 확인할 수 있습니다.

 

 

 Nexus에서 메일을 발송한 이후에, 메일함을 살펴보면

정상적으로 메일과 첨부파일이 도착한 것을 볼 수 있습니다.

 

이것으로 Nexus 9000 / 5000 , Arista vEOS에서 모두 메일 발송하는 Python Script를 살펴보았습니다.

전체적으로 변경된 부분은 단지 장비에 대한 상태를 확인하기 위한 명령어를 입력하고, 해당 결과값을 가공하는 부분만 다르고

나머지 부분은 모두 동일하다고 보시면 됩니다.

 

앞으로는 정말 코드를 처음부터 짤 수는 없더라고, 기존 코드를 이해하고 수정할 수 있을정도로 알아두어야만(?) 할 것 같습니다.

 

 

 

Posted by 네떡지기
프로그래밍/Python2014.08.18 17:42

 


10번째 Python for Networker 포스팅입니다.

이번 포스팅에서 Cisco Nexus의 7000과 5000에서 공통으로 사용이 가능하도록 기존에 만들었던 ipinfo.py 모듈을 변경해봅니다.

장비별로 개개의 코드를 작성해서 수행하는 것보다는 장비에서 공통으로 호환성있게 사용 가능한 코드를 만드는 것이 향후 코드에 대한

유지보수 측면에서 더욱 유리할 것 이기 때문에 유심있게 봐두면 좋을 듯 싶습니다.

 

Git에서 Code 보기

  - einfo.py : https://github.com/NetworkZIGI/Python_for_Network/blob/master/eipinfo.py

  - vCheck.py : https://github.com/NetworkZIGI/Python_for_Network/blob/master/vCheck.py

 


 

 

Nexus 7000와 Nexus 5000에서 지원하는 Python의 경우에는 각각 지원되는 방식이 다르다.

 

실제 Cisco에서 제공되는 Python의 Cisco Module을 확인해 보면 아래와 같이 내장된 Member가 서로 다른 것을 확인할 수 있다.

 

◇ Nexus 7K Cisco Module

 

__doc__

__name__

__package__

cli

cli_execution_error

clil_syntax_error

clid

clip

set_vrf

 

 

◇ Nexus 5K Cisco Module

 

BGPSession

Routes

check_port_discards

line_parser

show_run

BufferDepthMonitor

SectionParser

cisco_secret

mac_address_table

ssh

CLI

VRF

cisco_socket

md5sum

tacacs

CheckPortDiscards

Vlan

cli

msdp

telnet

CiscoSecret

__all__

dhcp

ospf

transfer

CiscoSocket

__builtins__

eigrp

ospfv3

udld

Feature

__doc__

feature

pim

vlan

History

__file__

get_global_vrf

private-vlan

vpc

IPv4ACL

__name__

get_valid_port

ptp

vrf

IPv6ACL

__package__

history

rip

vrrp

Interface

__path__

hsrp

routes

vtp

Key

acl

interface

scheduler

 

LineParser

bfd

interface-vlan

section_parser

 

MacAddressTable

bgp

key

set_global_vrf

 

OSPFSession

buffer_depth_monitor

lacp

show_queues

 

 

 

서로 지원되는 Cisco Module이 다르기 때문에, 관리자가 Module을 새롭게 만들 경우에는 이러한 점이 고려되어야 합니다.

물론 Cisco Module을 사용하지 않고 만든 Python Module은 상관이 없겠지만, Cisco Module을 Import하여 만든 Python Module은

각 Nexus 별로 지원되는 내용과 결과값이 다르기 때문에 별개의 코드로 만들어야 하는 경우가 발생하게 됩니다.

 

기존 Python for Networker : Part 6 에서 다뤄졌던, IP를 가지고 해당 IP의 정보(IP / Mac  / VLAN / Interface / Description)를 보는

ipinfo.py의 경우에도 대부분의 코드가 비슷하지만, Cisco Module이 사용된 부분에 대해서는 내용이 달라지게 됩니다.

 

가령 Nexus 7K의 경우에는 Cisco Cli 명령을 수행하기 위해서 cisco.cli 메서드를 사용하여 결과를 수행하면 str(문자열) 값으로

결과값을 가져옵니다. 반면에 Nexus 5K의 경우에는 cisco.CLI 메서드르 사용하고 이러한 결과값은 tuple 형태로 결과를 가져옵니다.

 

이처럼 cisco에서 제공하는 Module이 서로 다르게 처리되다 보니, 각 Module을 만들고자 할 때에는 각각의 Module에서 사용되는

cisco Module을 고려하여 만들어야 합니다.

 

그렇다면, Nexus 7K와 Nexus 5K에서 공통으로 사용할 수 있는 코드를 만들 수는 없을까요?.... 물론 가능합니다.

 

먼저 아래의 예제 코드를 살펴보면..

 

 

vCheck.py : Nexus 7000/5000 구분하는 예제 코드

import sys
N7K = 'Nexus7000'
N5K = 'Nexus5000'
#N3K = 'Nexus3000'     : Constant for Extension.

NexusVersion = ''

def NexusVersionCheck():
    global NexusVersion
    sysPathList = sys.path
    for pathItem in sysPathList:
        if(pathItem=='/bootflash/scripts'):
            NexusVersion = N7K
            break
    else:
        NexusVersion = N5K

 

위의 예제 코드는 코드가 실행되는 장비가 Nexus 7000인지, 5000인지 확인하는 코드입니다.

원리는 무척이나 단순합니다.

 

각 장비의 path 정보값을 가져와서 확인을 하는 데, Nexus 7000에서는 기존 포스팅에서 다뤘던 것처럼

bootflash/scripts 에 Python Module이 들어가게 됩니다. 그리고 이 Path 정보는 Nexus 7000에만 있습니다.

(물론 제가 Testing이 가능한 장비가 Nexus 7000과 5000밖에 없기 때문에, 다른 장비에서는 어떻게 달라질지 그리고 그경우에는

 어떠한 방법으로 다시 구분을 할지는 달라지게 됩니다. 단지 장비별로 이렇게 특정값을 확인하여 어떤 장비인지 확인할 수 있는지에

 대한 부분을 확인하는 Module을 만든다면, 현재 해당 Module이 실행되는 장비가 어떤 장비인지 확인 할 수 있습니다.)

 

이러한 구분 정보를 통하여 현재 동작하고 있는 Module의 장비 값을 Global 변수에 저장할 수 있습니다.

그러면, 실제 특정 기능을 수행하는 Module에서는 위의 정보를 바탕으로 필요한 Cisco Module을 사용하여 처리할 수 있습니다.

 

위의 Nexus Version을 체크하는 Module을 바탕으로, 기존에 작성하였던 ipinfo.py를 Nexus 7000과 5000에서 모두 동작하게 하는

공통 Module로 아래와 같이 작성할 수 있습니다.

 

 

eipinfo.py

#!/bin/env python
import argparse
import sys
import cisco
import vCheck
from vCheck import NexusVersionCheck


IP = 'IP-Address'
MAC = 'Mac-Address'
Vlan = 'Vlan'
Intf = 'Interface'
Desc = 'Description'


IP_info = {IP:'None', MAC:'None', Vlan:'None', Intf:'None', Desc:'None'}

 

def get_ARP_Table(ipaddr):
    arpCmd = 'sh ip arp ' + ipaddr
    arpCmdResultList = [] 
    if(vCheck.NexusVersion==vCheck.N7K):
        arpCmdResult = cisco.cli(arpCmd)
        arpCmdResultList = arpCmdResult.split('\n')
    elif(vCheck.NexusVersion==vCheck.N5K):
        arpCmdResult = cisco.CLI(arpCmd, False)
        arpCmdResultList = arpCmdResult.get_output()

    for arp in arpCmdResultList:
        if (-1<arp.find(args.ip)):
            return arp
    else:
        print ' %s : Not found IP Address Infomation' % args.ip
        sys.exit()

 

def get_IP_MAC_info(info):
    info_list = info.split()
    IP_info[IP] = info_list[0]
    IP_info[MAC] = info_list[2]
    IP_info[Vlan] = info_list[3][4:]

 

def get_Interface_info():
    macCmd = 'sh mac address-table addr ' + IP_info[MAC]
    macCmdResultList = [] 

    if(vCheck.NexusVersion==vCheck.N7K):
        macCmdResult = cisco.cli(macCmd)
        macCmdResultList = macCmdResult.split('\n')
    elif(vCheck.NexusVersion==vCheck.N5K):
        macCmdResult = cisco.CLI(macCmd, False)
        macCmdResultList = macCmdResult.get_output()

 

    for infInfo in macCmdResultList:
        idx = infInfo.find(IP_info[MAC])
        if(-1<idx):
            IP_info[Intf] = infInfo[58:]
            get_Description_info(IP_info[Intf])
            break


def get_Description_info(iInfo):
    if(iInfo.find('Eth') == 0 or iInfo.find('Po')==0):
        intCmd = 'sh int desc | inc ' + iInfo
        if(vCheck.NexusVersion==vCheck.N7K):
            intCmdResult = cisco.cli(intCmd)
            intCmdResultList = intCmdResult.split('\n')
            if(intCmdResult != ''):
                IP_info[Desc] = intCmdResultList[0][25:].strip()
        elif(vCheck.NexusVersion==vCheck.N5K):
            intCmdResult = cisco.CLI(intCmd, False)
            intCmdResultList = intCmdResult.get_output()
            if(intCmdResult != ''):
                IP_info[Desc] = intCmdResultList[0][25:].strip()

 

def show_IP_info():
    print '==================================='
    print '      enhanced IP Info : NetworkZIGI                 '
    print '==================================='
    print '%-15s : %s' % (IP,IP_info[IP])
    print '%-15s : %s' % (MAC,IP_info[MAC])
    print '%-15s : %s' % (Vlan, IP_info[Vlan])
    print '%-15s : %s' % (Intf, IP_info[Intf])
    print '%-15s : %s' % (Desc,IP_info[Desc])

 

NexusVersionCheck()
parser = argparse.ArgumentParser('Args',description='Args Desc')
parser.add_argument('ip')
args = parser.parse_args()
iparp = get_ARP_Table(args.ip)
get_IP_MAC_info(iparp)
get_Interface_info()
show_IP_info()

 

 

위의 Code 중에서 파란색으로 표기된 부분이 Nexus 7K와 5K를 구분하기 위한 부분입니다.

 

 그럼 이제 위의 1개의 코드로 Nexus 7000과 Nexus 5000에서 별도의 코드를 각각 사용하는 것이 아닌, 하나의 동일한 코드로

원하는 결과값을 같이 얻을 수 있게 되었습니다.

 

 이번 Part에서 다뤄진 부분은 제가 Test가 가능한 장비를 기준으로 두 장비에 대해서 단순한 방법으로 구분을 지었습니다.

하지만, Nexus 의 다른 시리즈의 경우에는 또 지원되는 부분이 다르기 때문에 그러한 부분까지 수용하기 위해서는 장비를 구분하는

vCheck 모듈의 수정이 필요하게 될 것입니다.

 

 여기서 세부적인 장비 구분을 체크하는 실제적인 내용보다는, 그러한 장비 구분을 통해서 실제 수행을 원하는 내용의 코드를 장비 개별

코드가 아니라, 하나의 공통 코드로 만들어서 사용할 수 있다는 것이 다루고자 하는 내용이었습니다.  

 

 그러한 부분을 잘 활용하게 된다면, 하나의 코드로 다른 버전의 장비에서도 호환이 되는 코드를 작성할 수 있을 것입니다.

 

물론 아예 처음부터 지원되는 cisco module이 동일하다면, 이러한 부분을 별도로 고려하지 않을 수 있겠지만

그러한 부분도 고려한 코드를 작성하는 것도 현재 시점에서는 또 하나의 몫이 아닐까 생각을 해봅니다.

Posted by 네떡지기
프로그래밍/Python2014.08.13 12:20

이번 포스팅은 별도의 Part은 아니고~ 추가 포스팅입니다.

지난 Part 6에서 다뤄진 내용에 대해서 Nexus 7K용으로 변경한 코드입니다.

꼭 바꿔야하는 부분을 제외하고.. 약간 추가적으로 내용 업데이트도 함께 했습니다. (그 부분은 5K도 공통사항이긴합니다..)

Nexus 7K로 변경해야 할 때, 어디를 바꿔야 하는지 문의하시는 분이 계셔서 수정해서 올려드립니다.
지난 번에 생각했던 것보다 조금 더 수정해야 하는 부분이 있어서. ^^;

포스팅으로 대체했습니다.

 

Python for Networker : Part 6 보기

 

Github에서 보기 

 


 

 

 

 ○ IP Info - Nexus 7000

 __author__ = 'Network ZIGI - Ko Jae Sung'

 #!/bin/env python
import argparse
import sys 
import cisco 
IP = 'IP-Address' 
MAC = 'Mac-Address' 
Vlan = 'Vlan' 
Intf = 'Interface' 
Desc = 'Description' 
IP_info = {IP:'None', MAC:'None', Vlan:'None', Intf:'None', Desc:'None'} 

def get_ARP_Table(ipaddr): 
    arpCmd = 'sh ip arp ' + ipaddr 
    arpCmdResult = cisco.cli(arpCmd) 
    arpCmdResultList = arpCmdResult.split('\n') 
    for arp in arpCmdResultList: 
        if (-1<arp.find(args.ip)):   
            return arp           
    else: 
        print ' %s : Not found IP Address Infomation' % args.ip  
        sys.exit() 

def get_IP_MAC_info(info): 
    info_list = info.split()          
    IP_info[IP] = info_list[0]        
    IP_info[MAC] = info_list[2]          
    IP_info[Vlan] = info_list[3][4:]    
                                     
def get_Interface_info(): 
    macCmd = 'sh mac address-table addr ' + IP_info[MAC] 
    macCmdResult = cisco.cli(macCmd) 
    macCmdResultList = macCmdResult.split('\n') 
 
    for infInfo in macCmdResultList: 
        idx = infInfo.find(IP_info[MAC]) 
        if(-1<idx): 
            IP_info[Intf] = infInfo[58:] 
            get_Description_info(IP_info[Intf]) 
            break 


def get_Description_info(iInfo): 
    if(iInfo.find('Eth') == 0 or iInfo.find('Po')==0):  
        intCmd = 'sh int desc | inc ' + iInfo 
        intCmdResult = cisco.cli(intCmd) 
        if(intCmdResult != ''): 
            intCmdResultList = intCmdResult.split('\n') 
            IP_info[Desc] = intCmdResultList[0][25:].strip() 

def show_IP_info(): 
    print '================================================' 
    print '             IP Info : NetworkZIGI              ' 
    print '================================================' 
    print '%-15s : %s' % (IP,IP_info[IP]) 
    print '%-15s : %s' % (MAC,IP_info[MAC]) 
    print '%-15s : %s' % (Vlan, IP_info[Vlan]) 
    print '%-15s : %s' % (Intf, IP_info[Intf]) 
    print '%-15s : %s' % (Desc,IP_info[Desc]) 

parser = argparse.ArgumentParser('Args',description='Args Desc') 
parser.add_argument('ip') 
args = parser.parse_args() 

iparp = get_ARP_Table(args.ip) 
get_IP_MAC_info(iparp) 
get_Interface_info() 
show_IP_info() 

 

 

Posted by 네떡지기
분류없음2014.07.31 23:51

 


벌써 9번째 포스팅에 접어들었네요. ^^;

 

이번 포스팅은 직접 장비가 없어도 해보실 수 있는 VM을 이용하여 실습을 할 수 있도록 하는 환경을 꾸미는 내용입니다.

 

바로 ARISTA의 vEOS를 VMWARE 환경에서 사용할 수 있도록 만들어 보겠습니다.

 

이번 포스팅에서 1대의 가상 머신을 설치해보지만, 여러대의 VM을 띄워서 네트워크 구성도 물론 가능합니다!

 

 

NetworkZIGI Python Git : https://github.com/NetworkZIGI/Python_for_Network

 


 

 

먼저 Arista의 vEOS를 사용하기 위해서, vEOS 이미지를 구하셔야 합니다.

vEOS 이미지는 Arista 홈페이지를 가면, 아래와 같이 vEOS를 다운 받으실 수 있습니다. 
물론 다운을 받기 위해서 가입을 하셔야 합니다. (단, 별도의 파트너 계정일 필요는 없이 회원 가입만으로 다운이 가능합니다.)

 

그리고 버전이 여러개가 있는데,

 

    F 버전 : 기능이 추가된 버전

    M버전 : 안정화된 버전

 

이라고 볼 수 있습니다.

 

 

버전 한가지를 골라서, 해당 버전의 모든 파일과 ISO 파일을 모두 다운 받습니다.

 

다운을 받는데는 시간이 조금 걸리기 때문에, 다운 시켜놓고~ 잠시 네떡지기의 블로그에서 다른 포스팅도 봐주시면 감사하겠습니다.

 

....

 

자 모든 파일이 다운이 끝났으면, 이제부터 환경을 만들어 보겠습니다.

전 과정(?)을 모두 캡춰를 떴으니~ 사진만 보고 따라가셔도 충분히 손쉽게 구축할 수 있습니다.

 

 

Custom 모드를 선택해서 시작합니다.

 

그냥 Next를 하시면 됩니다. ^^

 

아까 홈페이지에서 다운 받은

Aboot-veos-2.0.8.iso

로 지정하시면 됩니다!

 

Linux로 선택하시고, inOther Linux 2.6x 로 선택 하시면  됩니다.

 

 

 

 

적당하게, Virtual Machine Name을 주고, 위치를 지정합니다.

 

Next 클릭! (CPU 1)

 

2048MB 로 지정하시고, Next 선택

 

전 Host-only networking을 했습니다.

 

Next 클릭! (LSI Logic)

  

IDE로 지정하시고, Next 선택

 

 

Disk는 Existing Disk로 지정하시고,

Arista 홈페이지에서 다운받은 이미지 파일(vEOS-4.13.7M.vmdk)을 지정합니다.

Next 선택합니다.

 

모두 끝습니다.

Finish를 선택하시면 됩니다.

 

자, 이제 가상머신을 구동시킵니다!

 

위와 같이 vEOS가 부팅되는 것을 볼 수 있습니다.

 

부팅이 완료되면, 로그인 창이 뜹니다.

기본 계정은 'admin'으로 하시고, 별도의 비밀번호는 없습니다.

 

 

자, 이제 모든 환경이 갖춰졌으니 Python Shell을 띄워서 간단하게 Print까지 한 줄 해보았습니다.

 

이제부터는 집에 있는 컴퓨터로도 실습까지 해 볼 수 있는 멋진 환경을 구축하시게 되었습니다.

 

이번 포스팅은 이만 줄이고~ 다음 포스팅에서 다시 또 조만간 뵙도록 하겠습니다.

Posted by 네떡지기
프로그래밍/Python2014.07.28 12:59

 

Last Updated : 2014.07.30


 

이번 포스팅은 Nexus 7000 시리즈에서 Python Script를 실행하기 위한 방법입니다.

 

Nexus 버전별로 지원되는 부분이 조금씩 다른 듯 싶은데..    (물론 제가 모든 장비를 해 볼 수 있는 환경이 아니어서요... )

 

Nexus 5000의 경우에는 바로 Python 명령을 사용하여 기존의 만들어진 Python 모듈을 실행할 수 있지만,

 

Nexus 7000에서는 Python 명령을 치고 '?'를 치면...   아래와 같이 Python Shell로 들어가는 것 밖에 되지 않습니다.

 

 

 

Nexus 7000

Nexus 5000

N7K# python ?
  <CR>  

N5K# python ?
  <CR>       
  bootflash:  The file to run

 

그럼 과연 실행은 어떻게 할까요?

바로 source 명령어로 실행을 하게 됩니다.

그런데, 이 때 Source 명령으로 실행하기 위해 'Hello.py'를

 

print 'Hello ZIGI'

 

라는 한 줄짜리 코드를 작성해서 실행하려고 보면, 실행이 되지 않습니다.

그럼 source라는 명령을 치고 ? 를 쳐봅니다.

그럼 아래와 같이 출력이 됩니다.

 

 

Source 명령

NX-OS# source ?
  background (no abbrev)         Run the script in the background, see also 'show background' and 'kill background'
  build_cmd_script.py               No help
  build_cmd_script_from_file.py  No help
  cgrep                                Grep for something in stdin (-> use behind pipe) and display its 'context' \

                                         (determined by indentation, like in 'show run')
  check_sys_st_op_consist.py     No help
  cmn_file_util.py                    No help
  copy-sys (no abbrev)            Copy the system provided example scripts of /sys to bootflash:scripts
  def_cmd_script.tmp               No help
  elame.tcl                            No help
  gen_sys_st_op.py                  No help
  logw.py                              No help
  poap.py                             Loads system/kickstart images and config file for POAP
  show-version                      A succinct 'show version' -- mixes in stuff from 'show version build-info / internal build'
  sys/                                  Directory
  systemcheck.py                   No help
  systemcheck.pyc                 No help
  update_cmd_script.py           No help

 

Hello.py 라는 파일이 없습니다.

 

이유인 즉,

 

The bootflash:scripts directory is the default script directory. All scripts must be stored in the bootflash:scripts directory or in a subdirectory of it.

 

바로 bootflash 안에 scripts 폴더에 넣어야 합니다. 바로 위에 보이는 저 항목들도 모두 Scripts 폴더에 있기 때문이지요.

물론 Scripts 하위 폴더에 저장을 해도 상관은 없습니다. 경로만 지정한다면..

그럼 scripts 폴더에 다음 "hello.py"를 아래와 같이

 

print 'Hello ZIGI'

 

를 다시 만들어 실행해봅니다.

 

NX-OS# source hello.py
Error: language not supported

 

그럼 위와 같이 다시 또 실행이 되지 않습니다.

 

그 이유는.

 

You can run a tcl script instead of a Python script by inserting #!/bin/env tclsh before the first line in the example and replacing all occurrences of the Python

 

Python script 제일 상단에  "#!/bin/env python"  을 추가해줘야 합니다.

  

 

bootflash://scripts/hello.py

#!/bin/env python

print "Hello ZIGI"

※ 스크립트가 #!로 시작하는 경우, 스크립트를 해석하여 실행할 프로그램 의 경로명이 된다.

 

자, 이제 다시 실행을 해보겠습니다.

 

 

bootflash://scripts/hello.py : 실행

NX-OS# source hello.py

Hello ZIGI

NX-OS#

 

위와 같이 Python Script를 실행할 수 있는 걸 볼 수 있습니다.

 

그럼 기존에 포스팅했던 Script도 실행할 수 있습니다.

 

 

bootflash://scripts/hello.py : 실행

NX-OS# source ipinfo.py 10.10.10.100
================================================
             IP Info : NetworkZIGI             
================================================
IP-Address      : 10.10.10.100

Mac-Address   : 0080.9867.123B
Vlan              : 11
Interface       : Ethernet 1/1
Description     : ZIGI-WebServer

 

단, 코드를 약간 수정해주셔야 합니다.

왜냐하면, Cisco Nexus에서도 장비 버전별로 지원되는 패키지가 다르기 때문이지요.

Nexus 5000에서 사용한 cisco.CLI() 라는 메서드 대신에, cisco.cli(), cisco.clip(), cisco.clid()가 있습니다.

 

저는 cisco.cli() 메서드를 이용해서 위와 같이 만들었습니다.

어떻게 변형해야 하는지는 간단한 숙제로 남겨드리겠습니다. ^^

 

 

  

Posted by 네떡지기
프로그래밍/Python2014.07.24 21:30

이번 포스팅도 Python으로 만들어 보는 예제입니다.  마찬가지로 Cisco Nexus 5548 기준입니다.   

 

하지만, 현재 만드는 예제가 모두 기본 CLI명령을 입력하는 부분에서만 Cisco 패키지를 사용하기 때문에

 

간단한(?) 변형을 통해 다른 곳에도 활용이 가능합니다.

 

(물론 출력된 문자열이 Nexus 기준에서 가공하여 만든 예제라 문자열 가공을 각 상황에 맞게 일부 변형이 필요합니다)

 

이번 예제는 특정 interface의 사용량을 원하는 횟수만큼,  원하는 시간 간격으로 화면에 출력해주는 예제입니다.

 

* Github에서 보기

    uInt.py : https://github.com/NetworkZIGI/Python_for_Network/blob/master/uInt.py

    uIntmod : https://github.com/NetworkZIGI/Python_for_Network/blob/master/uIntmod.py

 


 

 

uInt.py

__author__ = 'Network ZIGI'

import cisco
import time
from argparse import ArgumentParser


def CheckInterfaceRate():
    inPacketList = []
    inBitList =[]
    outPacketList=[]
    outBitList=[]
 

    for cnt in range(1,int(args.repeat)+1):
        result = getInterfacerRate()
        print '%8d >>  [ Input ]  %13s bps -  %6s pps   :   [ Ouput ]  %13s bps  -  %6s pps    [ %s %s]' % \
        (cnt,result[0][4], result[0][6],result[1][4],result[1][6],result[0][0],result[0][1])
        inBitList.append(int(result[0][4]))
        inPacketList.append(int(result[0][6]))
        outBitList.append(int(result[1][4]))
        outPacketList.append(int(result[1][6]))
        time.sleep(int(args.interval[0]))

    print '==========================================================================='
    print 'Max  >>   [ Input ]  %13d bps -  %6d pps   :   [ Ouput ]  %13d bps  -  %6d pps ' % \
    (max(inBitList), max(inPacketList),max(outBitList), max(outPacketList))

 

def getInterfacerRate():
     intRateCmdResult = cisco.CLI('sh int '+args.Intinfo, False)
    intRateCmdResultList =intRateCmdResult.get_output()
    for rate in intRateCmdResultList:
        if(-1<rate.find('input rate')):
            inputList = rate.split()
        elif ( -1<rate.find('output rate')):
            outputList = rate.split()
            return inputList, outputList

 

parser = ArgumentParser('usingInt')
parser.add_argument('Intinfo',  help='Interface')
parser.add_argument('repeat', help='repeat Interface Input/Output rate')
parser.add_argument('interval', type=str, default=['1'],nargs='*',  help='Interval time (Second) - [default : 1 Second]')
args = parser.parse_args()
CheckInterfaceRate()

 

그리고 위의 코드를 아래와 같이 실행해봅니다.

 

필요한 매개변수는

 

1. 사용량을 확인할 인터페이스               2. 반복할 횟수               3. 체크할 시간 간격

 

uInt.py - Cli 모드 실행 결과

4F_DMZ_NEXUS_A_1# python uInt.py po1 5 2
  1 >> [ Input ]          9592 bps -       9 pps : [ Ouput ]        126888 bps  -     173 pps  [ 30 seconds]
  2 >> [ Input ]          9264 bps -       9 pps : [ Ouput ]        125600 bps  -     170 pps  [ 30 seconds]
  3 >> [ Input ]          9264 bps -       9 pps : [ Ouput ]        125600 bps  -     170 pps  [ 30 seconds]
  4 >> [ Input ]          9264 bps -       9 pps : [ Ouput ]        125600 bps  -     170 pps  [ 30 seconds]
  5 >> [ Input ]          9328 bps -       9 pps : [ Ouput ]        124000 bps  -     166 pps  [ 30 seconds]
===========================================================================
Max  >> [ Input ]          9592 bps -       9 pps : [ Ouput ]        126888 bps  -     173 pps

 

원하는 대로 결과값이 나온 것 같습니다!!

하지만... 절망.. Cli모드에서 실행을 하게되면 모든 코드가 종료된 이후에 결과가 나오게 됩니다.

이 부분을 실시간으로 나오게 하는게 있는지 확인을 오늘 이래저래.. 구글링을 해 보았으나..

없는 듯 싶습니다. (만약 있다면 알려주세요!!!)

 

그래서 어찌할까.. 하다가... Python Shell 모드에서 실행하도록 변형해봅니다.

 

위에서 만든 코드를 거의 그대로 가져다 쓸 수 있도록 메인 실행 부분을 함수로 변형하고 실행 시의 매개변수를

해당 함수를 호출 할 때의 매개변수로 대체하는 것 이외에는 달라지는 부분은 없습니다.

 

 

uIntmod.py

 # -*- coding: utf-8 -*-
__author__ = 'Network ZIGI'

import cisco 
import time

def CheckInterfaceRate(args):
    inPacketList = []
    inBitList =[]
    outPacketList=[]
    outBitList=[]
    inPacketavg=0
    inBitavg=0
    outPacketavg=0
    outBitavg=0

    for cnt in range(1,args['repeat']+1):
        result = getInterfaceRate(args['intInfo'])
        print '%8d  >>  [ Input ]  %13s bps -  %6s pps   :   [ Ouput ]  %13s bps  -  %6s pps    [ %s %s]' % \

       (cnt,result[0][4], result[0][6],result[1][4],result[1][6],result[0][0],result[0][1])
        inBitList.append(int(result[0][4]))
        inPacketList.append(int(result[0][6]))
        outBitList.append(int(result[1][4]))
        outPacketList.append(int(result[1][6]))
        time.sleep((args['interval']))

    print '==========================================================================='
    print 'Max  >>   [ Input ]  %13d bps -  %6d pps   :   [ Ouput ]  %13d bps  -  %6d pps ' % \

    (max(inBitList), max(inPacketList),max(outBitList), max(outPacketList))

 

def getInterfaceRate(Intinfo):
    intRateCmdResult =cisco.CLI('sh int '+Intinfo,False)
    intRateCmdResultList =intRateCmdResult.get_output()
    for rate in intRateCmdResultList:
        if(-1<rate.find('input rate')):
            inputList = rate.split()
        elif ( -1<rate.find('output rate')):
            outputList = rate.split()
            return inputList, outputList
 
def rate(info,r,step=1):
    args = {'intInfo':info,'repeat': r, 'interval':step}
    CheckInterfaceRate(args)

 

모듈로 만들었으니.. 이제 위의 모듈을 Shell모드에서 import하여 실행해봅니다.

 

 

 uIntmod : Python Shell Mode에서 실행하기

NX-OS# python
Python 2.7.2 (default, Nov 27 2012, 17:50:33)
[GCC 4.3.2] on linux2
Type "help", "copyright", "credits" or "license" for more information.
Loaded cisco NxOS lib!
>>> import uIntmod
>>> uIntmod.rate('po1',5,2)
       1  >>  [ Input ]           8968 bps -       9 pps   :   [ Ouput ]         122544 bps  -     164 pps    [ 30 secon
       2  >>  [ Input ]           9216 bps -       9 pps   :   [ Ouput ]         123296 bps  -     165 pps    [ 30 secon
       3  >>  [ Input ]           9216 bps -       9 pps   :   [ Ouput ]         123296 bps  -     165 pps    [ 30 secon
       4  >>  [ Input ]           8592 bps -       8 pps   :   [ Ouput ]         122856 bps  -     165 pps    [ 30 secon
       5  >>  [ Input ]           8592 bps -       8 pps   :   [ Ouput ]         122856 bps  -     165 pps    [ 30 secon
===========================================================================
Max  >>   [ Input ]           9216 bps -       9 pps   :   [ Ouput ]         123296 bps  -     165 pps
>>> exit()
NX-OS#

 

Shell 모드에서는 실행할 때, 만든 모듈을 Import하고 메서드를 이용해서 모듈의 기능을 사용합니다.

 

자 이제 실시간으로 한 줄씩.. 원하는 시간간격으로 Interface의 사용량을 확인할 수 있게 되었습니다.

 

Posted by 네떡지기
프로그래밍/Python2014.07.19 13:38

 


이번 포스팅은  Python으로 만들어 보는 예제입니다.

 

제가 Test 가능한 환경이 Cisco Nexus이기 때문에  Cisco Nexus 5548 기준으로 작성된 예제입니다만,

 

기본 CLI명령을 입력하는 부분에서만 Cisco 패키지의 명령을 사용하였기 때문에 변형을 한다면,

 

다른 곳에서 충분히 활용이 가능한(?) 예제가 될 수 있을 듯 싶습니다. 

 

(물론 출력된 문자열이 Nexus 기준에서 가공하여 만든 예제라 문자열 가공을 각 상황에 맞게 일부 변형이 필요합니다)

 

IP를 입력하면, 해당 IP의 MAC주소와 VLAN, Interface, Description 정보를 한 번에 확인할 수 있는 내용입니다.

 

추후에 아래 코드는 조금씩 변형되서 업데이트 버전이 만들 계획이지만, 언제 어떻게 될지는 아직은 알 수 없습니다! ^^;

 

아래 코드는 Github에서도 함께 볼 수 있습니다. 

 

Github 에서 보기 


 

 

 ○ IP Info

 __author__ = 'Network ZIGI - Ko Jae Sung'

  # 2014.07.19. First Version
  #
  # ================================================
  #      IP Info : NetworkZIGI   2014.07.19
  #================================================
  #IP-Address      : 10.0.0.1
  #Mac-Address     : 0012.3456.abcd
  #Vlan            : 11
  #Interface       : Eth14/2
  #Description     : NetworkZIGI Blog Server
  #
  # Blog : http://ThePlmingspace.tistory.com
  #
  # Tested : Cisco Nexus 5548  : 6.0(2)N2(4)

 

  import argparse
  import sys
  import cisco

  IP = 'IP-Address'
  MAC = 'Mac-Address'
  Vlan = 'Vlan'
  Int = 'Interface'
  Desc = 'Description'

  
  IP_info = {IP:'None', MAC:'None', Vlan:'None', Int:'None', Desc:'None'}    # IP정보를 저장할 Dict type 변수

 

  # ARP 정보를 가져오는 메서드

  def get_ARP_Table(ipaddr):
      arpCmd = 'sh ip arp ' + ipaddr
      arpCmdResult = cisco.CLI(arpCmd, False)
      arpCmdResultList = arpCmdResult.get_output()
      for arp in arpCmdResultList:
          if (-1<arp.find(args.ip)):
              return arp
      else:
          print ' %s : Not found IP Address Infomation' % args.ip
          sys.exit()

 

  # IP와 MAC, VLAN 정보를 가져오는 메서드

  def get_IP_MAC_info(info):
      info_list = info.split()
      IP_info[IP] = info_list[0]
      IP_info[MAC] = info_list[2]
      IP_info[Vlan] = info_list[3][4:]

 

  # Interface 정보를 가져오는 메서드

  def get_Interface_info():
      macCmd = 'sh mac address-table addr ' + IP_info[MAC]
      macCmdResult = cisco.CLI(macCmd, False)
      macCmdResultList = macCmdResult.get_output()
      if (len(macCmdResultList) > 6):                                                
          IP_info[Int] = macCmdResultList[5][58:]
          get_Description_info(IP_info[Int])

 

  # Description 정보를 가져오는 메서드

  def get_Description_info(iInfo):
      if(iInfo.find('Eth') == 0 or iInfo.find('Po')==0): 

          intCmd = 'sh int desc | inc ' + iInfo
          intCmdResult = cisco.CLI(intCmd, False)
          intCmdResultList = intCmdResult.get_output()
          IP_info[Desc] = intCmdResultList[0][25:]

 

  # IP 정보 출력

  def show_IP_info():
      print '================================================'
      print '             IP Info : NetworkZIGI              '
      print '================================================'
      print '%-15s : %s' % (IP,IP_info[IP])
      print '%-15s : %s' % (MAC,IP_info[MAC])
      print '%-15s : %s' % (Vlan, IP_info[Vlan])
      print '%-15s : %s' % (Int, IP_info[Int])
      print '%-15s : %s' % (Desc,IP_info[Desc])

 

  # 프로그램 시작 지점

  parser = argparse.ArgumentParser('Args',description='Args Desc')
  parser.add_argument('ip')
  args = parser.parse_args()

  iparp = get_ARP_Table(args.ip)
  get_IP_MAC_info(iparp)
  get_Interface_info()
  show_IP_info()

 

 

 ○ IP Info : 결과

NX-OS# python ipinfo.py 10.10.10.11
================================================
      IP Info : NetworkZIGI   2014.07.19       
================================================
IP-Address                                : 10.10.10.11
Mac-Address                           : 0012.3456.789A
Vlan                                           : 20
Interface                                  : E12/3
Description                              : NetworkZIGI Blog Web Server

 

Posted by 네떡지기

티스토리 툴바