------------------------------------------------------------------------------------------------------------------------------------

 客户端代码模板:(以ssh为例)

# _*_ coding: gbk _*_
# @Author: Wonder import socket
import json
import struct client = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
client.connect(('172.16.10.19', 9527)) while True:
try:
cmd = input('>>>请输入指令').strip()
if not cmd:
continue
if cmd == 'q':
break
cmd = cmd.encode('utf-8')
dict_context = {
'data_size': len(cmd) # 二进制的长度
}
client_bytes = json.dumps(dict_context).encode('utf-8') # dict----->json------->binary 报头
head = struct.pack('i', len(client_bytes)) # struct 将报头长度巧妙的转为4 bit # 以下为一波socket三连发送操作。
client.send(head) # 发报头长度, client.send(client_bytes) # 发报头,里面有实际数据的长度 client.send(cmd) # 传数据 bin_head = client.recv(4) # 接收来自server的报头信息
json_head_len = struct.unpack('i', bin_head)[0] # unpack 获取报文头长度
head_json = client.recv(json_head_len).decode() # 解码 获得 json格式的 报头字典
dic_head = json.loads(head_json) # 反序列化,得到 data的长度所在的字典
size = dic_head.get('data_size') # 取到data的真实长度值
length = 0
bin_toatal = b'' while length < size:
bin_content = client.recv(500)
bin_toatal += bin_content
length += len(bin_content) # 此处要累加bin_content的长度
print('当前下载进度',size , length , length / size)
print('当前下载进度---------------->', length / size) print(bin_toatal.decode('gbk'))
except Exception as e:
print(e)
break client.close()

  

 服务端模板:

# _*_ coding: gbk _*_
# @Author: Wonder
import socket
import subprocess
import json
import struct server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server.bind(('172.16.10.180', 9527))
server.listen(3)
while True:
conn, addr = server.accept()
while True:
try: bin_head = conn.recv(4) # 获取4位长度的报文头
json_head = struct.unpack('i', bin_head)[0] # 获得报头长度--->int bin_head = conn.recv(json_head).decode('utf-8') # 获取报头信息 ------>binary----->JSON
dic_head = json.loads(bin_head) # 反序列化得到字典
size = dic_head.get('data_size') # 字典取值得到数据长度 length = 0
bin_toatal = b''
while length < size: # if 循环接收,直到长度和报头中的长度一致
bin_content = conn.recv(50)
bin_toatal += bin_content
length += len(bin_toatal) cmd = bin_toatal.decode('utf-8') subprocess_obj = subprocess.Popen(cmd, shell=True,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE)
stdout = subprocess_obj.stdout.read() # binary
stderr = subprocess_obj.stderr.read() back_data_len = len(stderr) + len(stdout)
print(back_data_len) server_dict = {
'data_size': back_data_len # 务必代表二进制的长度
}
back_json = json.dumps(server_dict).encode('utf-8') # 序列化成 json字典 ------->json----->binary
server_head = struct.pack('i', len(back_json)) # 转成4位长度的二进制, 表示报头长度
conn.send(server_head) # 发报头长度
conn.send(back_json) # 发报头
conn.send(stdout) # 发数据
conn.send(stderr) except Exception as e:
print(e)
break
conn.close()
server.close()

 

 

UDP的初级使用

UDP服务端(即时通讯,你一句我一句)

# _*_ coding: gbk _*_
# @Author: Wonder
import socket # 指定是 数据报,type= 一定要写,不然报错
sk = socket.socket(type=socket.SOCK_DGRAM)
sk.bind(
('127.0.0.1', 9527)
) while True:
data, addr = sk.recvfrom(1024)
print(data.decode('utf-8'))
sk.sendto('永不在线'.encode('UTF-8'), addr)

客户端要绑定, 接收是recvfrom ,接收的是data和addr ,发送是sendto,发送的是data和目标addr

UDP客户端

# _*_ coding: gbk _*_
# @Author: Wonder
import socket sk = socket.socket(type=socket.SOCK_DGRAM)
addr = ('127.0.0.1', 9527)
while True:
msg = input('>>>输入内容')
if msg == 'q':
break
sk.sendto(msg.encode('utf-8'), addr)
data, back = sk.recvfrom(1024)
print(data.decode('utf-8'))

  

CSIC_716_20191205【TCP-解决粘包问题、UDP模板】的更多相关文章

  1. tcp粘包,udp丢包

    TCP是面向流的, 流, 要说明就像河水一样, 只要有水, 就会一直流向低处, 不会间断. TCP为了提高传输效率, 发送数据的时候, 并不是直接发送数据到网路, 而是先暂存到系统缓冲, 超过时间或者 ...

  2. TCP通信粘包问题分析和解决

    转载至https://www.cnblogs.com/kex1n/p/6502002.html 在socket网络程序中,TCP和UDP分别是面向连接和非面向连接的.因此TCP的socket编程,收发 ...

  3. TCP粘包, UDP丢包, nagle算法

    一.TCP粘包 1. 什么时候考虑粘包 如果利用tcp每次发送数据,就与对方建立连接,然后双方发送完一段数据后,就关闭连接,这样就不会出现粘包问题(因为只有一种包结构,类似于http协议,UDP不会出 ...

  4. TCP通信粘包问题分析和解决(全)(转)

    TCP通信粘包问题分析和解决(全) 在socket网络程序中,TCP和UDP分别是面向连接和非面向连接的.因此TCP的socket编程,收发两端(客户端和服务器端)都要有成对的socket,因此,发送 ...

  5. tcp粘包、解决粘包问题

    目录 subproess模块 TCP粘包问题 粘包两种情况 解决粘包问题 struct模块的使用 使用struct模块解决粘包 优化解决粘包问题 上传大文件 服务端 客户端 UDP协议 upd套接字 ...

  6. 8-2udp和tcp网络编程以及粘包和解决粘包的方法

    一  tcp网络编程 server 端 import socket sk=socket.socket() #实例化一个对象 sk.setsockopt(socket.SOL_SOCKET,socket ...

  7. tcp的粘包和拆包示例以及使用LengthFieldFrameDecoder来解决的方法

    粘包和拆包是什么? TCP协议是一种字节流协议,没有记录边界,我们在接收消息的时候,不能人为接收到的数据包就是一个整包消息 当客户端向服务器端发送多个消息数据的时候,TCP协议可能将多个消息数据合并成 ...

  8. day31——recv工作原理、高大上版解决粘包方式、基于UDP协议的socket通信

    day31 recv工作原理 源码解释: Receive up to buffersize bytes from the socket. 接收来自socket缓冲区的字节数据, For the opt ...

  9. TCP粘包问题的解决方案02——利用readline函数解决粘包问题

      主要内容: 1.read,write 与 recv,send函数. recv函数只能用于套接口IO ssize_t recv(int sockfd,void * buff,size_t len,i ...

  10. 《精通并发与Netty》学习笔记(14 - 解决TCP粘包拆包(二)Netty自定义协议解决粘包拆包)

    一.Netty粘包和拆包解决方案 Netty提供了多个解码器,可以进行分包的操作,分别是: * LineBasedFrameDecoder (换行)   LineBasedFrameDecoder是回 ...

随机推荐

  1. CSS3 新特性(box-sizing盒模型,背景线性渐变,filter滤镜,calc函数,transition过渡)

    1.盒子模型(box-sizing) CSS3 中可以通过 box-sizing 来指定盒模型,有两个值:即可指定为 content-box.border-box,这样我们计算盒子大小的方式就发生了改 ...

  2. LeetCode Array Easy 119. Pascal's Triangle II

    Description Given a non-negative index k where k ≤ 33, return the kth index row of the Pascal's tria ...

  3. opensns功能详解

    <!DOCTYPE html> opensns功能详解 wmd-preview h1 { color: #0077bb; /* 将标题改为蓝色 */ } opensns功能详解 软件工程 ...

  4. Leetcode 200.岛屿的数量 - DFS、BFS

    Leetcode 200 岛屿的数量: DFS利用函数调用栈保证了检索顺序, BFS则需要自己建立队列,把待检索对象按规则入队. class Solution { // DFS解法,8ms/10.7M ...

  5. centos 7.6安装python3环境

    Centos7安装Python3的方法   由于centos7原本就安装了Python2,而且这个Python2不能被删除,因为有很多系统命令,比如yum都要用到. [root@VM_105_217_ ...

  6. java 多上传 CommonsMultipartFile[] files

    /** * 视频上传 * ddl * @param request * @param response * @param files * @return * @throws Exception */@ ...

  7. 配置Redis集群为开机自启动

    vim /etc/init.d/redisc 将下方脚本写入redisc文件中 #!/bin/sh # chkconfig: 2345 80 90 # # Simple Redis init.d sc ...

  8. Http头域字段详解

    HTTP(HyperTextTransferProtocol) 是超文本传输协议的缩写,它用于传送WWW方式的数据,关于HTTP协议的详细内容请参考RFC2616.HTTP协议采用了请求/响应模型.客 ...

  9. Peer模式的多线程程序例子

    Peer模式的多线程程序例子 程序的模型大概是这样的.有一个master(),用来分发任务.有N个多线程的slave用来处理任务. 主程序里可以这样调用: 可以看出,上面这段程序还是依赖于Proces ...

  10. 转-C++之虚函数不能定义成内联函数的原因

    转自:https://blog.csdn.net/flydreamforever/article/details/61429140 在C++中,inline关键字和virtual关键字分别用来定义c+ ...