Python自動化運維 - paramiko模組介紹及使用
Paramiko是用python語言寫的一個模組,遠端連線到Linux伺服器,檢視上面的日誌狀態,批次配置遠端伺服器,檔案上傳,檔案下載等
paramiko是一個基於SSH用於連線遠端伺服器並執行相關操作(SSHClient和SFTPClinet,即一個是遠端連線,一個是上傳下載服務),使用該模組可以對遠端伺服器進行命令或檔案操作,值得一說的是,fabric和ansible內部的遠端管理就是使用的paramiko來現實。
簡介
ssh是一個協議,OpenSSH是其中一個開源實現,paramiko是Python的一個庫,實現了SSHv2協議(底層使用cryptography)。
有了Paramiko以後,我們就可以在Python程式碼中直接使用SSH協議對遠端伺服器執行操作,而不是透過ssh命令對遠端伺服器進行操作。
由於paramiko屬於第三方庫,所以需要使用如下命令先行安裝
pip3
install
paramiko
Paramiko介紹
paramiko包含兩個核心元件:SSHClient和SFTPClient。
SSHClient的作用類似於Linux的ssh命令,是對SSH會話的封裝,該類封裝了傳輸(Transport),通道(Channel)及SFTPClient建立的方法(open_sftp),通常用於執行遠端命令。
SFTPClient的作用類似與Linux的sftp命令,是對SFTP客戶端的封裝,用以實現遠端檔案操作,如檔案上傳、下載、修改檔案許可權等操作。
# Paramiko中的幾個基礎名詞:
1
、
Channel
:是一種類
Socket
,一種安全的
SSH傳輸通道
;
2
、
Transport
:是一種加密的會話,使用時會同步建立了一個加密的
Tunnels
(
通道
)
,這個
Tunnels叫做Channel
;
3
、
Session
:是
client與Server保持連線的物件
,用
connect
()
/
start_client
()
/
start_server
()
開始會話。
Paramiko的基本使用
SSHClient常用的方法介紹
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命令的方法。
open_sftp()
:在當前ssh會話的基礎上建立一個sftp會話。該方法會返回一個SFTPClient物件。
# 利用SSHClient物件的open_sftp()方法,可以直接返回一個基於當前連線的sftp物件,可以進行檔案的上傳等操作。
sftp
=
client
。
open_sftp
()
sftp
。
put
(
‘local。txt’
,
‘remote。txt’
)
SSHClient常用的方法舉例
import
paramiko
# 例項化SSHClient
ssh_client
=
paramiko
。
SSHClient
()
# 自動新增策略,儲存伺服器的主機名和金鑰資訊,如果不新增,那麼不再本地know_hosts檔案中記錄的主機將無法連線 ,此方法必須放在connect方法的前面
ssh_client
。
set_missing_host_key_policy
(
paramiko
。
AutoAddPolicy
())
# 連線SSH服務端,以使用者名稱和密碼進行認證 ,呼叫connect方法連線伺服器
ssh_client
。
connect
(
hostname
=
‘192。168。137。105’
,
port
=
22
,
username
=
‘root’
,
password
=
‘123456’
)
# 開啟一個Channel並執行命令 結果放到stdout中,如果有錯誤將放到stderr中
stdin
,
stdout
,
stderr
=
ssh_client
。
exec_command
(
‘df -hT ’
)
# stdout 為正確輸出,stderr為錯誤輸出,同時是有1個變數有值 # 列印執行結果 print(stdout。read()。decode(‘utf-8’))
# 關閉SSHClient連線
ssh_client
。
close
()
金鑰連線方式
# 配置私人金鑰檔案位置
private
=
paramiko
。
RSAKey
。
from_private_key_file
(
‘/root/。ssh/id_rsa’
)
#例項化SSHClient
ssh_client
=
paramiko
。
SSHClient
()
#自動新增策略,儲存伺服器的主機名和金鑰資訊,如果不新增,那麼不再本地know_hosts檔案中記錄的主機將無法連線
ssh_client
。
set_missing_host_key_policy
(
paramiko
。
AutoAddPolicy
())
#連線SSH服務端,以使用者名稱和密碼進行認證
ssh_client
。
connect
(
hostname
=
‘192。168。137。100’
,
port
=
22
,
username
=
‘root’
,
pkey
=
private
)
SFTPClient常用方法介紹
SFTPCLient作為一個sftp的客戶端物件
,根據
ssh傳輸協議的sftp會話
,實現遠端檔案操作,如上傳、下載、許可權、狀態
from_transport
(
cls
,
t
)
建立一個已連通的
SFTP客戶端通道
put
(
localpath
,
remotepath
,
callback
=
None
,
confirm
=
True
)
將本地檔案上傳到伺服器
引數
confirm
:是否呼叫
stat
()
方法檢查檔案狀態,返回
ls
-
l的結果
get
(
remotepath
,
localpath
,
callback
=
None
)
從伺服器下載檔案到本地
mkdir
()
在伺服器上建立目錄
remove
()
在伺服器上刪除目錄
rename
()
在伺服器上重新命名目錄
stat
()
檢視伺服器檔案狀態
listdir
()
列出伺服器目錄下的檔案
SFTPClient常用方法舉例
import
paramiko
# 例項化一個transport物件
tran
=
paramiko
。
Transport
((
‘192。168。137。100’
,
22
))
# 連線SSH服務端,使用password
tran
。
connect
(
username
=
“root”
,
password
=
‘123456’
)
# 或使用
# 配置私人金鑰檔案位置
private
=
paramiko
。
RSAKey
。
from_private_key_file
(
‘/root/。ssh/id_rsa’
)
# 連線SSH服務端,使用pkey指定私鑰
tran
。
connect
(
username
=
“root”
,
pkey
=
private
)
# 獲取SFTP例項
sftp
=
paramiko
。
SFTPClient
。
from_transport
(
tran
)
# 設定上傳的本地/遠端檔案路徑
local_path
=
“/home/1。txt”
remote_path
=
“/tmp/1。txt”
# 執行上傳動作
sftp
。
put
(
local_path
,
remote_path
)
# 執行下載動作
sftp
。
get
(
remote_path
,
local_path
)
# 關閉Transport通道
tran
。
close
()
完整程式碼示例:
操作單臺主機
# 單臺主機操作
import
paramiko
# 登陸引數設定
hostname
=
“192。168。137。100”
host_port
=
22
username
=
“root”
password
=
“123456”
def
ssh_client_con
():
“”“建立ssh連線,並執行shell指令”“”
# 1 建立ssh_client例項
ssh_client
=
paramiko
。
SSHClient
()
# 自動處理第一次連線的yes或者no的問題
ssh_client
。
set_missing_host_key_policy
(
paramiko
。
AutoAddPolicy
)
# 2 連線伺服器
ssh_client
。
connect
(
port
=
host_port
,
hostname
=
hostname
,
username
=
username
,
password
=
password
)
# 3 執行shell命令
# 構造shell指令
shell_command
=
“ps aux”
# 執行shell指令
stdin
,
stdout
,
stderr
=
ssh_client
。
exec_command
(
shell_command
)
# 輸出返回資訊
stdout_info
=
stdout
。
read
()
。
decode
(
‘utf8’
)
(
stdout_info
)
# 輸出返回的錯誤資訊
stderr_info
=
stderr
。
read
()
。
decode
(
‘utf8’
)
(
stderr_info
)
def
sftp_client_con
():
# 1 建立transport通道
tran
=
paramiko
。
Transport
((
hostname
,
host_port
))
tran
。
connect
(
username
=
username
,
password
=
password
)
# 2 建立sftp例項
sftp
=
paramiko
。
SFTPClient
。
from_transport
(
tran
)
# 3 執行上傳功能
local_path
=
“米湯。jpg”
# 本地路徑
remote_path
=
“/home/333。jpg”
# 遠端路徑
put_info
=
sftp
。
put
(
local_path
,
remote_path
,
confirm
=
True
)
(
put_info
)
(
f
“上傳{local_path}完成”
)
# 4 執行下載功能
save_path
=
“7。jpg”
# 本地儲存檔案路徑
sftp
。
get
(
remotepath
=
remote_path
,
localpath
=
save_path
)
(
f
‘下載{save_path}完成’
)
# 5 關閉通道
tran
。
close
()
# 呼叫函式執行功能
ssh_client_con
()
sftp_client_con
()
# 本例是單個主機操作
批次操作主機
import
paramiko
def
ssh_client_con
():
“”“建立ssh連線,並執行shell指令”“”
# 1 建立ssh_client例項
ssh_client
=
paramiko
。
SSHClient
()
# 自動處理第一次連線的yes或者no的問題
ssh_client
。
set_missing_host_key_policy
(
paramiko
。
AutoAddPolicy
)
# 2 連線伺服器
ssh_client
。
connect
(
port
=
host_port
,
hostname
=
hostname
,
username
=
username
,
password
=
password
)
# 3 執行shell命令
# 構造shell指令
shell_command
=
“”“
path=‘/tmp’
tree ${path}
# 如果tree命令執行失敗,則安裝tree後再執行
if [ $? -ne 0 ]
then
yum install -y tree
tree ${path}
fi
”“”
# 執行shell指令
stdin
,
stdout
,
stderr
=
ssh_client
。
exec_command
(
shell_command
)
# 輸出返回資訊
stdout_info
=
stdout
。
read
()
。
decode
(
‘utf8’
)
(
stdout_info
)
# 輸出返回的錯誤資訊
stderr_info
=
stderr
。
read
()
。
decode
(
‘utf8’
)
(
stderr_info
)
def
sftp_client_con
():
# 1 建立transport通道
tran
=
paramiko
。
Transport
((
hostname
,
host_port
))
tran
。
connect
(
username
=
username
,
password
=
password
)
# 2 建立sftp例項
sftp
=
paramiko
。
SFTPClient
。
from_transport
(
tran
)
# 3 執行上傳功能
local_path
=
“米湯。jpg”
remote_path
=
“/home/333。jpg”
put_info
=
sftp
。
put
(
local_path
,
remote_path
,
confirm
=
True
)
(
put_info
)
(
f
“上傳{local_path}完成”
)
# 4 執行下載功能
save_path
=
“7。jpg”
sftp
。
get
(
remotepath
=
remote_path
,
localpath
=
save_path
)
(
f
‘下載{save_path}完成’
)
# 5 關閉通道
tran
。
close
()
# 讀取主機資訊
try
:
with
open
(
‘host_site。txt’
,
‘r’
,
encoding
=
‘utf8’
)
as
host_file
:
for
host_info
in
host_file
:
line
=
host_info
。
strip
(
‘
\n
’
)
hostname
,
host_port
,
username
,
password
=
line
。
split
(
‘,’
)
(
f
‘————————-{hostname}執行結果——————-’
)
ssh_client_con
()
# 執行command並返回結果
# 本例適合批次主機處理相同的command
except
FileNotFoundError
as
e
:
(
e
)
# host_site。txt 檔案內容格式如下
# 主機地址 埠 使用者 密碼
# 192。168。137。100,22,root,123456
# 192。168。137。101,22,root,123456
# 192。168。137。102,22,root,123456
# 192。168。137。103,22,root,123456
# 192。168。137。104,22,root,123456