python-文件上传下载

互联网 2022/5/14 14:21:13

一、数据粘包 【1】客户端两次发送请求,但是可能被服务端的同个recv收到,不能区分,会造成数据粘包(实际上需要服务端将两次请求区分接受) 二、服务器 # -*- coding:utf-8 -*- # __author__:pansy # 2022/5/14 import socket# 创建socket对象 sk = socket.socket() # …

一、数据粘包

【1】客户端两次发送请求,但是可能被服务端的同个recv收到,不能区分,会造成数据粘包(实际上需要服务端将两次请求区分接受)

二、服务器

# -*- coding:utf-8 -*-
# __author__:pansy
# 2022/5/14
import socket

# 创建socket对象
sk = socket.socket()
# 给服务器绑定ip和端口
sk.bind(('127.0.0.1',8889))
# 创建监听,监听客户端是否有发请求过来
sk.listen()

def get_file(sk_obj):
    '''
    接收文件
    :param sk_obj: 文件对象
    :return:
    '''
    # 从服务端会发送1个请求,用来传输文件大小,文件大小是整形,需要将string类型强转成int类型
    file_size = int(sk_obj.recv(1024).decode('utf8'))
    # 为了避免粘包,当执行完接收file_size语句后,需要告知post_file,文件大小已经接收成功
    sk_obj.sendall(b'ok')

    # 从服务端会发送1个请求,用来传输文件名称
    file_name = sk_obj.recv(1024).decode('utf8')
    sk_obj.sendall(b'ok')

    # 接收文件内容
    with open('./%s' %file_name,'wb') as f:
        while file_size > 0:
            f.write(sk_obj.recv(1024))
            file_size -= 1024


# 阻塞状态,若接收到数据,则阻塞解除
# accept返回一个套接字和客户端的ip端口
conn ,addr = sk.accept()

# 调用接收文件方法,conn是专门用来处理客户端业务的套接字
get_file(conn)

conn.close()
sk.close()

三、客户端

# -*- coding:utf-8 -*-
# __author__:pansy
# 2022/5/14
import os
import socket

# 创建socket对象
sk = socket.socket()
# 连接服务器,连接的是服务器绑定的ip和端口
sk.connect(('127.0.0.1',8889))

def post_file(sk_obj,file_path):
    '''
    发送文件,需要和接收文件一一对应
    :param sk_obj:文件对象
    :param file_path:文件路径
    :return:
    '''

    # 发送文件大小,用os.stat方法可以获取文件属性
    file_size = os.stat(file_path).st_size
    # 获取到的file_size是整形,不能直接编码,所以需要先强转成字符串
    sk_obj.sendall(str(file_size).encode('utf8'))
    # 为了避免粘包,需要用recv接收下参数,直到接收到ok后,才会继续下面的代码
    sk_obj.recv(1024)

    # 发送文件名称,用os.path.split方法,可以将文件路径切割成路径和文件名,返回这两个字段
    file_name = os.path.split(file_path)[1]
    sk_obj.sendall(file_name.encode('utf8'))
    sk_obj.recv(1024)

    # 发送文件内容,循环发送,1次发送1024个字节
    # 1、先读取文件,用rb二进制读取
    with open(file_path,'rb') as f:
        # 每发送1次,file_size会减少1024,不满足1024的,全部发送
        while file_size > 0:
            sk_obj.sendall(f.read(1024))
            file_size -= 1024

# 调用发送文件方法
path = '/Users/panshaoying/Desktop/database/data/img1.png'
post_file(sk,path)

sk.close()
随时随地学软件编程-关注百度小程序和微信小程序
关于找一找教程网

本站文章仅代表作者观点,不代表本站立场,所有文章非营利性免费分享。
本站提供了软件编程、网站开发技术、服务器运维、人工智能等等IT技术文章,希望广大程序员努力学习,让我们用科技改变世界。
[python-文件上传下载]http://www.zyiz.net/tech/detail-320933.html

赞(0)
关注微信小程序
程序员编程王-随时随地学编程

扫描二维码或查找【程序员编程王】

可以随时随地学编程啦!

技术文章导航 更多>