Program implementation:1, single or multiple clients using Telnet to log on to the server (remote) for session2, service-side implementation login, registration, Exit Function3, messages sent by the client are broadcast to other user interfaces that have been logged in4, after connecting to the server, you can execute the corresponding program instruction code: https:coding.net/u/wangxiaoqiangs/p/pycode/git/tree/master/socket/gservergserver.py#!/usr/bin/env python#Coding:utf-8#Author:xiao GuaishouImportSocket fromDbImportDB fromThreadingImportCurrentThread, ThreadclassHandlerthread (object): Queue= []#sockect Queuedb =DB ()def __init__(self, sock): Self.sock=sockdefrecv (self): Data= Self.sock.recv (1024x768). Strip ()#If you use while to receive data, it causes the user to have to hit the enter key more than once returnDatadefSend (self, data): Self.sock.sendall ('\n[system]:%s\n'%data)#broadcast messages to the queue defBroadcast (self, user, data): forSockinchSelf.queue:sock.sendall ('\n[%s]:%s\n'%(user, data))#Close Client Connections defStop (self): Self.send ('byebye!') Self.sock.close () self.queue.remove (Self.sock)#after you close the connection, remember to delete it from the queue #Program Entry defhandler (self): funcdict= { 'Login': Self.login,'Register': Self.register}Try: Thname=CurrentThread (). GetName ()Print('[%s] Got connection from%s'% (Thname, Self.sock.getpeername ()))#all print data in the program will be replaced with the Loging module .Self.send ('Please select function: Login/register/exit') Data=self.recv ()ifdata = ='Exit': Self.stop ()#In fact, this should be done separately using self.sock.close () to close the connection, because there is no such connection in the queue, but with the following capture there is no problem ^_^ elifDatainchfuncdict:returnfuncdict.get (data) ()Else: Self.handler ()except:#If you don't capture it here, you won't be able to disconnect the client properly. Pass #Handling User Login defLogin (self): Self.send ('Login ... Please enter username password, format: User Password, enter Server: Execute program Instruction! ') User_data=self.recv ()#Program Internal Directives ifUser_data = ='Server:': Self.send ('\n\tserver:use reged\t Switch to the registration page \n\tserver:exit\t\t exit the system') User_data=self.recv ()ifUser_data = ='Server:use reged': Self.register ()elifUser_data = ='Server:exit': Self.stop ()Else: Self.send ('Input Error ...') DataList=User_data.split ()#determine user input, format is correct ifLen (datalist) = = 2: User=datalist[0] Password= Datalist[1] Db_data= Self.db.get_data ()or {} ifUserinchDb_data andPassword = =db_data.get (user): Self.queue.append (Self.sock)#users with permission to log on to the system, the connection is added to the queueSelf.send ('Welcome to the chat room, enter the Server: Get the Function Method! ') Self.broadcast ('System','[%s] Join the chat room! '%user) Self.chat_room (user)Else: Self.send ('User name, password error! ') Self.login () Self.login ()defRegister (self): Self.send ('Register ... Please enter username password, format: User Password, enter Server: Execute program Instruction! ') User_data=self.recv ()ifUser_data = ='Server:': Self.send ('\n\tserver:use login\t Switch to the registration page \n\tserver:exit\t\t exit the system') User_data=self.recv ()ifUser_data = ='Server:login': Self.login ()elifUser_data = ='Server:exit': Self.stop ()Else: Self.send ('Input Error ...') DataList=User_data.split ()ifLen (datalist) = = 2: User=datalist[0] Password= Datalist[1] Db_data= Self.db.get_data ()or {} ifUserinchDb_data:self.send ('the user name has been registered! ') Self.register ()Else: Db_data[user]=password Self.db.put_data (db_data) self.queue.append (self.sock) Self.bro Adcast ('System','new User [%s] join the chat room! '%user) Self.chat_room (user) Self.register ()defchat_room (self, user): User_data=self.recv ()ifUser_data = ='Server:': Self.send ('\n\tserver:logout\t exit chat room') User_data=self.recv ()ifUser_data = ='Server:logout': Self.stop ()return #If you do not add a return here, the Server: command executed by the client will also be broadcast Else: Self.send ('Input Error ...') self.chat_room (user)Else: Self.broadcast (User, User_data) self.chat_room (user)#create a thread for each connectiondefStartthread (sock, addr):Print('Received New Client connection.%s:%s'% (Addr[0], addr[1]) th=Handlerthread (sock) T= Thread (target=th.handler) T.setdaemon (True) T.start ()#Start the servicedefServer (): s=Socket.socket (socket.af_inet, socket. SOCK_STREAM) s.setsockopt (socket. Sol_socket, SOCKET. SO_REUSEADDR,1) S.bind ('0.0.0.0', 17170)) S.listen (1) whileTrue:Try: sock, addr=s.accept ()exceptKeyboardinterrupt:exit ('\nbyebye!') Startthread (sock, addr) s.close ()if __name__=='__main__': Server () db.py#Coding:utf-8ImportJSON#create a class instead of a databaseclassDB (object):def __init__(Self, path='storage.db'): Self.path=PathdefGet_data (Self, data=None):Try: With open (Self.path) as F:data=json.load (f)exceptIOError as E:returnData#when data is first taken, the default value of None is returned because the file does not exist or no data finally: returnDatadefPut_data (self, data): With open (Self.path,'W') as F:json.dump (data, F)
Python Multi-person chat tool (multi-threaded)