• python学习之路网络编程篇(第五篇)-续篇


    Python堡垒机实现之基础知识

    一般的堡垒机必须要具备以下5个基本功能:

      1、权限控制
      2、执行命令
      3、上传下载文件
      4、远程登录
      5、记录操作
    

    权限控制

        说明:根据不同的登录用户分配不同的可管理的主机组。(再细分的权限就是根据不同的用户控制可在主机上执行的命令,一般不会限制的这么严格)

        思路:使用数据库创建用户表,表字段有ID、用户名、密码、所属组,再创建主机表,表字段有ID,主机IP,所属组。其中用户表中的所属组和主机表中的所属组相对应,这样就能把两张表关联起来。当用户登录的时候就可以根据用户名去获取可管理的主机列表。

    例子:这里只写出关于python连接mysql数据库的例子

    执行命令:

        说明:这里的执行命令一般是指批量执行命令,比如需要同时获取N台主机的主机名。

        思路:使用paramiko模块来实现远程登录服务器并执行命令。使用multiprocessing来实现批量并发执行。

        例子:(这里只写出paramiko模块远程密码登录服务器并执行命令的例子)

    import paramiko
     
    class Paramiko_Manage():
        def __init__(self,host,port,user,passwd):    #初始化连接服务器所需要的参数
            self.host = host
            self.port = port
            self.user = user
            self.passwd = passwd    #使用密码认证
     
        def connect(self):        #连接方法,用来建立与服务器的连接
            self.transport = paramiko.Transport((self.host,self.port))
            self.transport.connect(username=self.user,password=self.passwd)
            print('connect')
     
        def close(self):        #关闭方法,用来关闭与服务器的连接
            self.transport.close()
            print('close') 
     
        def cmd(self,command):        #执行命令的方法,接收需要执行的命令作为参数
            ssh = paramiko.SSHClient()
            ssh._transport = self.transport
            stdin, stdout, stderr = ssh.exec_command(command,timeout=3)
            print('command resluat: ',stdout.read()) 
     
        def run(self,command):
            self.connect()        #建立连接
            self.cmd(command)     #执行命令
            self.close()          #关闭连接
     
    p = Paramiko_Manage('192.168.100.20',22,'test','123456')
    p.run('hostname')
     
    # 执行结果:
    # connect
    # command resluat:  Test1
    #  
    # close
    

    上传、下载文件:

        说明:批量上传文件相对比较简单,如果是批量下载文件还需要考虑到多台服务器文件重名的问题。

                还需要考虑到文件上传后比较大小以确认是否上传下载成功。

        思路:使用paramiko模块来实现远程上传下载文件。使用multiprocessing来实现批量并发执行。    

        例子:(这里只写出paramiko模块远程秘钥认证登录服务器并执行命令的例子)

    import paramiko
    import os
     
    class Paramiko_Manage():
        def __init__(self,host,port,user,key):
            self.host = host
            self.port = port
            self.user = user
            keyfile = os.path.expanduser(key)    #使用秘钥认证
            self.key = paramiko.RSAKey.from_private_key_file(keyfile)
     
        def connect(self):
            self.transport = paramiko.Transport((self.host,self.port))
            self.transport.connect(username=self.user,pkey=self.key)
            print('connect') 
     
        def close(self):
            self.transport.close()
            print('close') 
     
        def trans(self,file1,file2):    #传输文件的方法
            sftp = paramiko.SFTPClient.from_transport(self.transport)
            file1 = '%s_%s' % (file1, self.host)   #修改下载文件的保存文件名
            sftp.get(file2,file1)
            file1_size = os.path.getsize(file1)    #获取下载文件的大小
            file2_size = int(str(sftp.stat(file2)).split()[4]) #获取远程文件的大小
            if file1_size == file2_size:    #比较两个文件大小
                print('File trans done') 
     
        def run(self,file1,file2):
            self.connect()      #建立连接
            self.trans(file1,file2)  #传输文件
            self.close()               #关闭连接 
     
    p = Paramiko_Manage('192.168.100.20',22,'test2','~/.ssh/id_rsa')
    p.run('/root/hosts','/etc/hosts')
     
    # 执行结果:
    # connect
    # File trans done
    # close
    

    远程登录和记录操作:

        说明:通过堡垒机ssh远程连接到服务器,并执行操作,和在终端执行操作的效果一样。

        思路:使用paramiko实现远程连接服务器的功能,使用sys.stdin和select处理用户输入和接受返回结果。

        例子:

    import paramiko
    import select
    import sys
    import socket
    import os
     
    tran = paramiko.Transport((host,port))    #连接服务器,host和port自定义
    tran.start_client()
    default_path = os.path.join(os.environ['HOME'],'.ssh','id_rsa')
    key = paramiko.RSAKey.from_private_key_file(default_path)
    tran.auth_publickey('root',key)
    chan = tran.open_session()    #打开一个通道
    chan.get_pty()                #获取一个终端
    chan.invoke_shell()           #激活器
     
    f = open('log.log','a')       #打开一个文件用于写入执行的操作
    while True:
        # 监视用户输入和服务器返回数据
        # sys.stdin 处理用户输入
        # chan 是之前创建的通道,用于接收服务器返回信息
        readable,writeable,error = select.select([chan,sys.stdin,],[],[],1)
        if chan in readable:        #接受命令的返回结果
            try:
                x = chan.recv(1024)
                if len(x) == 0:
                    print('
    *** EOF
    ',) 
                    f.close()    #退出时关闭记录文件
                    break
                sys.stdout.write(x)
                sys.stdout.flush()
            except socket.timeout:
                pass
        if sys.stdin in readable:    #处理用户输入发送到服务器执行
            inp = sys.stdin.readline()
            f.write(inp)    #记录用户输入
            chan.sendall(inp)
     
    chan.close()
    tran.close()
    

      

     

     

  • 相关阅读:
    一道简单的数组遍历题,加上四个条件后感觉无从下手
    五分钟小知识:如何用算法高效寻找素数?
    如何高效对有序数组/链表去重?
    中级控件——文本输入——文本变化监听器
    中级控件——对话框——提醒对话框AlertDialog
    数据存储——四种存储方式——存储卡的文件操作——私有存储空间与公共存储空间
    中级控件——文本输入——焦点变更监听器
    中级控件——对话框——日期对话框DatePickerDialog
    中级控件——对话框——时间对话框TimePickerDialog
    数据存储——四种存储方式——共享参数SharedPreferences——保存路径是:/data/data/应用包名/shared_prefs/文件名.xml——实现密码登录功能——此章节是前面的内容整合
  • 原文地址:https://www.cnblogs.com/yamei/p/5743729.html
Copyright © 2020-2023  润新知