Python Socketserver實現FTP文件上傳下載代碼實例
一、Socketserver實現FTP,文件上傳、下載
目錄結構

1、socketserver實現ftp文件上傳下載,可以同時多用戶登錄、上傳、下載
效果圖:



二、上面只演示了下載,上傳也是一樣的,來不及演示了,上代碼
1、客戶端
import socket,hashlib,os,json,sys,time
class 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 filename
put 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_size
msg_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 = 0
f = 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 = 0
filesize = 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,paramiko
import settings
class Mysocketserver(socketserver.BaseRequestHandler):
def put(self,*args):
'''
接受客戶端上傳文件
:return:
'''
cmd_dic = args[0]
filename = cmd_dic['filename'] #獲取文件名
filesize= cmd_dic['size'] #獲取文件大?。ㄗ止?jié))
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])
break
if __name__ == '__main__':
HOST,PORT='localhost',9999
server=socketserver.ThreadingTCPServer((HOST,PORT),Mysocketserver)
server.serve_forever()
settings.py 文件
import os BASE_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使用socketServer包搭建簡易服務器過程詳解
- python網絡編程:socketserver的基本使用方法實例分析
- Python通過socketserver處理多個鏈接
- python如何使用socketserver模塊實現并發(fā)聊天
- python SocketServer源碼深入解讀
- python利用socketserver實現并發(fā)套接字功能
- Python探索之SocketServer詳解
- 基于python socketserver框架全面解析
- 利用Python中SocketServer 實現客戶端與服務器間非阻塞通信
- Python使用SocketServer模塊編寫基本服務器程序的教程
- 實例講解Python中SocketServer模塊處理網絡請求的用法
- python網絡編程之TCP通信實例和socketserver框架使用例子
- python基于socketserver實現并發(fā),驗證客戶端的合法性
相關文章
兩行代碼解決Jupyter Notebook中文不能顯示的問題
這篇文章主要介紹了兩行代碼解決Jupyter Notebook中文不能顯示的問題,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧2021-04-04
Python強化練習之PyTorch opp算法實現月球登陸器
在面向對象出現之前,我們采用的開發(fā)方法都是面向過程的編程(OPP)。面向過程的編程中最常用的一個分析方法是“功能分解”。我們會把用戶需求先分解成模塊,然后把模塊分解成大的功能,再把大的功能分解成小的功能,整個需求就是按照這樣的方式,最終分解成一個一個的函數2021-10-10
Python基于Opencv來快速實現人臉識別過程詳解(完整版)
這篇文章主要介紹了Python基于Opencv來快速實現人臉識別過程詳解(完整版)隨著人工智能的日益火熱,計算機視覺領域發(fā)展迅速,今天就為大家?guī)碜罨A的人臉識別基礎,從一個個函數開始走進這個奧妙的世界,需要的朋友可以參考下2019-07-07
PyTorch之nn.ReLU與F.ReLU的區(qū)別介紹
這篇文章主要介紹了PyTorch之nn.ReLU與F.ReLU的區(qū)別介紹,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧2020-06-06

