• 网络编程传输文件


    简易版服务器server
    import socket,struct,json
    sk = socket.socket()
    buffer = 1024 #每次接收数据的大小
    sk.bind(('127.0.0.1',8090))
    sk.listen()
    conn,addr = sk.accept()
    #接收
    head_len = conn.recv(4)
    head_len = struct.unpack('i',head_len)[0] #解包
    json_head = conn.recv(head_len).decode('utf-8') #反序列化
    head = json.loads(json_head)
    filesize = head['filesize']
    with open(head['filename'],'wb') as f:
        while filesize:
            if filesize >= buffer: #>=是因为如果刚好等于的情况出现也是可以的。
                content = conn.recv(buffer)
                f.write(content)
                filesize -= buffer
            else:
                content = conn.recv(buffer)
                f.write(content)
                break
    
    conn.close()
    sk.close()
    文件传输服务端
    简易版客户端client
     1 import os,json,socket,struct
     2 sk = socket.socket()
     3 sk.connect(('127.0.0.1',8090))
     4 buffer = 1024 #读取文件的时候,每次读取的大小
     5 head = {
     6             'filepath':r'D:打包程序', #需要下载的文件路径,也就是文件所在的文件夹
     7             'filename':'xxx.mp4',  #改成上面filepath下的一个文件
     8             'filesize':None,
     9         }
    10 
    11 file_path = os.path.join(head['filepath'],head['filename'])
    12 filesize = os.path.getsize(file_path)
    13 head['filesize'] = filesize
    14 # json_head = json.dumps(head,ensure_ascii=False)  #字典转换成字符串
    15 json_head = json.dumps(head)  #字典转换成字符串
    16 bytes_head = json_head.encode('utf-8') #字符串转换成bytes类型
    17 print(json_head)
    18 print(bytes_head)
    19 
    20 #计算head的长度,因为接收端先接收我们自己定制的报头,对吧
    21 head_len = len(bytes_head) #报头长度
    22 pack_len = struct.pack('i',head_len)
    23 print(head_len)
    24 print(pack_len)
    25 sk.send(pack_len)  #先发送报头长度
    26 sk.send(bytes_head) #再发送bytes类型的报头
    27 
    28 #即便是视频文件,也是可以按行来读取的,也可以readline,也可以for循环,但是读取出来的数据大小就不固定了,影响效率,有可能读的比较小,也可能很大,像视频文件一般都是一行的二进制字节流。
    29 #所有我们可以用read,设定一个一次读取内容的大小,一边读一边发,一边收一边写
    30 with open(file_path,'rb') as f:
    31     while filesize:
    32         if filesize >= buffer: #>=是因为如果刚好等于的情况出现也是可以的。
    33             content = f.read(buffer) #每次读取出来的内容
    34             sk.send(content)
    35             filesize -= buffer #每次减去读取的大小
    36         else: #那么说明剩余的不够一次读取的大小了,那么只要把剩下的读取出来发送过去就行了
    37             content = f.read(filesize)
    38             sk.send(content)
    39             break
    40 
    41 sk.close()
    文件传输客户端

    实现的功能是客户端拟定一个文件传输路径然后再传送到服务器上面,相当于保存在网络云盘里面,如果是下载功能及相反,显示服务器里面自己拥有的文件夹,然后客户端进行接收,属于下载功能.

    升级版服务器server

    import socket
    import struct
    import json
    import subprocess
    import os
    
    class MYTCPServer:
        address_family = socket.AF_INET
    
        socket_type = socket.SOCK_STREAM
    
        allow_reuse_address = False
    
        max_packet_size = 8192
    
        coding='utf-8'
    
        request_queue_size = 5
    
        server_dir='file_upload'
    
        def __init__(self, server_address, bind_and_activate=True):
            """Constructor.  May be extended, do not override."""
            self.server_address=server_address
            self.socket = socket.socket(self.address_family,
                                        self.socket_type)
            if bind_and_activate:
                try:
                    self.server_bind()
                    self.server_activate()
                except:
                    self.server_close()
                    raise
    
        def server_bind(self):
            """Called by constructor to bind the socket.
            """
            if self.allow_reuse_address:
                self.socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
            self.socket.bind(self.server_address)
            self.server_address = self.socket.getsockname()
    
        def server_activate(self):
            """Called by constructor to activate the server.
            """
            self.socket.listen(self.request_queue_size)
    
        def server_close(self):
            """Called to clean-up the server.
            """
            self.socket.close()
    
        def get_request(self):
            """Get the request and client address from the socket.
            """
            return self.socket.accept()
    
        def close_request(self, request):
            """Called to clean up an individual request."""
            request.close()
    
        def run(self):
            while True:
                self.conn,self.client_addr=self.get_request()
                print('from client ',self.client_addr)
                while True:
                    try:
                        head_struct = self.conn.recv(4)
                        if not head_struct:break
    
                        head_len = struct.unpack('i', head_struct)[0]
                        head_json = self.conn.recv(head_len).decode(self.coding)
                        head_dic = json.loads(head_json)
    
                        print(head_dic)
                        #head_dic={'cmd':'put','filename':'a.txt','filesize':123123}
                        cmd=head_dic['cmd']
                        if hasattr(self,cmd):
                            func=getattr(self,cmd)
                            func(head_dic)
                    except Exception:
                        break
    
        def put(self,args):
            file_path=os.path.normpath(os.path.join(
                self.server_dir,
                args['filename']
            ))
    
            filesize=args['filesize']
            recv_size=0
            print('----->',file_path)
            with open(file_path,'wb') as f:
                while recv_size < filesize:
                    recv_data=self.conn.recv(self.max_packet_size)
                    f.write(recv_data)
                    recv_size+=len(recv_data)
                    print('recvsize:%s filesize:%s' %(recv_size,filesize))
    
    
    tcpserver1=MYTCPServer(('127.0.0.1',8080))
    
    tcpserver1.run()
    文件传输升级版本

    升级版客户端client

     1 import socket
     2 import struct
     3 import json
     4 import os
     5 
     6 
     7 class MYTCPClient:
     8     address_family = socket.AF_INET
     9 
    10     socket_type = socket.SOCK_STREAM
    11 
    12     allow_reuse_address = False
    13 
    14     max_packet_size = 8192
    15 
    16     coding='utf-8'
    17 
    18     request_queue_size = 5
    19 
    20     def __init__(self, server_address, connect=True):
    21         self.server_address=server_address
    22         self.socket = socket.socket(self.address_family,
    23                                     self.socket_type)
    24         if connect:
    25             try:
    26                 self.client_connect()
    27             except:
    28                 self.client_close()
    29                 raise
    30 
    31     def client_connect(self):
    32         self.socket.connect(self.server_address)
    33 
    34     def client_close(self):
    35         self.socket.close()
    36 
    37     def run(self):
    38         while True:
    39             inp=input(">>: ").strip()
    40             if not inp:continue
    41             l=inp.split()
    42             cmd=l[0]
    43             if hasattr(self,cmd):
    44                 func=getattr(self,cmd)
    45                 func(l)
    46 
    47 
    48     def put(self,args):
    49         cmd=args[0]
    50         filename=args[1]
    51         if not os.path.isfile(filename):
    52             print('file:%s is not exists' %filename)
    53             return
    54         else:
    55             filesize=os.path.getsize(filename)
    56 
    57         head_dic={'cmd':cmd,'filename':os.path.basename(filename),'filesize':filesize}
    58         print(head_dic)
    59         head_json=json.dumps(head_dic)
    60         head_json_bytes=bytes(head_json,encoding=self.coding)
    61 
    62         head_struct=struct.pack('i',len(head_json_bytes))
    63         self.socket.send(head_struct)
    64         self.socket.send(head_json_bytes)
    65         send_size=0
    66         with open(filename,'rb') as f:
    67             for line in f:
    68                 self.socket.send(line)
    69                 send_size+=len(line)
    70                 print(send_size)
    71             else:
    72                 print('upload successful')
    73 
    74 
    75 
    76 client=MYTCPClient(('127.0.0.1',8080))
    77 
    78 client.run()
    升级版客户端
  • 相关阅读:
    vue系列教程:插值
    docker load 镜像时出现:open /var/lib/docker/tmp/docker-import-500852078/repositories: no such file or dir
    Day 18: 记filebeat内存泄漏问题分析及调优
    Filebeat 启动关闭流程
    docker加速
    Docker镜像保存save、加载load(外网转移至内网)
    filebeat.yml(中文配置详解)
    kafka介绍
    基于统一开发平台的微服务架构转型升级之路 | 某国有大型银行案例
    转 -Filebeat + Redis 管理 LOG日志实践
  • 原文地址:https://www.cnblogs.com/lowen107/p/10032461.html
Copyright © 2020-2023  润新知