为什么我的客户端套接字在第一次发送后就死了?

乔佛

我正在尝试简单的脚本客户端套接字。我的代码如下:

import pickle
import socket

pole = ["mail","firewall","fria"]

c=False
while c==False:
   try:
     client = socket.socket ( socket.AF_INET, socket.SOCK_STREAM )
     client.connect ( ( 'localhost', 1234 ) )
     print("established")
     c=True
   except:
     print(".")

i = (len(pole)-1)
while i>=0:
   client.send(pickle.dumps(pole[i]))
   pole.remove(pole[i])
   i-=1

client.close()

另一端是“永远”的服务器。但是服务器仅接收一个数据。为什么没有所有领域?客户端“ while”循环应运行3次,因此应发送所有循环([[mail],“ firewall”,“ fria”])。这是服务器输出:

在此处输入图片说明

然后客户端结束。为什么?客户端应在发送所有数据后结束。为什么一个发送连接关闭后,为什么?

感谢帮助

编辑---> server.py:

import pickle
import socket

updated_data = []        
server = socket.socket ( socket.AF_INET, socket.SOCK_STREAM )
server.bind ( ( '', 1234 ) )
server.listen ( 5 )

while 1:
   channel, details = server.accept()
   print ('Received connection:', details [ 0 ])
   updated_data.append(pickle.loads(channel.recv(1024)))
   print (updated_data)

channel.close()
金库

我刚刚测试了您的代码,它揭示了您send()从循环中获取的所有消息都被服务器作为单个消息接收,并且pickle仅首先加载它们。基本上,收到的消息是

b'\x80\x03X\x04\x00\x00\x00friaq\x00.\x80\x03X\x08\x00\x00\x00firewallq\x00.\x80\x03X\x04\x00\x00\x00mailq\x00.'

如您所见,所有pole元素都在此字符串中-这意味着客户端在连接关闭之前发送所有数据,并且服务器从客户端接收所有数据。

解决方案是对消息进行构架(以设置消息的边界)。这个问题相对广为人知(针对tcp消息边界tcp消息框架的Google搜索结果)。

我发现这篇博客文章非常有帮助。它说:

消息成帧通常使用两种方法:长度前缀和定界符。

长度前缀为每条消息加上该消息的长度。长度前缀的格式(和长度)必须明确说明。通常选择“ 4字节有符号小尾数”(即C#中的“ int”)。要发送消息,发送方首先将消息转换为字节数组,然后发送字节数组的长度,然后发送字节数组本身。

由于存在部分接收的可能性,因此接收带有长度前缀的消息比较困难。首先,必须将消息的长度读入缓冲区,直到缓冲区已满(例如,如果使用“ 4字节有符号小尾数法”,则该缓冲区为4字节)。然后分配一个第二缓冲区,并将数据读入该缓冲区。当第二个缓冲区已满时,则到达一条消息,然后返回读取下一条消息的长度。

定界符更复杂才能正确处理。发送时,通常必须使用转义功能替换数据中的任何定界符。接收代码无法预测传入消息的大小,因此必须将所有接收到的数据附加到接收缓冲区的末尾,并根据需要增加缓冲区。找到分隔符后,接收方可以对接收缓冲区应用转义功能以获取消息。如果消息永远不会包含定界符,则可以跳过转义/取消转义功能。

在您的特殊情况下,我将使用Python list(将作为“自动分隔的容器”)进行序列化,pickle因此我将不得不稍稍更改您的代码。

客户

import pickle
import socket

pole = ["mail","firewall","fria"]

c = False
while not c:
    try:
        client = socket.socket ( socket.AF_INET, socket.SOCK_STREAM )
        client.connect ( ( 'localhost', 1234 ) )
        print("established")
        c = True
    except:
        print(".")

# - i = (len(pole)-1)
# - import time
# - while i>=0:
# -     client.send(pickle.dumps(pole[i]))
# -     pole.remove(pole[i])
# -     i-=1

# +
client.send(pickle.dumps(pole))

client.close()

服务器

import pickle
import socket

updated_data = []    
server = socket.socket ( socket.AF_INET, socket.SOCK_STREAM )
server.bind ( ( '', 1234 ) )
server.listen ( 5 )

while 1:
    channel, details = server.accept()
    print ('Received connection:', details[0])
    data = channel.recv(1024)
    if data:
        # Deserialize
        data = pickle.loads(data)
        # We're able to extend the list with another list:
        # [1, 2, 3].extend([4, 5, 6]) is [1, 2, 3, 4, 5, 6]
        updated_data.extend(data)
        print(updated_data)

channel.close()

现在代码可以工作了,服务器可以打印了

Received connection: 127.0.0.1
['mail', 'firewall', 'fria']

并按updated_data预期增长。

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

第一次成功后,Windows Mobile 6.5客户端套接字发送失败

来自分类Dev

套接字在第一次接收后停止

来自分类Dev

为什么我的C套接字文件传输(服务器/客户端)程序只能正确运行一次?

来自分类Dev

为什么在第一次迭代后就停止了?

来自分类Dev

为什么我的PXSmartPanel第一次执行后不能显示正确的数据?

来自分类Dev

为什么pgp在我使用--passphrase-fd后第一次询问密码

来自分类Dev

如何一次向龙卷风套接字客户端广播消息?

来自分类Dev

为什么我的客户端套接字输入流没有接收从服务器套接字输出流发送的消息

来自分类Dev

为什么setTimeout()第一次只运行一次我的代码?

来自分类Dev

使用客户端IP作为cookie,以识别重复访问并在第一次访问后显示一条消息

来自分类Dev

为什么我的客户端套接字无法连接到ServerSocket?

来自分类Dev

为什么我的客户端套接字无法连接到ServerSocket?

来自分类Dev

第一次循环后无法发送邮件

来自分类Dev

为什么我的for loop提示第一次被打印两次?

来自分类Dev

为什么我的提示第一次重复两次?

来自分类Dev

接受连接时创建多个套接字,但数据被视为由第一个连接的客户端发送

来自分类Dev

为什么第一次迭代后的指针指向随机值?

来自分类Dev

第一次用户输入后,函数中的行长默认为1,为什么?

来自分类Dev

为什么在第一次输入后连续的fget和sscanf不起作用

来自分类Dev

为什么getchar不能在第一次迭代后执行?

来自分类Dev

第一次单击后,随机按钮游戏为什么会有缺陷?

来自分类Dev

在TCP套接字程序中,客户端发送一些数据,但是服务器需要多次读取。为什么?

来自分类Dev

为什么要在客户端套接字之前打开服务器套接字?

来自分类Dev

为什么Java ServerSocket accept方法针对来自客户端的一个连接请求两次返回套接字?

来自分类Dev

为什么Java ServerSocket accept方法针对来自客户端的一个连接请求两次返回套接字?

来自分类Dev

为什么在我第一次在我的代码中插入一个项目后我的代码中出现分段错误

来自分类Dev

通过套接字写入发送时,为什么客户端浏览器中没有显示图像?

来自分类Dev

在保持客户端套接字打开以发送多条消息时,为什么在消息延迟很大时程序会报错?

来自分类Dev

为什么第一次收费很重要

Related 相关文章

  1. 1

    第一次成功后,Windows Mobile 6.5客户端套接字发送失败

  2. 2

    套接字在第一次接收后停止

  3. 3

    为什么我的C套接字文件传输(服务器/客户端)程序只能正确运行一次?

  4. 4

    为什么在第一次迭代后就停止了?

  5. 5

    为什么我的PXSmartPanel第一次执行后不能显示正确的数据?

  6. 6

    为什么pgp在我使用--passphrase-fd后第一次询问密码

  7. 7

    如何一次向龙卷风套接字客户端广播消息?

  8. 8

    为什么我的客户端套接字输入流没有接收从服务器套接字输出流发送的消息

  9. 9

    为什么setTimeout()第一次只运行一次我的代码?

  10. 10

    使用客户端IP作为cookie,以识别重复访问并在第一次访问后显示一条消息

  11. 11

    为什么我的客户端套接字无法连接到ServerSocket?

  12. 12

    为什么我的客户端套接字无法连接到ServerSocket?

  13. 13

    第一次循环后无法发送邮件

  14. 14

    为什么我的for loop提示第一次被打印两次?

  15. 15

    为什么我的提示第一次重复两次?

  16. 16

    接受连接时创建多个套接字,但数据被视为由第一个连接的客户端发送

  17. 17

    为什么第一次迭代后的指针指向随机值?

  18. 18

    第一次用户输入后,函数中的行长默认为1,为什么?

  19. 19

    为什么在第一次输入后连续的fget和sscanf不起作用

  20. 20

    为什么getchar不能在第一次迭代后执行?

  21. 21

    第一次单击后,随机按钮游戏为什么会有缺陷?

  22. 22

    在TCP套接字程序中,客户端发送一些数据,但是服务器需要多次读取。为什么?

  23. 23

    为什么要在客户端套接字之前打开服务器套接字?

  24. 24

    为什么Java ServerSocket accept方法针对来自客户端的一个连接请求两次返回套接字?

  25. 25

    为什么Java ServerSocket accept方法针对来自客户端的一个连接请求两次返回套接字?

  26. 26

    为什么在我第一次在我的代码中插入一个项目后我的代码中出现分段错误

  27. 27

    通过套接字写入发送时,为什么客户端浏览器中没有显示图像?

  28. 28

    在保持客户端套接字打开以发送多条消息时,为什么在消息延迟很大时程序会报错?

  29. 29

    为什么第一次收费很重要

热门标签

归档