您的位置:首页技术文章
文章详情页

Python Socketserver实现FTP文件上传下载代码实例

【字号: 日期:2022-08-01 08:35:15浏览:17作者:猪猪

一、Socketserver实现FTP,文件上传、下载

目录结构

Python Socketserver实现FTP文件上传下载代码实例

1、socketserver实现ftp文件上传下载,可以同时多用户登录、上传、下载

效果图:

Python Socketserver实现FTP文件上传下载代码实例

Python Socketserver实现FTP文件上传下载代码实例

Python Socketserver实现FTP文件上传下载代码实例

二、上面只演示了下载,上传也是一样的,来不及演示了,上代码

1、客户端

import socket,hashlib,os,json,sys,timeclass Ftpclient(object): def __init__(self): self.client = socket.socket() def connect(self,ip,port): self.client.connect((ip, port)) def help(self): msg=’’’ ls pwd cd ..get filenameput filename’’’ print(msg) def interactive(self): ''' 客户端入口 :return: ''' while True: verify = self.authenticate() #服务器端认证 if verify:while True: cmd = input(’输入命令 >>’).strip() if len(cmd) == 0:continue cmd_str = cmd.split()[0] if hasattr(self,’cmd_%s’ %cmd_str): func = getattr(self,’cmd_%s’ %cmd_str) func(cmd) else: self.help() def cmd_put(self,*args): ''' 上传文件 :param args: :return: ''' cmd_solit = args[0].split() start_time = self.alltime() # 开始时间 if len(cmd_solit) > 1: filename = cmd_solit[1] if os.path.isfile(filename):filesize = os.stat(filename).st_sizemsg_dic = { ’filename’:filename, ’size’:filesize, ’overridden’:True, ’action’:cmd_solit[0]}self.client.send( json.dumps(msg_dic).encode(’utf-8’))server_respinse=self.client.recv(1024) #防止粘包,等服务器确认返回print(’文件开始上传’,server_respinse)client_size = 0f = open(filename,’rb’)for line in f: client_size += self.client.send(line) self.processBar(client_size,filesize) #进度条else: print(’文件传输完毕,大小为 %s’%client_size) end_time = self.alltime() # 结束时间 print(’本次上传花费了%s 秒’%self.alltime(end_time,start_time)) f.close() else:print(filename,’文件不存在’) else: print(’输入有误!’) def cmd_get(self,*args): ''' 下载文件 :param args: :return: ''' cmd_solit = args[0].split() start_time = self.alltime() # 开始时间 filename = cmd_solit[1] if len(cmd_solit) > 1: msg_dic = {’filename’: filename,’size’: ’’,’overridden’: True,’action’: cmd_solit[0],’file_exist’:’’ } self.client.send(json.dumps(msg_dic).encode(’utf-8’)) self.data = self.client.recv(1024).strip() cmd_dic = json.loads(self.data.decode(’utf-8’)) print(cmd_dic) if cmd_dic[’file_exist’]:if os.path.isfile(filename): f = open(filename + ’.new’, ’wb’)else: f = open(filename, ’wb’)self.client.send(b’200 ok’) #防止粘包,等服务器确认返回client_size = 0filesize = cmd_dic[’size’]m = hashlib.md5()while client_size < filesize: data=self.client.recv(1024) f.write(data) client_size +=len(data) m.update(data) self.processBar(client_size, filesize)else: print(’下载完毕’) end_time = self.alltime() # 结束时间 print(’本次下载花费了%s 秒’ % self.alltime(end_time, start_time)) f.close() new_file_md5 = m.hexdigest() server_file_md5 = self.client.recv(1024) print(’MD5’, server_file_md5,new_file_md5) else:print(’下载的 %s文件不存在’%filename) else: print(’输入有误!’) def cmd_dir(self,*arge): cmd_solit = arge[0].split() if len(cmd_solit) > 0: msg_dic = {’action’: cmd_solit[0] } self.client.send(json.dumps(msg_dic).encode()) cmd_dir = self.client.recv(1024) print(cmd_dir.decode()) else: print(’输入错误!’) def alltime(self,*args): ''' 计算上传、下载时间 :param args: :return: ''' if args: return round(args[0] - args[1]) else: return time.time() def processBar(self,num, total): ''' 进度条 :param num:文件总大小 :param total: 已存入文件大小 :return: ''' rate = num / total rate_num = int(rate * 100) if rate_num == 100: r = ’r%s>%d%%n’ % (’=’ * int(rate_num /3), rate_num,) else: r = ’r%s>%d%%’ % (’=’ * int(rate_num /3), rate_num,) sys.stdout.write(r) sys.stdout.flush def authenticate(self): ''' 用户加密认证 :return: ''' username = input(’输入用户名:>>’) password = input(’输入密码:>>’) m = hashlib.md5() if len(username) > 0 and len(password) >0: username = ’’.join(username.split()) password = ’’.join(password.split()) m.update(username.encode(’utf-8’)) m.update(password.encode(’utf-8’)) m = {’username’:username,’password’:password,’md5’:m.hexdigest() } self.client.send(json.dumps(m).encode(’utf-8’)) server_user_md5 = self.client.recv(1024).strip() print(server_user_md5.decode()) if server_user_md5.decode() == ’success’:print(’登录成功!’)return ’ok’ else:print(’用户名密码错误!’) else: print(’请输入用户名密码’)f = Ftpclient()f.connect(’localhost’,9999)f.interactive()

2、服务器端

import socketserver,json,os,hashlib,sys,paramikoimport settingsclass Mysocketserver(socketserver.BaseRequestHandler): def put(self,*args): ’’’ 接受客户端上传文件 :return: ’’’ cmd_dic = args[0] filename = cmd_dic[’filename’] #获取文件名 filesize= cmd_dic[’size’] #获取文件大小(字节) if os.path.isfile(filename): #判断文件是否存在 f = open(filename + ’.new’,’wb’) else: f = open(filename, ’wb’) self.request.send(b’200 ok’) #防止粘包 print(’%s 文件开始上传’ % self.client_address[0]) received_size = 0 while received_size < filesize: data = self.request.recv(1024) f.write(data) received_size += len(data) else: print(’文件传输完毕’,filename) def get(self, *args): ’’’ 客户端下载文件 :return: ’’’ msg_dic = { ’filename’: ’’, ’size’: ’’, ’overridden’: True, ’action’: ’’, ’file_exist’: ’’ } cmd_solit = args[0] filename = cmd_solit[’filename’] file_exist = os.path.isfile(filename) msg_dic[’file_exist’] = file_exist print(file_exist) if file_exist: filesize = os.stat(filename).st_size msg_dic[’filename’] = filename msg_dic[’size’] = filesize msg_dic[’action’] = cmd_solit[’action’] self.request.send(json.dumps(msg_dic).encode(’utf-8’)) server_respang = self.request.recv(1024) #防止粘包 print(’开始传输’,server_respang) f = open(filename,’rb’) m = hashlib.md5() for lien in f:m.update(lien)self.request.send(lien) else:print(’传输完成’)f.close()self.request.send(m.hexdigest().encode()) else: print(’文件不存在’) self.request.send(json.dumps(msg_dic).encode(’utf-8’)) def client_authentication(self): ''' 客户端认证 :return: ''' self.client_user= self.request.recv(1024).strip() client_xinxi = json.loads(self.client_user.decode(’utf-8’)) try: with open(settings.school_db_file + client_xinxi[’username’],’rb’) as f:data = json.load(f)if data[’md5’] == client_xinxi[’md5’]: #判断用户输入是否和服务器端MD5是否一致 print(’验证成功!’) self.request.send(’success’.encode()) return ’success’else: self.request.send(’error’.encode()) except Exception as e: print(’没有此用户’,e) self.request.send(’error’.encode()) def dir(self,*args): ''' 查看目录 :param args: :return: ''' cmd_split = args[0] dd=cmd_split[’action’] result_os = os.popen(dd).read() self.request.send(result_os.encode()) def handle(self): ''' 服务器端入口 :return: ''' while True: try:success = self.client_authentication()if success: self.data=self.request.recv(1024).strip() cmd_dic = json.loads(self.data.decode(’utf-8’)) action = cmd_dic[’action’] if hasattr(self,action): func = getattr(self,action) func(cmd_dic) except ConnectionResetError as e:print(’连接断开’,self.client_address[0])breakif __name__ == ’__main__’: HOST,PORT=’localhost’,9999 server=socketserver.ThreadingTCPServer((HOST,PORT),Mysocketserver) server.serve_forever()

settings.py 文件

import osBASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))DB_FILE = os.path.join(BASE_DIR, 'data')school_db_file = os.path.join(DB_FILE)print(school_db_file)

data里两个做测试的文件,

alex 文件内容: {'username': 'alex', 'password': '123456', 'md5': '94e4ccf5e2749b0bfe0428603738c0f9'}

kml123456文件内容:{'username': 'kml123456', 'password': '123456','md5': 'a791650e70ce08896e3dafbaa7598c26'}

到这里差不多就没了,

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持好吧啦网。

标签: Python 编程
相关文章: