繁体   English   中英

如何使用UDP python套接字从服务器向客户端发送大文件(2MB)多个文件

[英]How to send big image (2MB) multiple files from server to client with UDP python socket

我想通过UDP传输多个图像。 我知道可以使用TCP,但我想通过UDP使用它。 下面是我使用的代码片段。 是否可以通过UDP传输更大的文件? 我设法传输小文件,但对大文件失败。 我感谢使用UDP套接字的任何帮助或替代方法。

客户端代码接收图像。

BUF_SIZE = 1024
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
sock.bind(('localhost', port))
sock.settimeout(30)
def rcv_data(sock, num_packet_to_recv, file_size):
    bytes_rcvd = bytearray()
    f = open(download_dir , 'wb')
    print('Receiving packets will start')
    while num_packet_to_recv > 0:
        try:
           client_data, server_addr = sock.recvfrom(BUF_SIZE + 8)
           seq_num = client_b_data[-8:]
           img_data = client_data[:-8]
           num_packet_to_recv = num_packet_to_recv - 1
        #store img_data and seq_num to bytes_rcvd for later 
    #sorting by sequence number  
    f.write(sorted_bytes_rcvd)

    except Exception as e:
        print('rcv error {}'.format(e))
f.close()

服务器端发送数据

def send_img(host, port, file_name, num_pkt):
    try:
        sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
        sock.setblocking(0)
        sock.settimeout(60)
        client_addr = (host, port)
        # send the file name
        while num_pkt > 0:
            img_part = requested_file.read(BUF_SIZE + 8)
            sock.sendto(img_part + seq_num)
            num_pkt -= 1

您发布的代码似乎假设从发送方到接收方的途中不会丢弃任何数据包-这种假设在现实生活中不会成立(即使发送方和接收方都位于同一台机器上也是如此)!这是最可能的原因,除了很小的文件以外,传输不起作用(可以依靠运气来确保所有数据包都能在第一次尝试中通过)。

为了实现更强大的机制,您的接收器程序将需要某种方式(a)检测数据包何时被丢弃,并且(b)通过向发件人发送一条消息,要求发件人从以下位置重新传输数据来对此知识做出反应“丢失”的数据包。 (当然,重传请求包也可能会丢失,因此您还需要一种方法来处理它!)

同时,您的发送方程序不仅需要发送数据(如当前所做的那样),还需要从接收方接收任何传入的重新发送请求数据包,并通过重新发送请求的数据来对它们作出反应。

根据协议的确切设计,发送方和接收方可能还需要在经过一定时间后不发送或接收数据的情况下采取措施,以避免所有接收到数据包的文件传输过程都停顿下来。本来会先进的它被丢弃。

因此,您当前仅在循环中调用阻塞sendto()recvfrom()是不够的。 相反,发送方和接收方都将需要实现某种状态机,以使它们都可以在适当的时间发送适当的数据包,并快速接收和处理任何传入的数据包。通常可以单独进行此操作发送方和接收方线程,或者将套接字设置为非阻塞模式,并在对select()poll()的阻塞调用周围编写事件循环。 (我更喜欢后者,因为在状态机很难正确处理的同时,IMO更难于使用多线程)

在每个数据包中放置一个序列号是一个好的开始。 这样可以使接收器知道如何对数据进行排序,并使其能够检测到接收到的数据中是否有“空洞”。 一旦检测到漏洞(即一个或多个丢失的序列号),便可以将数据包发送回发送方,要求重新发送这些数据包,而发送方将通过重新发送这些数据包来做出反应。 视需要重复,直到接收器收到具有每个可能序列号的数据包(您还需要以某种方式与接收器通信,以期望有多少个序列号)。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM