网络编程终极版,粘包问题

>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>struct模块
import struct#打包数字模块

res=struct.pack('i',20312) #但后面放入的数字无限大的时候,'i'会变化不够用,但是专程json格式的时候,就够用了1000的数值等于4个字节
print(res.len(res))
##结果b'x0x00x00' 4

res2=struct.unpack('i',res)
print(res2)
###(20312,)结果为元组的形式




>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>服务端>>>>>>>>>>>>>>>>>>>>>>>>>>>>
from socket import *
import subprocess
import struct
import json

server=socket(AF_INET,SOCK_STREAM)
server.bind(('127.0.0.1',8080))
server.listen(5)

while True:
conn,client_addr=server.accept() #(连接对象,客户端的ip和端口)
print(client_addr)
while True:
try:
cmd=conn.recv(1024)#额,把远程客户端发来的消息执行一下,返回执行的结果发送到客户端
obj=subprocess.Popen(cmd.decode('utf-8'),
shell=True,
stdout=subprocess.PIPE,#把正确的值丢到这个PIPI管道
stderr=subprocess.PIPE#额,把错误的值丢到这个管道
)
#额,取出管道内的内容,这里是固定用法
stdout=obj.stdout.read()
stderr=obj.stderr.read()

# 1、制作报头
header_dic={
'total_size':len(stdout) + len(stderr),
'md5':'123svsaef123sdfasdf',
'filename':'a.txt'
}
header_json = json.dumps(header_dic)
header_bytes = header_json.encode('utf-8')

# 2、先发送报头的长度 #额,其实 是发送打包的的报头长度
header_size=len(header_bytes)
conn.send(struct.pack('i',header_size))

# 3、发送报头
conn.send(header_bytes)

# 4、发送真实的数据
conn.send(stdout)
conn.send(stderr)
except ConnectionResetError:
break

conn.close()
server.close()

>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>客户端>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
client=socket(AF_INET,SOCK_STREAM)
client.connect(('127.0.0.1',8080))
# print(client)

while True:
cmd=input('>>>: ').strip()
if not cmd:continue
client.send(cmd.encode('utf-8'))
#1、先收报头的长度
#额这里解开报头的打包里面就存放了了一个元组(12343242,)前面是字符串形式报头的长度
header_size=struct.unpack('i',client.recv(4))[0]


#2、接收报头 #额接受json形式字符串的字典报头
header_bytes=client.recv(header_size)

#3、解析报头
header_json=header_bytes.decode('utf-8')
header_dic=json.loads(header_json)
print(header_dic)

total_size=header_dic[ 'total_size']#额,根据字典里面的值来获得接受值的大小
# print(total_size) #1025
#4、根据报头内的信息,收取真实的数据

recv_size=0
res=b''
while recv_size < total_size:
recv_data=client.recv(1024)
res+=recv_data
recv_size+=len(recv_data)

print(res.decode('gbk'))
client.close()
 
原文地址:https://www.cnblogs.com/lijieshi/p/9285491.html