socketserver 之 recv(1024) 問題!


 



一、socket發送數據基本流程
  • 圖示
    • 流程解釋
      • 上述流程,為基本的收發數據流程,並且使用ack來解決粘包問題
      • 並且,最后通過獲取server發送的“get file success”來給予用戶友好展示

二、實際應用問題:
  • 問題表現:
    • client已經接收了完成了所有文件數據,但且還處於阻塞狀態,即:收不到"get file success"
  • 問題排查:
    • 查看 client 端收到的文件,發現 "get file success" 這個消息,被追加在了文件末尾!
    • 查看 client 端主要代碼:
with open(file, 'wb') as f1:
recv_size = 0
while recv_size < file_size:
data = self.sk.recv(1024)
recv_size += len(data)
f1.write(data)

print(self.sk.recv(1024).decode())  # 打印友好信息
print('send_file:{} md5_sum:{}'.format(file_size, file_sum), 'recv_file:{} md5_sum:{}'.format(recv_size, md5_sum), sep='\n')  # 打印文件md5值
  • 原因總結:
    • 因為client是通過 sk.recv(1024)來進行接受數據,而1024表示,最多每次接受1024字節,
    • 當文件本身所有數據小於1024時候,那么,最后的"get file success"友好信息也會被client一次性接受,表現在data = self.sk.recv(1024)
    • 即此時:
      • data包涵了文件本身的所有數據+"友好信息"數據,
      • 而當代碼走到print(self.sk.recv(1024).decode())時,便會阻塞(實際上server已經將友好信息發送,只不過因為1024的原因,當做了文件本身數據)
  • 解決方式:
    • 1、更改1024為更小單位,比如recv(10)
      • 接收次數變得更多,且若只要是文件,則一定有余數(文件大小 / 10),比如到最后剩余3字節沒有接受完,而 3< 10,所以這3字節還是會和“友好信息”混在一起
    • 2、不發送友好信息
      • 在client端直接判斷 recv_data_size 和 send_data_size,並計算文件哈希值,來判斷文件是否完整,
      • 本就該如此做,即刪掉兩端關於“友好信息”的交互代碼












 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM