马上注册,结交更多好友,享用更多功能^_^
您需要 登录 才可以下载或查看,没有账号?立即注册
x
问题描述:服务端读取报文头、报文体都没问题,但是读取报文尾的时候,内容是跟报文体是一样的,求大神指导
报文 = 报文头(标识报文体长度) + 报文体 + 报文尾(标识报文体的hash值,用于校验报文是否被篡改)
客户端import socket
import time
import json
import traceback
def connect(ip, port):
server_ip = ip
server_port = port
tcp_client = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
try:
tcp_client.connect((server_ip, server_port))
except socket.error:
print('连接失败!!!')
return tcp_client
def recv_msg(conn, length: int):
ret_msg = bytes()
recv_len = length
while recv_len > 0:
msg = conn.recv(recv_len)
ret_msg += msg
cur_len = len(msg)
recv_len -= cur_len
return ret_msg
def send_msg(tcp_client):
try:
data = dict()
data['name'] = 'login'
data['user_id'] = '8888'
data['password'] = '123456'
# for i in range(1000):
# data['demo_field_{}'.format(
# i)] = 'sdflakswdfnasdlfkjalnsdfknalksdjflkjaslkdfjlksajdflkjalksdfjlkasjdfklajslkdfjklsadjflks_{}'.format(
# i)
data['time'] = time.strftime("%Y-%m-%d")
# dict转json
str_json = json.dumps(data)
# 计算长度
length = len(str_json)
head = length.to_bytes(4, byteorder='big', signed=False)
#计算hash值
client_hash = "{:0>20}".format(str(hash(str_json)))
# 拼装报文头与报文体
msg = head + str_json.encode('utf-8') + client_hash.encode('utf-8')
print(msg)
tcp_client.send(msg)
# 1.先接收头四位报文头
len_msg = tcp_client.recv(4)
length = int.from_bytes(len_msg, byteorder='big', signed=False)
print('客户端收到报文长度:{}'.format(length))
# 2.再接收报文体
req_msg = recv_msg(tcp_client, length)
json_str = str(req_msg, encoding='utf-8')
print('客户端收到报文str:{}'.format(json_str))
req_msg_dict = json.loads(json_str)
# print('客户端收到报文dict:{}'.format(req_msg_dict))
except Exception as e:
print('连接失败!!!')
traceback.print_exc()
raise e
IP = '127.0.0.1'
PORT = 12581
if __name__ == '__main__':
conn = connect(ip=IP, port=PORT)
send_msg(conn)
conn.close()
服务端from socketserver import ThreadingTCPServer
from socketserver import StreamRequestHandler
import json
import traceback
def recv_msg(conn, length: int):
ret_msg = bytes()
recv_len = length
while recv_len > 0:
msg = conn.read(recv_len)
ret_msg += msg
cur_len = len(msg)
recv_len -= cur_len
return ret_msg
class MyStreamRequestHandler(StreamRequestHandler):
def handle(self):
print('连接上来啦, 连接号:[{0}]'.format(self.wfile))
while True:
try:
print("等待客户端发送报文...")
# 1.先接收头四位报文头
len_msg = self.rfile.read(4)
if len_msg:
length = int.from_bytes(len_msg, byteorder='big', signed=False)
print('服务端收到报文长度:{}'.format(length))
# 2.再接收报文体
req_msg = recv_msg(self.rfile, length)
# req_msg = self.rfile.read(length)
#接收报文尾
req_hash = str(self.rfile.read(20),encoding='utf-8')
json_str = str(req_msg, encoding='utf-8')
print('服务端收到报文str:{}'.format(json_str))
print('服务端收到hash:{}'.format(req_hash))
req_msg_dict = json.loads(str(req_msg, encoding='utf-8'))
# print('服务端收到报文dict:{}'.format(req_msg_dict))
# 发送应答
head = length.to_bytes(4, byteorder='big', signed=False)
rsp_msg = head + bytes(json.dumps(req_msg_dict), encoding='utf-8')
print('服务端发送应答报文:{}'.format(rsp_msg))
self.wfile.write(rsp_msg)
else:
# 客户端主动断开后,req_msg是b''
print('连接已断开, 连接号:[{0}]'.format(self.wfile))
break
except Exception as e:
print('Socket异常:{}'.format(e))
traceback.print_exc()
break
self.request.close()
def start_server(port: int):
# 设置IP 和 Port
addr = ('0.0.0.0', port)
# 使用socketserver库
server = ThreadingTCPServer(addr, MyStreamRequestHandler)
# 启动服务,线程挂起
server.serve_forever()
PORT = 12581
if __name__ == '__main__':
print("启动服务端!!!")
start_server(PORT)
print("服务端关闭")
|