telnetlib中興裝置自動化

三十而志于学發表於2024-10-11
如何透過telnetlib模組操作中興裝置
import telnetlib, re, os, threading, multiprocessing, datetime
import pandas as pd
from pandas
pd.set_option('display.width', None)
# pd.options.display.max_columns = None
# pd.options.display.max_rows = None
path = os.getcwd()

def telnet(host, port, username, password):
    tn = telnetlib.Telnet(host, port, timeout=5)
    tn.read_until(b"Username:")
    tn.write(username.encode('ascii') + b"\n")
    tn.read_until(b"Password:")
    tn.write(password.encode('ascii') + b"\n")
    tn.read_until(b"#", timeout=5)
    tn.write(b"terminal length 0 \n") #zte
    tn.read_until(b"#")
    return tn

def runcommands(host, port, username, password, command):
    commands = command.split("\n")
    output = ""
    try:
        tn = telnet(host, port, username, password)
        for cmd in commands:
            tn.write(cmd.encode('ascii') + b"\n")
            output_tmp = tn.read_until(b"#", 5)
            output += output_tmp.decode('ascii')
        tn.close()
        print(output)
    except Exception as e:
        print(f"命令執行失敗,{e}")
        try:
            tn.close()
        except Exception as e:
            print("tn close failed")
    return output

def showInterfaceBrief(host, port, username, password,command="show interface bri"):
    output = runcommands(host, port, username, password, command)
    outputs = output.splitlines()
    msgs = []
    for line in outputs:
        # 提取詳細介面資訊
        pattern = r'(\S+)\s+(\S+)\s+(\S+)\s+(\S+)\s+(down|up)\s+(down|up)\s+(down|up)\s+(\S*)'
        matchs = re.findall(pattern, line)
        if matchs != []:
            match = matchs[0]
            if len(match) == 8:
                desc = match[7]
            else:
                desc = ""
            msgs.append({
                'interface': match[0],
                'portattribute': match[1],
                'mode': match[2],
                'bw(mbps)': match[3],
                'admin_status': match[4],
                'phy_status': match[5],
                'prot_status': match[6],
                'description': desc,
            })
    df = pd.DataFrame(msgs)
    df["host"] = host
    print(df)
    return df

def showInterfaceDetail(host, port, username, password,command="show interface "):
    try:
        interfaces = showInterfaceBrief(host, port, username, password, "show interface bri")
        interfaces["bw"] = None
        interfaces["mtu"] = None
        interfaces["In_Bytes"] = None
        interfaces["E_Bytes"] = None
        tn = telnet(host, port, username, password)
        for interface in interfaces["interface"]:
            cmd = command + interface
            tn.write(cmd.encode('ascii') + b"\n")
            output = tn.read_until(b"#", 5).decode("ascii")
            pattern = r'BW\s+(\d+)'
            match = int(re.findall(pattern, output, re.S)[0])
            interfaces.loc[interfaces["interface"] == interface, "bw"] = match
            pattern = r'MTU\s+(\d+)'
            match = int(re.findall(pattern, output, re.S)[0])
            interfaces.loc[interfaces["interface"] == interface, "mtu"] = match
            pattern = r'In_Bytes\s+(\S+)\s+'
            match = int(re.findall(pattern, output, re.S)[0])
            interfaces.loc[interfaces["interface"] == interface, "In_Bytes"] = match
            pattern = r'E_Bytes\s+(\S+)\s+'
            match = int(re.findall(pattern, output, re.S)[0])
            interfaces.loc[interfaces["interface"] == interface, "E_Bytes"] = match
        tn.close()
        print(interfaces)
    except Exception as e:
        print(f"命令執行失敗,{e}")
        try:
            tn.close()
        except Exception as e:
            print("tn close failed")
    return interfaces

def showIpInterfacesBrief(host, port, username, password, command="show ip int bri"):
    output = runcommands(host, port, username, password, command)
    outputs = output.splitlines()
    msgs = []
    for line in outputs:
        # 提取詳細介面資訊
        pattern = r'(\S+)\s+(\S+)\s+(\S+)\s+(down|up)\s+(down|up)\s+(down|up)\s*'
        matchs = re.findall(pattern, line)
        if matchs != []:
            match = matchs[0]
            msgs.append({
                'interface': match[0],
                'ip_address': match[1],
                'mask': match[2],
                'admin_status': match[3],
                'phy_status': match[4],
                'prot_status': match[5]
            })
    df = pd.DataFrame(msgs)
    df["host"] = host
    print(df)
    return df

def pingtest(host, port, username, password, command="ping 192.168.10.1"):
    output = runcommands(host, port, username, password, command)
    pattern = r'Success rate is (\d+)\s*'
    matchs = int(re.findall(pattern, output)[0])
    if matchs == 0:
        print(f'host {host} {command} is failed')
    else:
        print(f'host {host} {command} is successed, the success rate is {matchs}')


def showIpOspfNeighbor(host, port, username, password, command="show ip ospf neighbor"):
    output = runcommands(host, port, username, password, command)
    pattern = r'\((\S+)\)'
    routerid = re.search(pattern, output).group(1)
    outputs = output.splitlines()
    neighbors = []
    for line in outputs:
        # 提取詳細介面資訊
        pattern = r'(\S+)\s+(\d+)\s+(\S+)\s+(\S+)\s+(\S+)\s+(\S+)'
        matchs = re.findall(pattern, line)
        if matchs != []:
            match = matchs[0]
            neighbors.append({
                'neighborid': match[0],
                'pri': match[1],
                'state': match[2],
                'deadtime': match[3],
                'address': match[4],
                'interface': match[5]
            })
    df = pd.DataFrame(neighbors)
    df["routerid"] = routerid
    print(df)
    return df

def showIpOspfInterfaces(host, port, username, password):
    output = runcommands(host, port, username, password, "show ip ospf interface")
    outputs = re.split(r'\n\s*\n', output.strip())
    ospf_msgs = []
    for msg in outputs:
         if "xgei" in msg:
            # host\interface\status\address\area\networktype\authentication\hello\dead\retransmit
            pattern = r'(\S*xgei\S+)\s+is\s(up|down)'
            matchs = re.findall(pattern, msg)
            interface = matchs[0][0]
            status = matchs[0][1]
            pattern = r'.*Address\s+(\S+)\s+'
            matchs = re.findall(pattern, msg)
            address = matchs[0]
            pattern = r'.*the\sarea\s(\S+)\s'
            matchs = re.search(pattern, msg)
            area = matchs[0]
            pattern = r'.*Network\sType\s(\S+)'
            matchs = re.findall(pattern, msg)
            networktype = matchs[0]
            pattern = r'.*Authentication\sType\s(\S+)'
            matchs = re.findall(pattern, msg)
            authentication = matchs[0]
            pattern = r'.*Hello\s(\d+),\sDead\s(\d+),\sRetransmit\s(\d+)'
            matchs = re.findall(pattern, msg)
            hello = matchs[0][0]
            dead = matchs[0][1]
            retransmit = matchs[0][2]
            ospf_msgs.append({
                "host": host,
                "interface": interface,
                "status": status,
                "address": address,
                "area": area,
                "networktype": networktype,
                "authentication": authentication,
                "hello": hello,
                "dead": dead,
                "retransmit": retransmit
            })
    df = pd.DataFrame(ospf_msgs)
    print(df)
    return df

def checkInterfacesAndRepair(host, port, username, password, interfaces):
    print("----------------before repair interface----------------")
    interfaces_df = showInterfaceBrief(host, port, username, password)
    for interface in interfaces:
        # if interface in interfaces_df["interfaces"]:
        #     print(f"{host} do not have {interface}")
        #     continue
        status = interfaces_df.loc[interfaces_df["interface"] == interface, "admin_status"].values[0]
        if status == "down":
            runcommands(host, port, username, password, f"conf t\ninterface {interface}\nno shutdown\nexit\nexit\nwrite\n")
            print(f"{host} interface {interface} is down, now set it up")
        else:
            print(f"{host} interface {interface} is not down")
    interfaces_after_df = showInterfaceBrief(host, port, username, password)
    print("----------------after repair interface----------------")
    for interface in interfaces:
        status = interfaces_df.loc[interfaces_df["interface"] == interface, "admin_status"].values[0]
        if status == "up":
            print(f"{host} interface {interface} is up after repaired")
        else:
            print(f"{host} interface {interface} is still down after repaired")


if __name__ == '__main__':
    devices = [{"ip":"10.0.0.1","port":"23","username":"zte","password":"zte"},
             {"ip":"10.0.0.2","port":"23","username":"zte","password":"zte"}]
    for device in devices:
        host = device["ip"]
        port = device["port"]
        username = device["username"]
        password = device["password"]
        print(f'{host}-{port}-{username}-{password}')
        # # ---------執行命令----------
        # output = runcommands(host, port, username, password, "show running-config\nshow interface brief \nshow ip interface brief")
        # current_time = datetime.datetime.now().strftime("%Y%m%d-%H%M%S")
        # filename = "showrun_" + host + "_" + current_time + ".txt"
        # with open(filename, "w", encoding="utf-8") as file:
        #     file.write(output)

        # # --------提取show interface brief資訊-------
        # output = showInterfaceBrief(host, port, username, password)
        # current_time = datetime.datetime.now().strftime("%Y%m%d-%H%M%S")
        # filename = "InterfaceBrief_" + host + "_" + current_time + ".csv"
        # output.to_csv(filename)

        # # --------提取show ip interface brief資訊-------
        # output = showIpInterfacesBrief(host, port, username, password)
        # current_time = datetime.datetime.now().strftime("%Y%m%d-%H%M%S")
        # filename = "IPInterfaceBrief_" + host + "_" + current_time + ".csv"
        # output.to_csv(filename)

        # # --------ping測試------------
        # pingtest(host, port, username, password, "ping 192.168.10.1")

        # # --------獲取埠速率\mtu資訊---------
        # output = showInterfaceDetail(host, port, username, password)
        # current_time = datetime.datetime.now().strftime("%Y%m%d-%H%M%S")
        # filename = "InterfaceDetail_" + host + "_" + current_time + ".csv"
        # output.to_csv(filename)

        # # -------獲取ospf鄰居資訊---------
        # output = showIpOspfNeighbor(host, port, username, password)

        # # --------修復埠------------
        # interfaces = ["xgei-0/2/0/8", "xgei-0/2/0/19", "xgei-0/2/0/20"]
        # checkInterfacesAndRepair(host, port, username, password, interfaces)

        # -------顯示ospf埠詳細資訊--------
        showIpOspfInterfaces(host, port, username, password)


    # # -------------多執行緒--------------
    # # 建立執行緒
    # threads = []
    # for login_msg in login_msgs:
    #     host = login_msg["ip"]
    #     port = login_msg["port"]
    #     threads.append(threading.Thread(showInterfaceDetail(host, port, "huawei", "huawei")))
    #
    # # 啟動執行緒
    # for t in threads:
    #     t.start()
    #
    # # 等待所有執行緒完成
    # for t in threads:
    #     t.join()

    # # -------------多程序--------------
    # # 建立程序池
    # with multiprocessing.Pool(processes=len(login_msgs)) as pool:
    #     # 向程序池新增任務
    #     for login_msg in login_msgs:
    #         host = login_msg["ip"]
    #         port = login_msg["port"]
    #         pool.apply_async(showInterfaceDetail(host, port, "huawei", "huawei"))
    #
    #     # 等待所有子程序完成
    #     pool.close()
    #     pool.join()



相關文章