import selectors
import socket
import os,time
BASE_DIR = os.path.dirname(os.path.abspath(__file__))
'''
知识点:
self.dic = {conn}、监听过程中 events 对象为活动列表。
总结:
read()不应该写死时间,重新监听执行到read()时通过dic分割、状态保持,
以判断选择执行代码逻辑,
'''
class selectFtpServer:
# sel = selectors.DefaultSelector()
def __init__(self):
self.ip_port=('127.0.0.1',8885)
self.sel=selectors.DefaultSelector()#根据平台选择最佳的IO多路机制,比如linux就会选择epoll
self.hasReceived=0
self.dic = {}
self.create_sock()
self.handle()
# 创建socket对象
def create_sock(self):
server = socket.socket()
server.bind(('localhost', 1234))
server.listen(100)
server.setblocking(False)
# 实例变量进行注册,sever与实例方法accept绑定
self.sel.register(server, selectors.EVENT_READ, self.accept)
print('server is running, waiting for connect')
def handle(self):
while True:
events = self.sel.select() # [server,conn1,conn2]活动列表
for key, mask in events:
callback = key.data # 触发accept
callback(key.fileobj, mask) # accept(new_socket,mask)
def accept(self,sock, mask):
print('登录服务端---')
conn, addr = sock.accept() # Should be ready
print('accepted', conn, 'from', addr)
conn.setblocking(False)
self.sel.register(conn, selectors.EVENT_READ, self.read)
self.dic[conn]={}#conn赋值
def read(self,conn, mask):
try:
if not self.dic[conn]:
data = conn.recv(1024)
try:
cmd, filename, filesize = str(data.decode("utf-8")).split("|")
self.dic[conn] = {"cmd": cmd, "filename": filename, "filesize": filesize, "hasReceived": 0}
except Exception as e:
cmd, filename = str(data.decode("utf-8")).split("|")
self.dic[conn] = {"cmd": cmd, "filename": filename,"filesize": os.path.getsize(os.path.join(BASE_DIR, "load", filename)),"hasSended": 0}
if cmd=='put':#上传
conn.send('ok'.encode('utf8'))
if cmd=='get':#下载
conn.send(str(self.dic[