大聊Python----通过Socket实现简单的ssh客户端
光只是简单的发消息、收消息没意思,干点正事,可以做一个极简版的ssh,就是客户端连接上服务器后,让服务器执行命令,并返回结果给客户端。
#ssh_client.py import socket client = socket.socket() # 生命socket类型 同时 生成socket连接# 对相
client.connect(('HW-20180425SPSL',6969)) # 连接6969端口
while True:
msg = input(">>:").strip()
if len(msg) == 0:continue
client.send(msg.encode("utf-8"))
data = client.recv() # 接收到 512 个字节
print(data.decode()) client.close()
#ssh_server import socket
import os server = socket.socket()
server.bind(("HW-20180425SPSL",6969)) # 绑定要监听的端口
server.listen(5) # 监听 最大允许多少监听 while True: # 大循环
conn, addr = server.accept() while True:
data = conn.recv(1024)
print(data.decode())
if not data:
print("client has lost....")
break
print("执行指令",data)
cmd_res = os.popen(data.decode()).read() # 接收字符串 执行结果也是字符串
if len(cmd_res) == 0:
cmd_res = "cmd has no output..."
conn.send(cmd_res.encode("utf-8")) server.close()
执行dir后,你就会发现执行命令后,返回结果不全!然后再执行pwd,你会发现执行pwd后,会返回dir没有显示的剩余数据!这是为什么呢?
这是因为,我们的客户写client.recv(512), 即客户端一次最多只接收512个字节,如果服务器端返回的数据是2000字节,那有至少1400多字节是客户端第一次接收不了的,那怎么办呢,服务器端此时不能把数据直接扔了呀,so它会暂时存在服务器的io发送缓冲区里,等客户端下次再接收数据的时候再发送给客户端。 这就是为什么客户端执行第2条命令时,却接收到了第一条命令的结果的原因。 这时有同学说了, 那我直接在客户端把client.recv(1024)改大一点不就好了么, 改成一次接收个100mb,哈哈,这是不行的,因为socket每次接收和发送都有最大数据量限制的,毕竟网络带宽也是有限的呀,不能一次发太多,发送的数据最大量的限制就是缓冲区能缓存的数据的最大量,这个缓冲区的最大值在不同的系统上是不一样的, 我实在查不到一个具体的数字,但测试的结果是,在linux上最大一次可接收10mb左右的数据,不过官方的建议是不超过8k,也就是8192,并且数据要可以被2整除,不要问为什么 。anyway , 如果一次只能接收最多不超过8192的数据 ,那服务端返回的数据超过了这个数字怎么办呢?比如让服务器端打开一个5mb的文件并返回,客户端怎么才能完整的接受到呢?那就只能循环收取啦。
## ssh_client ## import socket client = socket.socket() # 生命socket类型 同时 生成socket连接# 对相
client.connect(('HW-20180425SPSL',6969)) # 连接6969端口
while True:
msg = input(">>:").strip()
if len(msg) == 0:continue # 为空继续
client.send(msg.encode("utf-8")) # 将 字符串 进行编码 发送给 服务器端
data_size = client.recv(512) # 接收 服务端向客户端 发送的 cmd 操作命令后生成的数据的长度
print("命令的长度为:",data_size) # unicode
reserver_size = 0
while reserver_size < int(data_size.decode()): # 0 < 512
data = client.recv(512) # 循环第一次 len(data) = 512 , 循环第二次 len(data) = 201
reserver_size += len(data) # 每次收到有可能小于512 ,所以必须用len()判断
print(reserver_size) # 循环第一次 len(reserver_size) = 512 , 循环第二次 len(reserver_size) = 713
print(data.decode())
else: # 数据发送完毕
print("data res receive down...",reserver_size) client.close()
## ssh_server.py ## import socket
import os server = socket.socket()
server.bind(("HW-20180425SPSL",6969)) # 绑定要监听的端口
server.listen(5) # 监听 最大允许多少监听 while True: # 大循环
conn, addr = server.accept() while True:
data = conn.recv(512) # 客户端 向 服务端 发送过来的数据(也就是字符串)
print(data.decode()) # 将该字符串进行解码 打印该字符串
if not data: # 数据为空
print("client has lost....")
break
print("执行指令",data) # unicode
cmd_res = os.popen(data.decode()).read() # 接收cmd的字符串 执行结果也是字符串
if len(cmd_res) == 0: # cmd 发送过来的 数据长度为0
cmd_res = "cmd has no output..."
conn.send( str(len(cmd_res.encode()) ).encode("utf-8") ) #先发大小给客户端 因为 len(cmd_res)结果是整数,所以 需要将它变为字符串 ,因为只有字符串才可以encode
conn.send(cmd_res.encode("utf-8")) server.close()
ssh_server所显示出来的结果为:
dir
执行指令 b'dir'
ssh_client所显示出来的结果为:
>>:dir
命令的长度为: b'713'
驱动器 E 中的卷是 Lunix
卷的序列号是 561D-6560
E:\week_27_1 的目录
2018/07/03 20:30 <DIR> .
2018/07/03 20:30 <DIR> ..
2018/07/03 20:34 <DIR> .idea
2018/06/19 18:45 <DIR> app01
2018/07/03 20:30 1,070 client.py
2018/06/14 09:45 556 manage.py
2018/07/03 20:18 1,094 server.py
2018/06/14 09:48 <DIR> static
2018/06/19 15:53 <DIR> templates
2018/07/01 15:41 62
text.text
2018/06/14 09:44 <DIR> venv
2018/06/19 15:26 <DIR> week_27_1
4 个文件 2,782 字节
8 个目录 22,906,576,896 可用字节
data res receive down... 713
大聊Python----通过Socket实现简单的ssh客户端的更多相关文章
- Python进阶----SOCKET套接字基础, 客户端与服务端通信, 执行远端命令.
Python进阶----SOCKET套接字基础, 客户端与服务端通信, 执行远端命令. 一丶socket套接字 什么是socket套接字: 专业理解: socket是应用层与TCP/IP ...
- 运用socket实现简单的服务器客户端交互
Socket解释: 网络上的两个程序通过一个双向的通信连接实现数据的交换,这个连接的一端称为一个socket. Socket的英文原义是“孔”或“插座”.作为BSD UNIX的进程通信机制,取后一种意 ...
- 大爽Python入门教程 1-1 简单的数学运算
大爽Python入门公开课教案 点击查看教程总目录 1 使用pycharm建立我们的第一个项目 打开pycharm,点击菜单栏,File->New Project 在Location(项目地址) ...
- 大爽Python入门教程 1-3 简单的循环与判断
大爽Python入门公开课教案 点击查看教程总目录 这里只初步认识下循环和判断,以便于我们去实现一些简单的计算. 循环和判断的详细知识和细节,我们将在后面的章节(大概是第三章)展开阐述. 1 初步了解 ...
- 运用socket实现简单的ssh功能
在python socket知识点中已经对socket进行了初步的了解,那现在就使用这些知识来实现一个简单的ssh(Secure Shell)功能. 首先同样是建立两个端(服务器端和客户端) 需求是: ...
- Socket创建简单服务器和客户端程序
使用Socket编程创建简单服务器和客户端 要知道的 Socket-AddressFamily, SocketType, ProtocolType https://blog.csdn.net/weix ...
- python模块——socket (实现简单的C/S架构端通信操作CMD)
# 服务端代码#!/usr/bin/env python # -*- coding:utf-8 -*- __author__ = "loki" import socket impo ...
- python-socket实现简单的ssh客户端
客户端代码,监听端口号为 localhost 9999 #!/usr/local/bin/python3 # -*- coding:utf-8 -*- import socket client = s ...
- python之socket-ssh实例
本文转载自大王http://www.cnblogs.com/alex3714/articles/5830365.html 加有自己的注释,应该会比原文更突出重点些 一. 基本Socket实例 前面讲了 ...
随机推荐
- 会话模型与SSO
关于会话模型其实网站已有很多帖子说明,其中有关于sessionid,cookie以及他们之间的关系,自己先了解吧 1 会话模型 会话模型是客户端和服务端交互的一种模型,会话模型友好的处理了客户端有无通 ...
- intellij idea 如何将一个普通项目转换为maven项目
1.工程文件下新建文件pom.xml,并填写好内容. 2.在pom.xml 文件上右键 Add as Maven Project.
- 在html在添加cookie和读取cookie
1.保存cookie var oDate = new Date(); oDate.setDate(oDate.getDate() + );//有效期为30天 document.cookie = &qu ...
- xsy1436-括号游戏
题目 递归定义括号序列: 空串是括号序列 (A)是一个括号序列,其中A为括号序列 AB是一个括号序列,其中A,B均为括号序列 定义严格括号序列为形如(A)的括号序列,其中A为括号序列. 给出一个长度为 ...
- 前台界面(2)---CSS 样式
目录 1. 内联样式 2. 层叠样式表CSS 2.1. 类选择器 2.1.1. 颜色设置 2.1.2. 字号设置 2.1.3. CSS边框属性 2.1.4. 设置背景颜色 2.1.5. 设置布局边框 ...
- [CF1083B]The Fair Nut and Strings
题目大意:在给定的长度为$n(n\leqslant5\times10^5)$的字符串$A$和字符串$B$中找到最多$k$个字符串,使得这$k$个字符串不同的前缀字符串的数量最多(只包含字符$a$和$b ...
- [洛谷P4081][USACO17DEC]Standing Out from the Herd
题目大意:给你$n$个字符串,对每个字符串求出只在这个字符串中出现的字串的个数 题解:先建广义$SAM$,然后对每个点统计一下它的子树中是不是都是在同一个字符串中的,是的话,就把这个点标成这一个字符串 ...
- bzoj 1221: [HNOI2001] 软件开发 (网络流)
注意说如果直接从每天的新的连向旧的,那整个图的最大流还是不变,答案就一直会是Σni*f type arr=record toward,next,cap,cost:longint; end; const ...
- BZOJ3172 [Tjoi2013]单词 【AC自动机】
3172: [Tjoi2013]单词 Time Limit: 10 Sec Memory Limit: 512 MB Submit: 4293 Solved: 2083 [Submit][Stat ...
- HDOJ.1228 A + B (map)
A + B 点我挑战题目 点我一起学习STL-MAP 题意分析 讲字符串和数字用map对应即可 代码总览 /* Title:HDOJ.1228 Author:pengwill Date:2016-11 ...