zoukankan      html  css  js  c++  java
  • 【python】-- paramiko、跳板机(堡垒机)

    paramiko

    Python的paramiko模块,该模块用于连接远程服务器并执行相关命令,常用于作批量管理使用

    一、下载:

    pip3 install paramiko
    

    源码:查看

    二、paramiko代码实例:

    1、SSHClient

    SSHClient 作用:用于连接远程服务器并执行基本命令

    1.1、基于用户名密码连接远程服务器

    import paramiko
       
    # 创建SSH对象
    ssh = paramiko.SSHClient()
    # 允许连接不在know_hosts文件中的主机
    ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
    # 连接服务器
    ssh.connect(hostname='c1.salt.com', port=22, username='shuaigaogao', password='0808')
    # 执行命令
    stdin, stdout, stderr = ssh.exec_command('df') #stdin =>  标准输入,就是你输入的那个命令   stdout => 标准输出,你输入命令后执行的结果   stderr => 标准错误,名利执行的过程中,如果出错了,就把这个错误打到这里
    # 获取命令结果
    result = stdout.read()  #输出的结果是bytes类型的
    # 关闭连接
    ssh.close()
    

      

    1.1.1、SSHClient 封装 Transport

    import paramiko
     
    transport = paramiko.Transport(('hostname', 22))
    transport.connect(username='zhangqigao', password='123')
     
    ssh = paramiko.SSHClient()
    ssh._transport = transport
     
    stdin, stdout, stderr = ssh.exec_command('df')
    print stdout.read()
     
    transport.close()
    

     1.2、基于公钥密钥链接

    import paramiko
      
    private_key = paramiko.RSAKey.from_private_key_file('/home/auto/.ssh/id_rsa') #私钥文件的路径
      
    # 创建SSH对象
    ssh = paramiko.SSHClient()
    # 允许连接不在know_hosts文件中的主机
    ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
    # 连接服务器
    ssh.connect(hostname='192.168.128.13', port=22, username='zhangqigao', pkey=private_key)
      
    # 执行命令
    stdin, stdout, stderr = ssh.exec_command('df')
    # 获取命令结果
    result = stdout.read()
      
    # 关闭连接
    ssh.close()
    

    1.2.1、SSHClient 封装 Transport

    import paramiko
     
    private_key = paramiko.RSAKey.from_private_key_file('/home/auto/.ssh/id_rsa')
     
    transport = paramiko.Transport(('hostname', 22))
    transport.connect(username='wupeiqi', pkey=private_key)
     
    ssh = paramiko.SSHClient()
    ssh._transport = transport
     
    stdin, stdout, stderr = ssh.exec_command('df')
     
    transport.close()
    

    1.3、基于私钥字符串进行连接

    import paramiko
    from io import StringIO
    
    key_str = """-----BEGIN RSA PRIVATE KEY-----
    MIIEpQIBAAKCAQEAq7gLsqYArAFco02/55IgNg0r7NXOtEM3qXpb/dabJ5Uyky/8
    NEHhFiQ7deHIRIuTW5Zb0kD6h6EBbVlUMBmwJrC2oSzySLU1w+ZNfH0PE6W6fans
    H80whhuc/YgP+fjiO+VR/gFcqib8Rll5UfYzf5H8uuOnDeIXGCVgyHQSmt8if1+e
    7hn1MVO1Lrm9Fco8ABI7dyv8/ZEwoSfh2C9rGYgA58LT1FkBRkOePbHD43xNfAYC
    tfLvz6LErMnwdOW4sNMEWWAWv1fsTB35PAm5CazfKzmam9n5IQXhmUNcNvmaZtvP
    c4f4g59mdsaWNtNaY96UjOfx83Om86gmdkKcnwIDAQABAoIBAQCnDBGFJuv8aA7A
    ZkBLe+GN815JtOyye7lIS1n2I7En3oImoUWNaJEYwwJ8+LmjxMwDCtAkR0XwbvY+
    c+nsKPEtkjb3sAu6I148RmwWsGncSRqUaJrljOypaW9dS+GO4Ujjz3/lw1lrxSUh
    IqVc0E7kyRW8kP3QCaNBwArYteHreZFFp6XmtKMtXaEA3saJYILxaaXlYkoRi4k8
    S2/K8aw3ZMR4tDCOfB4o47JaeiA/e185RK3A+mLn9xTDhTdZqTQpv17/YRPcgmwz
    zu30fhVXQT/SuI0sO+bzCO4YGoEwoBX718AWhdLJFoFq1B7k2ZEzXTAtjEXQEWm6
    01ndU/jhAasdfasdasdfasdfa3eraszxqwefasdfadasdffsFIfAsjQb4HdkmHuC
    OeJrJOd+CYvdEeqJJNnF6AbHyYHIECkj0Qq1kEfLOEsqzd5nDbtkKBte6M1trbjl
    HtJ2Yb8w6o/q/6Sbj7wf/cW3LIYEdeVCjScozVcQ9R83ea05J+QOAr4nAoGBAMaq
    UzLJfLNWZ5Qosmir2oHStFlZpxspax/ln7DlWLW4wPB4YJalSVovF2Buo8hr8X65
    lnPiE41M+G0Z7icEXiFyDBFDCtzx0x/RmaBokLathrFtI81UCx4gQPLaSVNMlvQA
    539GsubSrO4LpHRNGg/weZ6EqQOXvHvkUkm2bDDJAoGATytFNxen6GtC0ZT3SRQM
    WYfasdf3xbtuykmnluiofasd2sfmjnljkt7khghmghdasSDFGQfgaFoKfaawoYeH
    C2XasVUsVviBn8kPSLSVBPX4JUfQmA6h8HsajeVahxN1U9e0nYJ0sYDQFUMTS2t8
    RT57+WK/0ONwTWHdu+KnaJECgYEAid/ta8LQC3p82iNAZkpWlGDSD2yb/8rH8NQg
    9tjEryFwrbMtfX9qn+8srx06B796U3OjifstjJQNmVI0qNlsJpQK8fPwVxRxbJS/
    pMbNICrf3sUa4sZgDOFfkeuSlgACh4cVIozDXlR59Z8Y3CoiW0uObEgvMDIfenAj
    98pl3ZkCgYEAj/UCSni0dwX4pnKNPm6LUgiS7QvIgM3H9piyt8aipQuzBi5LUKWw
    DlQC4Zb73nHgdREtQYYXTu7p27Bl0Gizz1sW2eSgxFU8eTh+ucfVwOXKAXKU5SeI
    +MbuBfUYQ4if2N/BXn47+/ecf3A4KgB37Le5SbLDddwCNxGlBzbpBa0=
    -----END RSA PRIVATE KEY-----"""
    
    private_key = paramiko.RSAKey(file_obj=StringIO(key_str))
    transport = paramiko.Transport(('10.0.1.40', 22))
    transport.connect(username='wupeiqi', pkey=private_key)
    
    ssh = paramiko.SSHClient()
    ssh._transport = transport
    
    stdin, stdout, stderr = ssh.exec_command('df')
    result = stdout.read()
    
    transport.close()
    
    print(result)
    

    2、SFTPClient

    SFTPClient作用:用于连接远程服务器并执行上传下载

    2.1、基于用户名密码上传下载

    import paramiko
      
    transport = paramiko.Transport(('hostname',22))
    transport.connect(username='zhangqigao',password='123')
      
    sftp = paramiko.SFTPClient.from_transport(transport)
    # 将location.py 上传至服务器 /tmp/test.py
    sftp.put('/tmp/location.py', '/tmp/test.py')
    # 将remove_path 下载到本地 local_path
    sftp.get('remove_path', 'local_path')
      
    transport.close()
    

    2.2、基于公钥密钥上传下载

    import paramiko
      
    private_key = paramiko.RSAKey.from_private_key_file('/home/auto/.ssh/id_rsa')  #私钥文件路径
      
    transport = paramiko.Transport(('hostname', 22))
    transport.connect(username='wupeiqi', pkey=private_key )
      
    sftp = paramiko.SFTPClient.from_transport(transport)
    # 将location.py 上传至服务器 /tmp/test.py
    sftp.put('/tmp/location.py', '/tmp/test.py')
    # 将remove_path 下载到本地 local_path
    sftp.get('remove_path', 'local_path')
      
    transport.close()
    

      

     

    跳板机(堡垒机)

    堡垒机作用:

    一、权限管理

     当你公司的服务器变的越来越多后,需要操作这些服务器的人就肯定不只是一个运维人员,同时也可能包括多个开发人员,那么这么多的人操作业务系统,如果权限分配不当就会存在很大的安全风险,举几个场景例子:

    1. 设想你们公司有300台Linux服务器,A开发人员需要登录其中5台WEB服务器查看日志或进行问题追踪等事务,同时对另外10台hadoop服务器有root权限,在有300台服务器规模的网络中,按常理来讲你是已经使用了ldap权限统一认证的,你如何使这个开发人员只能以普通用户的身份登录5台web服务器,并且同时允许他以管理员的身份登录另外10台hadoop服务器呢?并且同时他对其它剩下的200多台服务器没有访问权限

    2. 目前据我了解,很多公司的运维团队为了方面,整个运维团队的运维人员还是共享同一套root密码,这样内部信任机制虽然使大家的工作方便了,但同时存在着极大的安全隐患,很多情况下,一个运维人员只需要管理固定数量的服务器,毕竟公司分为不同的业务线,不同的运维人员管理的业务线也不同,但如果共享一套root密码,其实就等于无限放大了每个运维人员的权限,也就是说,如果某个运维人员想干坏事的话,他可以在几分钟内把整个公司的业务停转,甚至数据都给删除掉。为了降低风险,于是有人想到,把不同业务线的root密码改掉就ok了么,也就是每个业务线的运维人员只知道自己的密码,这当然是最简单有效的方式,但问题是如果你同时用了ldap,这样做又比较麻烦,即使你设置了root不通过ldap认证,那新问题就是,每次有运维人员离职,他所在的业务线的密码都需要重新改一次。

    其实上面的问题,我觉得可以很简单的通过堡垒机来实现,收回所有人员的直接登录服务器的权限,所有的登录动作都通过堡垒机授权,运维人员或开发人员不知道远程服务器的密码,这些远程机器的用户信息都绑定在了堡垒机上,堡垒机用户只能看到他能用什么权限访问哪些远程服务器。

    在回收了运维或开发人员直接登录远程服务器的权限后,其实就等于你们公司生产系统的所有认证过程都通过堡垒机来完成了,堡垒机等于成了你们生产系统的SSO(single sign on)模块了。你只需要在堡垒机上添加几条规则就能实现以下权限控制了:

    1. 允许A开发人员通过普通用户登录5台web服务器,通过root权限登录10台hadoop服务器,但对其余的服务器无任务访问权限

    2. 多个运维人员可以共享一个root账户,但是依然能分辨出分别是谁在哪些服务器上操作了哪些命令,因为堡垒机账户是每个人独有的,也就是说虽然所有运维人员共享了一同一个远程root账户,但由于他们用的堡垒账户都是自己独有的,因此依然可以通过堡垒机控制每个运维人员访问不同的机器。

     二、审计管理

    审计管理其实很简单,就是把用户的所有操作都纪录下来,以备日后的审计或者事故后的追责。在纪录用户操作的过程中有一个问题要注意,就是这个纪录对于操作用户来讲是不可见的,什么意思?就是指,无论用户愿不愿意,他的操作都会被纪录下来,并且,他自己如果不想操作被纪录下来,或想删除已纪录的内容,这些都是他做不到的,这就要求操作日志对用户来讲是不可见和不可访问的,通过堡垒机就可以很好的实现。

    三、堡垒机架构 

    堡垒机的主要作用权限控制和用户行为审计,堡垒机就像一个城堡的大门,城堡里的所有建筑就是你不同的业务系统 , 每个想进入城堡的人都必须经过城堡大门并经过大门守卫的授权,每个进入城堡的人必须且只能严格按守卫的分配进入指定的建筑,且每个建筑物还有自己的权限访问控制,不同级别的人可以到建筑物里不同楼层的访问级别也是不一样的。还有就是,每个进入城堡的人的所有行为和足迹都会被严格的监控和纪录下来,一旦发生犯罪事件,城堡管理人员就可以通过这些监控纪录来追踪责任人。 

    堡垒要想成功完全记到他的作用,只靠堡垒机本身是不够的, 还需要一系列安全上对用户

    进行限制的配合,堡垒机部署上后,同时要确保你的网络达到以下条件:

    • 所有人包括运维、开发等任何需要访问业务系统的人员,只能通过堡垒机访问业务系统
      • 回收所有对业务系统的访问权限,做到除了堡垒机管理人员,没有人知道业务系统任何机器的登录密码
      • 网络上限制所有人员只能通过堡垒机的跳转才能访问业务系统 
    • 确保除了堡垒机管理员之外,所有其它人对堡垒机本身无任何操作权限,只有一个登录跳转功能
    • 确保用户的操作纪录不能被用户自己以任何方式获取到并篡改 

    五、堡垒机代码实例:

    点击:查看

  • 相关阅读:
    Java 跨系统开发隐患(一)
    SpringBoot邮件推送功能
    基于图灵api的Python机器人
    JSP编码问题解决方法
    记一次数据结构课设
    基于百度语音识别API的Python语音识别小程序
    帝国cms过滤采集内容
    如何批量取消文章审核
    评论时判断会员是否登录
    帝国cms把文章加入到收藏夹代码
  • 原文地址:https://www.cnblogs.com/Keep-Ambition/p/8206834.html
Copyright © 2011-2022 走看看