Junos PyEZ-тэй ажиллах тухай өгүүлэл—"Junos OS үйлдлийн системтэй төхөөрөмжүүдийг удирдах, автоматжуулах боломжийг олгодог Python микрофрэймворк" нь бидний дуртай арга зам болох автоматжуулалт, удирдлагын тухай юм. Энэ нийтлэлд тайлбарласан скриптийг Python сурах, Junos үйлдлийн систем дээр ажиллаж байгаа техник хангамжийн мэдээлэл цуглуулах, тохиргоог өөрчлөх зэрэг ажлуудыг автоматжуулах зэрэг хэд хэдэн зорилгын үүднээс бичсэн болно. Энэхүү Python + Junos PyEZ хослолыг Python програмчлалын хэл сурах муруй бага, Junos PyEZ номын санг ашиглахад хялбар тул Junos OS-ийн талаар мэргэжлийн мэдлэг шаарддаггүй тул сонгосон.
Зорилго
Тус компанид хамаарах боломжтой IPv4 дэд сүлжээнүүдийн аудит. Дэд сүлжээ нь Junos OS дээр ажилладаг чиглүүлэгчийн үүрэг гүйцэтгэдэг шилжүүлэгч дээрх маршрутуудад байхгүй бол боломжтой гэж үзнэ.
Реализация
Python + Junos PyEZ, хэдийгээр би үүнийг paramiko болон ssh.exec_command-аар дамжуулан хийхийг оролдсон ч, Үүний үр дүнд та санал асуулга явуулж буй төхөөрөмж дээр сүлжээний төхөөрөмжийн удирдлагын протоколыг (NetConf) тохируулах шаардлагатай болно. NetConf нь алсын процедурын дуудлага (RPC) -ээр дамжуулан төхөөрөмжтэй харилцдаг бөгөөд энэ жишээнд хүлээн авсан мэдээллээ харуулахын тулд XML ашигладаг.
PyPI-аас Junos PyEZ-ийн одоогийн хувилбарыг суулгахын тулд дараах тушаалыг ажиллуулна уу:
$ pip install junos-ezncТа үүнийг GitHub дээрх төслийн үндсэн салбараас дараах тушаалыг ашиглан суулгаж болно.
$ pip install git+https://github.com/Juniper/py-junos-eznc.gitМөн өөр нэг сонголт
$ pip install -r requirements.txt Энэ тушаал нь ажиллахад шаардагдах дутуу номын сангуудыг суулгана. Миний хувилбарт шаардлага.txt Тэдгээрийн зөвхөн хоёр нь байгаа бөгөөд жагсаасан хувилбарууд нь скрипт бичих үеийн хамгийн сүүлийн хувилбарууд юм.
junos-eznc
netaddrАнхдагч байдлаар, скрипт нь систем дэх одоогийн хэрэглэгчийн нэрийг авдаг; Та show_route.py -u товчлуурыг ашиглан өөр хэрэглэгчийн нэрээр нэвтэрч болно. getpass.getpass нь stdin-ийн нууц үгийг хүлээн авдаг тул энэ нь системд үлдэхгүй. Төхөөрөмжтэй холбогдохын тулд та асуух үед түүний хостын нэр эсвэл IP хаягийг оруулах шаардлагатай. Төхөөрөмжийн зөвшөөрөл авахад шаардлагатай бүх өгөгдлийг хүлээн авсан.
Junos PyEZ нь Junos үйлдлийн системийн техник хангамжийг SSH-ээр консол, telnet эсвэл netconf ашиглан холбохыг дэмждэг. Энэ нийтлэлд сүүлчийн сонголтыг авч үзэх болно.
Тоног төхөөрөмжид холбогдохын тулд jnpr.junos модулийн Төхөөрөмжийн ангиллыг ашигладаг.
with jnpr.junos.Device(host=router,
user=args.name,
passwd=password) as dev:Чиглүүлэгчид мэдэгдэж буй бүх маршрутын хүсэлтийг алсын процедурын дуудлага эсвэл алсын процедурын дуудлагын аль нь илүү тохиромжтой байхаар хийдэг.
data = dev.rpc.get_route_information()Junos үйлдлийн систем дээрх ижил төстэй тушаал
user@router> show route | display xmlКомандад rpc-г нэмснээр бид хүсэлтийн хаягийг олж авах бөгөөд үүнийг RPC аргын нэртэй тааруулж болно. Энэ аргыг мөн сонирхсон бусад нэрийг олоход ашиглаж болно. Хүсэлтийн шошго бичих синтакс нь аргын нэрээс ялгаатай гэдгийг тэмдэглэх нь зүйтэй; ялангуяа зураасыг доогуур зураасаар солих хэрэгтэй.
user@router> show route | display xml rpc
<rpc-reply >route_list = data.xpath("//rt-destination/text()")Хэрэв би чиглүүлэгчийн мэддэг сүлжээнээс өөр дэд сүлжээг шалгах шаардлагатай бол чиглүүлэгчээс дахин асуулга хийхээс зайлсхийхийн тулд би асуултын үлдсэн хэсгийг хэсэг хугацаанд ороосон. Миний асууж буй чиглүүлэгч нь зөвхөн OSPF-ээр дамжуулан чиглүүлэлтүүдийг мэддэг тул захын чиглүүлэгчийн хувьд скриптийг гүйцэтгэх хугацааг багасгахын тулд асуулгад бага зэрэг өөрчлөлт оруулах нь дээр гэдгийг дурдах нь зүйтэй.
data = dev.rpc.get_ospf_route_information()Одоо while циклийн агуулгыг харцгаая.
Эхлээд хэрэглэгч нэг дэд сүлжээний сүлжээнээс гурван найм хүртэлх масктай дэд сүлжээнд орохыг хүсэх болно; Энэ нь хайлтын хүрээг тохируулахад шаардлагатай. Хайлтын шалгуур, хүрээг тодорхойлох энэ арга надад үнэхээр таалагдахгүй байна, гэхдээ би илүү сайн шийдлийг хараахан олоогүй байна. Дараа нь, гарах дэд сүлжээнүүдийн жагсаалтаас route_list-ээс би сонирхож буй дэд сүлжээнүүдээ сонгоод, гурван найм хүртэлх тооны агуулах хувьсагчийг ашиглана.
tmp = re.search(r'^%sS*' % subnet_search, route_list[i])IPNetwork буюу netaddr модулийг ашигласнаар би дэд сүлжээг IPv4 хаягуудын жагсаалт болгон авдаг.
range_subnet = netaddr.IPNetwork(tmp.group(0))IPNetwork-ийг ашигласнаар би хэрэглэгчийн оруулсан сүлжээнээс маск бүхий олон тооны хаягуудыг авч, эзлэгдсэн хаягуудын жагсаалттай харьцуулахын тулд энэ мужаас бүх хаягийн жагсаалтыг гаргадаг.
for i in set(net_list).difference(set(busyip)):
freeip.append(i)Би үнэгүй хаягуудын жагсаалтыг дэд сүлжээ хэлбэрээр харуулдаг
print(netaddr.IPSet(freeip))Ex4550, ex4600 загваруудыг чиглүүлэгч болгон ашигладаг унтраалга дээр туршсан бүрэн скриптийг доор харуулав.
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
import argparse
import getpass
import netaddr
import re
import sys
import jnpr.junos
parser = argparse.ArgumentParser()
parser.add_argument('-u', '--user',
action='store',
dest='name',
help='Enter login from tacacs if it differs from the '
'username in the system.')
args = parser.parse_args()
if not args.name:
args.name = getpass.getuser() # Return the “login name” of the user.
router = input("Full routers name: ")
password = getpass.getpass("Password: ")
try:
# Authenticates to a device running Junos, for get information about routs
# into xml format and selects by tag.
route_list = []
with jnpr.junos.Device(host=router,
user=args.name,
passwd=password) as dev:
data = dev.rpc.get_route_information()
route_list = data.xpath("//rt-destination/text()")
except (jnpr.junos.exception.ConnectRefusedError,
jnpr.junos.exception.ConnectUnknownHostError) as err:
print("Equipment name or password wrong.")
sys.exit(1)
while True:
subnet = input("Net with mask: ")
subnet_search = input("Input no more three octet: ")
# Gets a list of busy IP addresses from the received subnets.
busyip = []
for i in range(len(route_list)):
tmp = re.search(r'^%sS*' % subnet_search, route_list[i])
if tmp:
range_subnet = netaddr.IPNetwork(tmp.group(0))
for ip in range_subnet:
busyip.append("%s" % ip)
range_subnet = netaddr.IPNetwork(subnet)
# Gets list ip adresses from subnetworks lists.
net_list = []
for ip in range_subnet:
net_list.append("%s" % ip)
# Сomparing lists.
freeip = []
for i in set(net_list).difference(set(busyip)):
freeip.append(i)
print(netaddr.IPSet(freeip))
request = input("To run request again enter yes or y, "
"press 'enter', complete request: ")
if request in ("yes", "y"):
continue
else:
print('Bye')
break
Эх сурвалж: www.habr.com
