TCP简单实现文件上传与下载
Posted wen-kang
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了TCP简单实现文件上传与下载相关的知识,希望对你有一定的参考价值。
服务器端:
1 import socket
2 from ms.login import read
3 import os
4 import sys
5 import struct
6 import operator
7 import time
8 from ms.login import down
9 from ms.login import up
10
11 sk=socket.socket() #创建socket对象
12 sk.bind((‘127.0.0.1‘,8080)) #绑定地址
13 sk.listen() #监听
14
15 conn,addr=sk.accept() #建立一个连接
16
17 info=conn.recv(50).decode(‘utf-8‘) #接收客户端的用户名密码
18 user,psd=info.split(‘|‘) #分割获取用户名 和 密码
19
20 ret=read(user,psd) #调read读取用户名信息 验证用户名密码是否正确
21 if ret: #登录成功
22 conn.send(bytes(‘ok‘.encode(‘utf-8‘))) #返回一个OK
23 conn.send(bytes(‘用户登录成功,请选择要执行的操作【U:上传文件】【D:下载文件】‘.encode(‘utf-8‘)))
24
25 choice=conn.recv(4).decode(‘utf-8‘) #客户端选择上传还是下载
26
27 if choice==‘U‘: #文件上传
28 up(conn) #调上传方法
29
30 elif choice==‘D‘: # 文件下载
31 down(conn) #调下载方法
32 else:
33 print(‘error,错误的操作指令!‘)
34 else: #登录失败 关闭连接和对象
35 conn.send(bytes(‘用户登录失败,断开连接...‘.encode(‘utf-8‘)))
36 conn.close()
37 sk.close()
调用函数的模块:
1 import os
2 import sys
3 import struct
4 import operator
5 import time
6 import socket
7
8 #登录验证
9 def read(user,psd):
10 with open(‘info‘,‘r‘,encoding=‘utf-8‘)as f:
11 for i in f: #读取所有记录
12 i=i.strip() #去空格
13 if user in i: #如果用户名相匹配
14 n_user,n_psd=i.split(‘|‘) #分割字符串 得到用户名密码
15 if n_psd==psd:
16 return True #密码正确则为TRUE
17 else:
18 return False #错误则为FALSE
19 #上传
20 def up(conn):
21 long=conn.recv(4) #4字节的数据长度包
22 size=struct.unpack(‘i‘,long)[0]
23
24 ret=conn.recv(size).decode(‘utf-8‘) #来自客户端发过来的数据
25 print(ret)
26
27 path = os.path.dirname(os.path.abspath(__file__))
28 path = os.path.join(path, ‘up‘)
29
30 os.chdir(path)
31 filename = conn.recv(50).decode(‘utf-8‘)
32
33 with open(filename,‘w+‘,encoding=‘utf-8‘)as f:
34 f.write(ret)
35
36
37 #下载
38 def down(conn):
39 files = os.listdir()
40 lis_file = ‘‘
41 for i in files:
42 lis_file += i + ‘
‘
43 if operator.eq(lis_file, ‘‘): # 如果文件列表为空
44 conn.send(‘‘.encode(‘utf-8‘))
45 else:
46 conn.send(lis_file.encode(‘utf-8‘)) #把文件列表发给客户端
47 while True:
48 filename=conn.recv(1024).decode(‘utf-8‘) #接收要下载的文件名
49 if filename not in files:
50 conn.send(bytes(‘文件名不存在!‘.encode(‘utf-8‘)))
51 else:
52 conn.send(bytes(‘开始文件传输!‘.encode(‘utf-8‘)))
53 break
54 size=os.stat(filename).st_size
55 info=struct.pack(‘i‘,size)
56 conn.send(info) #文件信息大小打包发送给客户端
57
58 with open(filename,‘rb‘)as f:
59 while True:
60 file_data=f.read(4096)
61 if not file_data:
62 break
63 conn.send(file_data)
64
65 show=‘{0}
下载文件:{1}:
{2}byte
Successful...
‘.format(time.strftime(‘%Y-%m-%d:%H:%M:%S‘,time.localtime(time.time())),filename,size)
66 print(show)
67 path=os.path.dirname(os.path.abspath(__file__))
68 path=os.path.join(path,‘log‘)
69
70 os.chdir(path) #临时把当前目录变为 E:programmslog
71 with open(‘data_log‘,‘a‘,encoding=‘utf-8‘)as f:
72 f.write(show) #把输出信息记录入日志
客户端:
1 import socket
2 import struct
3 import os,sys
4 import operator
5 import time
6
7 sk=socket.socket()
8 sk.connect((‘127.0.0.1‘,8080))
9 user=input(‘请输入用户名:‘)
10 psd=input(‘请输入密码:‘)
11 login=str(user)+‘|‘+str(psd)
12 sk.send(bytes(login.encode(‘utf-8‘))) #传用户名密码给客户端
13 ret=sk.recv(1024).decode(‘utf-8‘) #接收登录状态 ok
14
15 if ret==‘ok‘:
16 menu=sk.recv(1024).decode(‘utf-8‘)
17 print(menu) #显示操作菜单
18 do=input(‘请输入要执行的操作...‘).upper()
19 sk.send(bytes(do.encode(‘utf-8‘))) #输入上传还是下载
20
21 #选择上传
22 if do==‘U‘:
23 path = input(‘请输入要上传的文件路径
‘)
24 filename = input(‘请输入文件名
‘)
25 size=struct.pack(‘i‘,os.stat(filename).st_size)
26 sk.send(size) #发送要上传文件的大小
27 long=os.stat(filename).st_size
28
29 with open(path,‘rb‘)as f:
30 while True:
31 file_data=f.read(4096)
32 if not file_data:
33 break
34 sk.send(file_data) #把要上传的数据传给服务器
35
36 show = ‘{0}
上传文件:{1}:
{2}byte
Successful...
‘.format(
37 time.strftime(‘%Y-%m-%d:%H:%M:%S‘, time.localtime(time.time())), filename,long)
38 print(show)
39 sk.send(bytes(filename.encode(‘utf-8‘)))
40
41
42 # 选择下载
43 elif do==‘D‘:
44 r=sk.recv(1024).decode(‘utf-8‘) #收到文件列表
45 if operator.eq(r,‘‘):
46 print(‘没有可以下载的文件‘)
47 print(r)
48 filename= input(‘请输入要下载的文件名>>>‘)
49 sk.send(bytes(filename.encode(‘utf-8‘))) #发送要下载的文件名
50 state=sk.recv(1024).decode(‘utf-8‘) #文件下载状态
51 print(state)
52
53 info=sk.recv(4) #4字节的包
54 size=struct.unpack(‘i‘,info)[0] #文件的字节大小
55 print(filename,size)
56
57 data=sk.recv(size).decode(‘utf-8‘)
58
59 path = os.path.dirname(os.path.abspath(__file__))
60 path = os.path.join(path, ‘down‘)
61 os.chdir(path)
62 with open(filename,‘w+‘,encoding=‘utf-8‘)as f:
63 f.write(data)
64 print(data)
65
66 else:
67 print(‘error,错误的操作指令!‘)
68
69
70 sk.close()
以上是关于TCP简单实现文件上传与下载的主要内容,如果未能解决你的问题,请参考以下文章