Python模块:paramiko
paramiko是一个用于做远程控制的模块,使用该模块可以对远程服务器进行命令或文件操作,值得一说的是,fabric和ansible内部的远程管理就是使用的paramiko来现实。
1、下载安装
Windows:pip3 install paramiko
Linux:
# pycrypto,由于 paramiko 模块内部依赖pycrypto,所以先下载安装pycrypto # 下载安装 pycrypto wget http://ftp.dlitz.net/pub/dlitz/crypto/pycrypto/pycrypto-2.6.tar.gz tar -xvf pycrypto-2.6.1.tar.gz cd pycrypto-2.6.1 python setup.py build python setup.py install # 进入python环境,导入Crypto检查是否安装成功 from Crypto.Cipher import AES # 下载安装 paramiko 目前新的版本,官网在此: https://github.com/paramiko/paramiko unzip paramiko-master.zip cd paramiko-master python setup.py build python setup.py install centos7 Python3 可以直接pip3 install paramiko 我用的这种方法 # 进入python环境,导入paramiko检查是否安装成功
1 [root@greg02 ~]# pip3 install paramiko 2 Collecting paramiko 3 Downloading paramiko-2.4.0-py2.py3-none-any.whl (192kB) 4 100% |████████████████████████████████| 194kB 65kB/s 5 Collecting bcrypt>=3.1.3 (from paramiko) 6 Downloading bcrypt-3.1.4-cp36-cp36m-manylinux1_x86_64.whl (54kB) 7 100% |████████████████████████████████| 61kB 99kB/s 8 Collecting cryptography>=1.5 (from paramiko) 9 Downloading cryptography-2.1.3-cp36-cp36m-manylinux1_x86_64.whl (2.2MB) 10 100% |████████████████████████████████| 2.2MB 95kB/s 11 Collecting pyasn1>=0.1.7 (from paramiko) 12 Downloading pyasn1-0.3.7-py2.py3-none-any.whl (63kB) 13 100% |████████████████████████████████| 71kB 203kB/s 14 Collecting pynacl>=1.0.1 (from paramiko) 15 Downloading PyNaCl-1.2.0-cp36-cp36m-manylinux1_x86_64.whl (692kB) 16 100% |████████████████████████████████| 696kB 91kB/s 17 Collecting six>=1.4.1 (from bcrypt>=3.1.3->paramiko) 18 Downloading six-1.11.0-py2.py3-none-any.whl 19 Collecting cffi>=1.1 (from bcrypt>=3.1.3->paramiko) 20 Downloading cffi-1.11.2-cp36-cp36m-manylinux1_x86_64.whl (419kB) 21 100% |████████████████████████████████| 430kB 339kB/s 22 Collecting idna>=2.1 (from cryptography>=1.5->paramiko) 23 Downloading idna-2.6-py2.py3-none-any.whl (56kB) 24 100% |████████████████████████████████| 61kB 388kB/s 25 Collecting asn1crypto>=0.21.0 (from cryptography>=1.5->paramiko) 26 Downloading asn1crypto-0.23.0-py2.py3-none-any.whl (99kB) 27 100% |████████████████████████████████| 102kB 416kB/s 28 Collecting pycparser (from cffi>=1.1->bcrypt>=3.1.3->paramiko) 29 Downloading pycparser-2.18.tar.gz (245kB) 30 100% |████████████████████████████████| 256kB 387kB/s 31 Installing collected packages: six, pycparser, cffi, bcrypt, idna, asn1crypto, cryptography, pyasn1, pynacl, paramiko 32 Running setup.py install for pycparser ... done 33 Successfully installed asn1crypto-0.23.0 bcrypt-3.1.4 cffi-1.11.2 cryptography-2.1.3 idna-2.6 paramiko-2.4.0 pyasn1-0.3.7 pycparser-2.18 pynacl-1.2.0 six-1.11.0 34 [root@greg02 ~]# python3 35 Python 3.6.2 (default, Nov 15 2017, 04:14:48) 36 [GCC 4.8.5 20150623 (Red Hat 4.8.5-16)] on linux 37 Type "help", "copyright", "credits" or "license" for more information. 38 >>> import paramiko 39 >>>
2.远程连接Linux(centos7)并打印命令结果
import paramiko # 创建SSH对象 ssh = paramiko.SSHClient() # 允许连接不在know_hosts文件中的主机 ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy()) # 连接服务器 ssh.connect('192.168.179.130', 22, 'root', '123456') # 执行命令 stdin, stdout, stderr = ssh.exec_command('df') # 获取命令结果 print(stdout.read()) # 关闭连接 ssh.close()
3. 通过公钥连接,前提是两台Linux可以互相连接
比如在Linux1(192.168.179.131)上配置公钥私钥,通过ssh 192.168.179.130无需输入密码可以连接Linux2
[root@greg02 ~]# ssh 192.168.179.130 Last login: Wed Nov 15 19:31:19 2017 from 192.168.179.131 [root@greg01 ~]# [root@greg01 ~]#exit logout Connection to 192.168.179.130 closed.
import paramiko private_key = paramiko.RSAKey.from_private_key_file('/root/.ssh/id_rsa') # 创建SSH对象 ssh = paramiko.SSHClient() # 允许连接不在know_hosts文件中的主机 ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy()) # 连接服务器 ssh.connect('192.168.179.130', 22, 'root', '123456',key=private_key)
# 执行命令
stdin, stdout, stderr = ssh.exec_command('df')
# 获取命令结果
result = stdout.read()
# 关闭连接
ssh.close()
4.上传或下载文件
import os,sys import paramiko t = paramiko.Transport(('192.168.179.130',22)) t.connect(username='root',password='greg311') sftp = paramiko.SFTPClient.from_transport(t) sftp.get('/root/test.py','d:/test.py') sftp.put('d:/test.jpg','/root/test.jpg') t.close()
5.通过密钥上传或下载文件
import paramiko pravie_key_path = '/root/.ssh/id_rsa' key = paramiko.RSAKey.from_private_key_file(pravie_key_path) t = paramiko.Transport(('192.168.179.130',22)) t.connect(username='wupeiqi',pkey=key) sftp = paramiko.SFTPClient.from_transport(t) sftp.put('/tmp/test3.py','/tmp/test3.py') sftp.get('/tmp/test4.py','/tmp/test4.py') t.close()
6.python3 paramiko-master/demos/demo.py
[root@greg02 demos]#python3 demo.py Hostname: 192.168.179.131 *** WARNING: Unknown host key! Username [root]: root Auth by (p)assword, (r)sa key, or (d)ss key? [p] p Password for root@192.168.179.131: *** Here we go! Last login: Wed Nov 15 19:09:05 2017 from 192.168.179.1 [root@greg01 ~]# ls 123.txt anaconda-ks.cfg index.html para2.py rsync [root@greg01 ~]# exit logout *** EOF [root@greg02 demos]#vim demo.py
7.interactive捕获命令并记录
1 import socket 2 import sys 3 import time 4 from paramiko.py3compat import u 5 6 # windows does not have termios... 7 try: 8 import termios 9 import tty 10 has_termios = True 11 except ImportError: 12 has_termios = False 13 14 15 def interactive_shell(chan): 16 if has_termios: 17 posix_shell(chan) 18 else: 19 windows_shell(chan) 20 21 22 def posix_shell(chan): 23 import select 24 25 oldtty = termios.tcgetattr(sys.stdin) 26 try: 27 tty.setraw(sys.stdin.fileno()) 28 tty.setcbreak(sys.stdin.fileno()) 29 chan.settimeout(0.0) 30 cmd = [] 31 f = open('ssh_test.log','w') 32 while True: 33 r, w, e = select.select([chan, sys.stdin], [], []) 34 if chan in r: 35 try: 36 x = u(chan.recv(1024)) 37 if len(x) == 0: 38 sys.stdout.write('\r\n*** EOF\r\n') 39 break 40 sys.stdout.write(x) 41 sys.stdout.flush() 42 except socket.timeout: 43 pass 44 if sys.stdin in r: 45 x = sys.stdin.read(1) 46 if len(x) == 0: 47 break 48 if x == '\r': 49 print('input>',''.join(cmd)) 50 log = "%s %s\n" %(time.strftime("%Y-%m-%d %X", time.gmtime()), ''.join(cmd)) 51 print(log) 52 f.write(log) 53 cmd = [] 54 else: 55 cmd.append(x) 56 chan.send(x) 57 58 finally: 59 termios.tcsetattr(sys.stdin, termios.TCSADRAIN, oldtty) 60 f.close() 61 62 # thanks to Mike Looijmans for this code 63 def windows_shell(chan): 64 65 print("window chan",chan.host_to_user_obj) 66 print("window chan",chan.crazyeye_account) 67 import threading 68 69 sys.stdout.write("Line-buffered terminal emulation. Press F6 or ^Z to send EOF.\r\n\r\n") 70 71 def writeall(sock): 72 while True: 73 data = sock.recv(256) 74 if not data: 75 sys.stdout.write('\r\n*** EOF ***\r\n\r\n') 76 sys.stdout.flush() 77 break 78 sys.stdout.write(data) 79 sys.stdout.flush() 80 81 writer = threading.Thread(target=writeall, args=(chan,)) 82 writer.start() 83 84 try: 85 while True: 86 d = sys.stdin.read(1) 87 if not d: 88 break 89 chan.send(d) 90 except EOFError: 91 # user hit ^Z or F6 92 pass
运行:
[root@greg02 demos]#cat ssh_test.log 2017-11-15 12:33:18 ls 2017-11-15 12:33:32 cd /pa pa mi 2017-11-15 12:33:33 ls 2017-11-15 12:33:40 exit