Python Paramiko多线程SSH并发执行指南

云舒
云舒
发布时间:2026-10-13 | 4人浏览过
原创

本文介绍如何使用Python的Paramiko库结合多线程技术,实现对多台远程Linux服务器的SSH并发访问与命令执行。内容涵盖Paramiko的安装、核心API(connect、exec_command等)详解,以及通过编写Python脚本读取IP列表,利用threading模块实现高效批量运维操作的具体步骤和代码示例。

Paramiko概述与安装

Paramiko概述

SSH是一种网络协议,OpenSSH是其常见的开源实现。Paramiko则是Python语言中用于实现SSHv2协议的第三方库,其底层依赖cryptography库进行加密处理。

借助Paramiko,开发者可以直接在Python代码中调用SSH协议与远程服务器进行交互,从而替代传统的通过命令行使用ssh命令的操作方式,使自动化脚本编写更加灵活。

由于Paramiko并非Python标准库,使用前需通过命令行工具进行安装。

安装Paramiko

pip install paramiko

Paramiko常用方法详解

3. 常用方法

connect()方法用于建立与远程服务器的连接并完成身份认证,其中hostname是唯一的必传参数。

常用参数说明

hostname:指定要连接的目标主机地址。

port=SSH_PORT:指定SSH服务的端口号。

username=None:指定登录验证的用户名。

password=None:指定登录验证的用户密码。

pkey=None:用于指定私钥文件进行身份验证。

key_filename=None:指定私钥文件路径,可以是单个文件或文件列表。

timeout=None:设置TCP连接的可选超时时间。

allow_agent=True:是否允许连接SSH代理,默认为True。

look_for_keys=True:是否在~/.ssh目录下搜索私钥文件,默认为True。

compress=False:是否启用数据压缩功能。

set_missing_host_key_policy()方法用于处理远程服务器主机密钥未记录在本地known_hosts文件中的情况,支持三种策略。

当连接远程主机且本地没有该主机的密钥或HostKeys对象时,需设置相应策略。目前支持以下三种:

AutoAddPolicy:自动将新主机名及密钥添加到本地HostKeys对象,不受load_system_host_key配置影响。使用此策略时,新建SSH连接无需手动输入yes或no确认。

WarningPolicy:对未知主机密钥发出Python警告但仍接受连接。功能与AutoAddPolicy类似,但会提示这是新连接。

RejectPolicy:自动拒绝未知主机名和密钥,依赖load_system_host_key的配置。这是Paramiko的默认选项。

exec_command()方法用于在远程服务器上执行Linux命令。

例如:exec_command("ls /") 或 exec_command("df -h")。

多线程SSH并发执行实现

4. 使用方法


import paramiko
  # 实例化SSHClient
  client = paramiko.SSHClient()
 
  # 自动添加策略,保存服务器的主机名和密钥信息,如果不添加,那么不再本地know_hosts文件中记录的主机将无法连接
  client.set_missing_host_key_policy(paramiko.AutoAddPolicy())
 
  # 连接SSH服务端,以用户名和密码进行认证
  client.connect(hostname='192.168.1.1', port=22, username='root', password='123456')
 
  # 打开一个Channel并执行命令
  stdin, stdout, stderr = client.exec_command('df -h ') # stdout 为正确输出,stderr为错误输出,同时是有1个变量有值
 
  # 打印执行结果
  print(stdout.read().decode('utf-8'))
 
  # 关闭SSHClient
  client.close()

5. 利用多线程实现SSH并发访问

需求如下:

编写一个名为remote_comm.py的脚本,实现以下功能:

  • 从指定文件中读取所有远程主机的IP地址。
  • 在Shell命令行中接收远程服务器IP地址文件路径、服务器密码以及需要在远程主机上执行的命令。
  • 通过多线程技术,在所有远程服务器上并发执行指定命令。

步骤一:编写脚本


#!/usr/bin/env python3
import sys
import getpass
import paramiko
import threading
import os
#创建函数实现远程连接主机、服务器密码以及在远程主机上执行的命令的功能
def remote_comm(host, pwd, command):
#创建用于连接ssh服务器的实例
  ssh = paramiko.SSHClient()
#设置自动添加主机密钥
  ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
#连接ssh服务器,添加连接的主机、用户名、密码填好,捕获异常,有异常则跳出函数
  try:
   ssh.connect(hostname=host, username='root', password=pwd)
  except:
   return 
#在ssh服务器上执行指定命令,返回3项类文件对象,分别是,输入、输出、错误
  stdin, stdout, stderr = ssh.exec_command(command)
#读取输出
  out = stdout.read()
#读取错误
  error = stderr.read()
#如果有输出
  if out:
#打印主机输出内容
    print('[%s] OUT:\n%s' % (host, out.decode('utf8')))
#如果有错误
  if error:
#打印主机错误信息
    print('[%s] ERROR:\n%s' % (host, error.decode('utf8')))
#程序结束
  ssh.close()
if __name__ == '__main__':
#设定sys.argv长度,确保remote_comm函数中参数数量
  if len(sys.argv) != 3:
    print('Usage: %s ipaddr_file "command"' % sys.argv[0])
    exit(1)
#判断命令行上输入如果不是文件,确保输入的是文件 
  if not os.path.isfile(sys.argv[1]):
    print('No such file:', sys.argv[1])
    exit(2)
#fname为存储远程主机ip的文件,用sys.argv方法,可以在执行脚本时再输入文件名,更为灵活
  fname = sys.argv[1]
#command为在远程主机上执行的命令,用sys.argv方法,可以在执行脚本时再输入相应命令,command为remote_comm函数第三个参数
  command = sys.argv[2]
#通过getpass输入远程服务器密码,pwd为remote_comm函数第二个参数
  # pwd = getpass.getpass()
  pwd='Taren1.bgsn'
#打开存有远程主机ip的文件
  with open(fname) as fobj:
#将遍历文件将ip以列表形式存入ips,line.strip()可以去掉每行ip后\n
    ips = [line.strip() for line in fobj]
#循环遍历列表,获取ip地址,ip为remote_comm函数第一个参数
  for ip in ips:
#将读取到的ip地址作为remote_comm函数实际参数传递给函数,ips中有几个ip地址循环几次
#创建多线程
    t = threading.Thread(target=remote_comm, args=(ip, pwd, command))
#启用多线程
    t.start()

步骤二:准备SSH主机列表

创建一个文件,包含某个网段内所有可ping通的IP地址。可以使用nmap扫描活跃主机,或自行编写Python脚本生成该列表。


[root@room9pc01 ~]#nmap -n -sP 176.130.7.0/24 | grep 176 | awk '{print $5}' > /mnt/server_addr.txt
[root@room9pc01 ~]#cat /mnt/server_addr.txt
Nmap scan report for 176.130.7.1
Nmap scan report for 176.130.7.24
Nmap scan report for 176.130.7.46
Nmap scan report for 176.130.7.53
Nmap scan report for 176.130.7.57

.....................

步骤三:执行脚本

运行脚本,该脚本接受两个参数:一个是包含IP地址的文件路径,另一个是要执行的命令。


[root@room9pc01 mnt]# python3 ssh.py server_addr.txt 'who'
[176.130.7.57] OUT:
student :0      2019-12-02 09:04 (:0)
student pts/0    2019-12-02 15:03 (:0)
[176.130.7.169] OUT:
student :0      2019-12-02 08:17 (:0)
student pts/0    2019-12-02 08:23 (:0)
student pts/4    2019-12-02 08:24 (:0)
[176.130.7.162] OUT:
student :0      2019-12-02 08:17 (:0)
student pts/0    2019-12-02 15:03 (:0)
[176.130.7.178] OUT:
student :0      2019-12-02 08:06 (:0)

总结

总结

以上介绍了使用Python Paramiko模块结合多线程实现SSH并发执行操作的方法,希望对读者有所帮助。如有任何疑问,欢迎留言,小编会及时回复。感谢大家对本站的支持! 如果觉得本文对您有帮助,欢迎转载,请注明出处,谢谢!

本站声明

本文内容仅供参考,不代表本站观点。转载或引用请注明出处。如发现内容问题,请通过联系我们页面反馈。

Python 相关产品和应用

全部下载

专题列表