python操作服務器,迷你庫ssh-lite發佈升級(支持shell交互/文件上傳下載,封裝自paramiko)

在做後臺測試/自動化運維的時候,使用python操作ssh服務器是很常見的情況。常規是使用paramiko庫,但他比較複雜,主要是讀取的請求是阻塞的(需要自己多線程管理)。甚至好多自動化測試教學培訓,都不涉及paramiko這個庫。
但操作linux確實是作爲測試,尤其自動化測試來講,算是四大基礎設施之一(其他的如操作數據庫,操作文件和操作網絡[發請求的客戶端,和收請求的服務端])。

網上並沒有找到專門目的是爲了簡化封裝ssh操作的庫,所以以前就封裝了一個用。對我來講,控制自動編譯、部署、啓停服務,管理docker容器、推送文件、日誌斷言都要依靠它。

目前是1.7版本,修復了對亂碼不兼容的bug,升級了expect斷言(支持了從服務器輸出中發現報錯的信息時可立即中斷),支持重定向debug信息到日誌文件或其他管道,修復了會在錯誤的目錄下安裝庫(但不影響功能)的問題
1.2版本升級解決了跳板機等機器不支持sftp服務時,創建ssh對象報錯的問題。

功能:

  • shell交互
  • 文件上傳下載
  • expect和grep
  • 預置組合鍵

github倉庫地址,歡迎issue PR和star
https://github.com/rainydew/ssh-lite

自己也想寫一個庫,上傳到pypi上給大家用? 參考我的另一篇博文https://blog.csdn.net/qq_27884799/article/details/96664812

這個庫目前已上傳至pypi,可以快速安裝(兼容python 3.5+)

pip install ssh-lite

注意ssh-lite是數學上的減號

簡單使用(注意import的時候,ssh_lite是下劃線,因爲不允許用-號)

from ssh_lite import Server

ci = Server("127.0.0.1", "123456", "root")
ci.send_and_read("")    # 先消化掉登錄後屏幕上的輸出,比如Last Login之類的信息
print(ci.send_and_read("ls -l"))   # 這樣,再打印的時候,就此時只剩下了ls -l後的輸出
del ci

效果

ls -l
total 1736
-rw-r--r-- 1 root  root  1775417 Aug 25  2019 get-pip.py
-rwxrwxrwx 1 root  root      289 Feb 20 12:00 temp.py
-rwxrwxrwx 1 root  root      136 Nov 22 21:18 upload

提供一個更復雜的示例,使用了上下文管理器來自動關閉連接

from ssh_lite import Server, KeyAbbr

remote = "/docker_binding_path"
file = "test.file"

with Server("127.0.0.1", "123456", "root", port=22, key_path=None) as ci:  # type: Server  # 這個庫也支持使用RSA密鑰文件
    ci.debug = True     # 將其改成True以後,所有的服務端輸出就會在控制檯也打印出來
    ci.get_file("/a_log_file_to_get", ".")      # 下載文件,目標路徑不需要文件名 
    ci.send_and_read("mkdir -p " + remote, timeout=1)
    ci.send_and_read("rm -f {}*".format(remote), timeout=1)
    ci.put_file("prepare/" + file, remote + file)      # 上傳文件則嚴格要求目標路徑也包含文件名(否則報錯)
    ci.send_and_read("", timeout=1)    # 在執行expect命令前,先清除緩衝區的其他信息文本
    cmd = 'docker exec -i container_name curl -v "http://127.0.0.1:9990/upload?file=/reference_path/{}&uri=me"'.format(
        file)
    print("inner cmd is: {}".format(cmd))
    ci.send(cmd)    # 發送docker內的指令
    ci.expect("< HTTP/1.1 200 OK", timeout=30)      # 在30s內如果看不到期待的輸出,則會報錯
    ci.send(KeyAbbr.CTRL_C, end="")      # 發送ctrl+C退出轉化的HTTP2長連接。默認換行符是\n,但發送ctrl+C不需要換行,所以指定end爲空
    ci.send('exit')       # 推出容器以便釋放連接
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章