1. 程式人生 > 程式設計 >使用Python paramiko模組利用多執行緒實現ssh併發執行操作

使用Python paramiko模組利用多執行緒實現ssh併發執行操作

1.paramiko概述

ssh是一個協議,OpenSSH是其中一個開源實現,paramiko是Python的一個庫,實現了SSHv2協議(底層使用cryptography)。

有了Paramiko以後,我們就可以在Python程式碼中直接使用SSH協議對遠端伺服器執行操作,而不是通過ssh命令對遠端伺服器進行操作。

由於paramiko屬於第三方庫,所以需要使用如下命令先行安裝

2.安裝paramiko

pip install paramiko

3.常用方法

connect():實現遠端伺服器的連線與認證,對於該方法只有hostname是必傳引數。

常用引數

hostname 連線的目標主機

port=SSH_PORT 指定埠

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():設定遠端伺服器沒有在know_hosts檔案中記錄時的應對策略。目前支援三種策略:

設定連線的遠端主機沒有本地主機金鑰或HostKeys物件時的策略,目前支援三種:

AutoAddPolicy 自動新增主機名及主機金鑰到本地HostKeys物件,不依賴load_system_host_key的配置。即新建立ssh連線時不需要再輸入yes或no進行確認

WarningPolicy 用於記錄一個未知的主機金鑰的python警告。並接受,功能上和AutoAddPolicy類似,但是會提示是新連線

RejectPolicy 自動拒絕未知的主機名和金鑰,依賴load_system_host_key的配置。此為預設選項

exec_command():在遠端伺服器執行Linux命令的方法。

如 exec_command("ls /")exec_command("df -h")

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,password=pwd)
  except:
   return 
#在ssh伺服器上執行指定命令,返回3項類檔案物件,分別是,輸入、輸出、錯誤
  stdin,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,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

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

步驟三:執行指令碼

執行指令碼,此指令碼有兩個引數,一個是檔案引數,一個是執行命令

[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併發執行操作,希望對大家有所幫助,如果大家有任何疑問請給我留言,小編會及時回覆大家的。在此也非常感謝大家對我們網站的支援!
如果你覺得本文對你有幫助,歡迎轉載,煩請註明出處,謝謝!